简体   繁体   English

如何在没有闪烁的情况下恢复最小化窗口

[英]How to restore minimized window without flicker

I've made an expose-clone for Vista that sometimes need to restore a minimized window. 我为Vista制作了一个暴露克隆,有时需要恢复最小化的窗口。 I've managed to do this with the SetWindowPlacement function. 我已经设法使用SetWindowPlacement函数执行此操作。 The problem is that this also repaints the window which looks like crap after the window nicely has slided into the screen. 问题是,在窗口很好地滑入屏幕后,这也重新粉刷了看起来像垃圾的窗口。

This is the code i use to bring a window to the top and give it focus: 这是我用来将窗口置于顶部并给予焦点的代码:

    private static void ActivateWindow(IntPtr windowToShow)
    {
        RectAPI r = new RectAPI();
        Win32.GetWindowRect(windowToShow, ref r);

        if (r.top == -32000) //r.top is -32000 if the window is in minimized state
        {
            WINDOWPLACEMENT wp = new WINDOWPLACEMENT();
            Win32.GetWindowPlacement(windowToShow, ref wp);

            if (wp.flags == WindowPlacementFlags.WPF_RESTORETOMAXIMIZED)
                wp.showCmd = cmdShow.SW_SHOWMAXIMIZED;
            else
                wp.showCmd = cmdShow.SW_RESTORE;

            Win32.SetWindowPlacement(windowToShow, ref wp);
        }

        Win32.SetForegroundWindow(windowToShow);
    }

If i use it on a window that is already restored it will only call SetForegroundWindow and the window will get to the top of the z-order and get focus without any flicker. 如果我在已经恢复的窗口上使用它,它将只调用SetForegroundWindow,窗口将到达z顺序的顶部并获得焦点而没有任何闪烁。

But if i call it on a minimized window I also have to use SetWindowPlacement to bring back the window to restored state. 但是如果我在最小化窗口上调用它,我还必须使用SetWindowPlacement将窗口恢复到恢复状态。 This is what causes the window to repaint and flicker :/ 这是导致窗口重绘和闪烁的原因:/

There has to be a way to restore a minimized window without the flicker because the built in window manager does this. 必须有一种方法可以在没有闪烁的情况下恢复最小化的窗口,因为内置的窗口管理器可以做到这一点。

One way to do it is to use double-buffering technique: paint to an off-screen bitmap, then restore, then blit the bitmap to the screen. 一种方法是使用双缓冲技术:绘制到屏幕外的位图,然后恢复,然后将位图blit到屏幕。 But it seems like overkill if restoring a minimized window is the only scenario where it's needed. 但是,如果恢复最小化窗口是唯一需要它的情况,那似乎有些过分。 Maybe others will have better ideas?.. 也许其他人会有更好的想法?...

Also, if you paint entire window client area, you can disable WM_ERASEBKGND (or rather, say that you processed it but don't do anything) to avoid unneeded fill-with-background-then-redraw sequence. 此外,如果您绘制整个窗口客户区,您可以禁用WM_ERASEBKGND(或者更确切地说,表示您已处理它但不执行任何操作)以避免不必要的填充背景然后重绘序列。

This link on MSDN will explain how you would want to handle the window painting in your case. MSDN上的此链接将说明您希望如何处理窗口绘制。 Window events like window refresh or minimize/maximize will require repainting of your window or a region of the window. 窗口事件(如窗口刷新或最小化/最大化)将需要重新绘制窗口或窗口区域。

Happy Coding!! 快乐编码!!

I'm OP...accidentaly ate my cookie. 我是OP ...偶然吃了我的饼干。

Studied how windows flip3d and the taskbar manages this a bit closer and they actually repaint the window before they start the animation of the thumb. 研究了如何将windows flip3d和任务栏管理得更近,他们实际上在重新启动拇指动画之前重新绘制窗口。 Try to minimize a window and then restore it with flip3d, you will see a small blink on the 3d-window before it get restored. 尝试最小化窗口然后使用flip3d恢复它,在3d窗口恢复之前会看到一个小的闪烁。

Tried the same thing with my app and it looks alot better, not perfect but acceptable :/ 用我的应用尝试了同样的事情它看起来好多了,不完美但可以接受:/

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM