为什么我无法使用 Windows API 函数获得正确的光标坐标?

问题描述 投票:0回答:1

我正在尝试捕获 Windows 应用程序中光标的坐标。虽然位置 (0, 0) 的坐标在左上角正确显示,但随着远离它,坐标变得越来越扭曲,因此不再是 (600, 600),而只是 (583, 560)显示在右下角。这是我正在使用的代码


#include <windows.h>
#include <stdio.h>

LRESULT MainWindowProcedure(HWND Window, UINT Message, WPARAM WParam, LPARAM LParam)
{
    switch (Message)
    {
        case WM_MOUSEMOVE:
        {
            POINT Cursor;
            GetCursorPos(&Cursor);
            ScreenToClient(Window, &Cursor);

            char Buffer[256];
            snprintf(Buffer, sizeof(Buffer), "X: %d, Y: %d \n", Cursor.x, Cursor.y);
            OutputDebugStringA(Buffer);

        } break;
        case WM_DESTROY:
        {
            PostQuitMessage(0);
        } break;
        default:
        {
            return DefWindowProc(Window, Message, WParam, LParam);
        } break;
    }
}

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
        WNDCLASSEXA WindowClass = {0};

        WindowClass.cbSize = sizeof(WNDCLASSEXA);
        WindowClass.style = CS_HREDRAW | CS_VREDRAW;
        WindowClass.lpfnWndProc = MainWindowProcedure;
        WindowClass.hInstance = hInstance;
        WindowClass.lpszClassName = "WindowClass";

        if (RegisterClassExA(&WindowClass) != 0)
        {
            HWND Window = CreateWindowExA(0, "WindowClass", "Window", WS_OVERLAPPEDWINDOW | WS_VISIBLE, 
                CW_USEDEFAULT, CW_USEDEFAULT, 600, 600, 0, 0, hInstance, 0);
            if (Window != 0)
            {

                int Running = 1;
                while (Running) {

                    MSG Message;

                    while (PeekMessageA(&Message, 0, 0, 0, PM_REMOVE))
                    {
                        if (Message.message == WM_QUIT)
                        {
                            Running = false;
                            break;
                        }

                        TranslateMessage(&Message);
                        DispatchMessageA(&Message);
                    }

                }
            }
        }
}

我还尝试了 Windowsx.h 中的 GET_X_LPARAM 和 GET_Y_LPARAM。完全相同的问题。有人知道问题出在哪里吗?

c winapi
1个回答
0
投票

一切似乎都按设计进行。当鼠标光标在窗口的客户区移动时,系统如实地报告光标坐标。

这个问题是一种误导性的期望。调用

nWidth
 时的 nHeight
CreateWindowExA()
参数描述窗口的宽度和高度,包括非客户区域(边框、标题栏等)。

有关应用程序窗口的文档条目有以下插图,演示了客户区域如何小于窗口矩形:

window overview

要找出鼠标光标相对于窗口客户区域的位置,您可以调用

GetClientRect()
来确定客户区域的范围或创建具有特定客户区域大小的窗口。
AdjustWindowRectEx()
计算给定客户端大小的窗口大小。

请记住,所有这些都受 DPI 虚拟化的影响。 Windows 上的高 DPI 桌面应用程序开发涵盖了详细信息。

© www.soinside.com 2019 - 2024. All rights reserved.