Scrolling the window under the mouse

If you look at Visual Studio 2012, you will notice that if you use the mouse wheel, the window under the mouse will scroll, not the focused window. That is, if you have a pointer in the code editor and hover over the solution browser window and scroll, the solution browser will scroll, not the code editor. The WM_MOUSEWHEEL message, however, is sent only to the focused window, so in this case the code editor. How can we implement our program in such a way that WM_MOUSEWHEEL messages scroll the window under the mouse, which is an intuitive and not a focused window?

+4
source share
3 answers

Apparently, we can solve this problem in the center of the program. Look at your code for the message loop that should be in your WinMain method:

while (GetMessage (&msg, NULL, 0, 0) > 0)
{
    TranslateMessage (&msg);
    DispatchMessage (&msg);
}

Here we just need to say that if the message is a WM_MOUSEWHEEL message, which we want to transfer to the window under the mouse, and not in the focus window:

POINT mouse;

while (GetMessage (&msg, NULL, 0, 0) > 0)
{
    //Any other message.
    if (msg.message != WM_MOUSEWHEEL)
    {
        TranslateMessage (&msg);
        DispatchMessage (&msg);
    }
    //Send the message to the window over which the mouse is hovering.
    else
    {
        GetCursorPos (&mouse);
        msg.hwnd = WindowFromPoint (mouse);
        TranslateMessage (&msg);
        DispatchMessage (&msg);
    }
}

And now in the window under the mouse scrolls will always appear, rather than a focused window.

+6
source

Process the WM_MOUSEWHEEL message both in the parent and in the child window that should receive the message.

Do something similar in the WM_MOUSEWHEEL handler for your child window:

    POINT mouse;
    GetCursorPos(&mouse);
    if (WindowFromPoint(mouse) != windowHandle)
    {
        // Sends the WM_MOUSEWHEEL message to your parent window
        return DefWindowProc(windowHandle, message, wParam, lParam);
    }

Then, in the WM_MOUSEWHEEL handler for your parent window, you do:

    POINT mouse;

    GetCursorPos(&mouse);
    HWND hwnd = WindowFromPoint(mouse);

    SendMessage(hwnd, message, wParam, lParam);

, , , , WM_MOUSEWHEEL.

+2

I found out that it is much easier to override the PreTranslateMessage function in your application class.

BOOL MyApp::PreTranslateMessage(MSG* pMsg)
{
    POINT mouse;
    CWnd* windowUnderMouse;

    if (pMsg->message == WM_MOUSEWHEEL)
    {
        GetCursorPos(&mouse);       
        pMsg->hwnd = WindowFromPoint(mouse);
    }

    return CWinApp::PreTranslateMessage(pMsg);
}

Hope this helps someone.

+2
source

All Articles