EJ42
EJ42

Reputation: 61

Can I make MoveWindow use screen coordinates in Windows 10? C++

I wrote a simple utility that lets you move and/or resize any window on the screen by typing the new desired width, height, and upper-left corner of the window. It works great on 100% scaling, but it fails when I change the scaling.

For example, on my 4k display, I have 150% scaling set. MoveWindow treats my 3840x2160 display as if it is a 2560x1440 display. When I tell a window to move to (1280,0), it moves the upper-left corner to the top-center of the screen. I want my program to do that when I put in (1920,0) instead. The problem with this is that I can still physically move the window to every single pixel on the screen. MoveWindow just loses access to the extra pixels that fall in-between.

Is there something I can do to force MoveWindow to ignore the scaling value?

Upvotes: 2

Views: 1824

Answers (2)

EJ42
EJ42

Reputation: 61

As IInspectable said earlier, the program did fail on Windows 7 until I made the following changes. So far, this seems to work fine on Windows 7 through 10.

    if (IsWindows8Point1OrGreater())
    {
        HINSTANCE hinstLib;
        MYPROC ProcAdd;
        BOOL fFreeResult, fRunTimeLinkSuccess = FALSE;

        hinstLib = LoadLibrary(TEXT("SHCore.dll"));

        if (hinstLib != NULL)
        {
            ProcAdd = (MYPROC)GetProcAddress(hinstLib, "SetProcessDpiAwareness");

            if (NULL != ProcAdd)
            {
                fRunTimeLinkSuccess = TRUE;
                HRESULT ejHR = (ProcAdd)(PROCESS_PER_MONITOR_DPI_AWARE);
            }

            fFreeResult = FreeLibrary(hinstLib);
        }

        if (!fRunTimeLinkSuccess)
        {
            SetProcessDPIAware();
        }
    }
    else if (IsWindowsVistaOrGreater())
    {
        SetProcessDPIAware();
    }

Upvotes: 2

EJ42
EJ42

Reputation: 61

Jonathan Potter was right. All I had to do was set the DPI awareness, and then all of my MoveWindow calls worked at the true resolution regardless of which other program's windows I chose to move or resize. I just added the following code to WinMain:

if (IsWindowsVistaOrGreater())
{
    HRESULT ejHR = SetProcessDpiAwareness(PROCESS_PER_MONITOR_DPI_AWARE);
}
else
{
    SetProcessDPIAware();
}

Upvotes: 0

Related Questions