如何准确地测量用英寸或厘米鼠标移动与已知DPI鼠标(How to accurately measur

2019-08-17 16:02发布

我有一个在它的5700 DPI完全运行的罗技G500游戏鼠标。

我想用C ++可以准确地测定物理单位鼠标,即水平运动的程序。 厘米或英寸。

我使用Windows API和Windows原始输入通过WM_INPUT消息得到鼠标移动原料的变化。

然后我假定1个单元通过WM_INPUT报道运动是一英寸的1 /第五千七,并且如我跟踪鼠标的净移动,以为可以执行一个简单的计算,得到净物理运动:

距离(英寸)= total_movement_from_wminput / DPI; // DPI = 5700在这种情况下

不幸的是,计算似乎并不准确。 我可以从物理测量告诉只是我的鼠标垫,即在大约鼠标移动的6英寸,计算产生约值5个半英寸(一回合1/2英寸的损失)。

我要去哪里错了? 我已经把我的鼠标5700DPI在它的控制面板,可它的实际DPI不到呢? 我通过WM_INPUT是物质运动的1 / DPI英寸不正确约1个单位变化的假设?

有没有人对我怎么能拿这是准确的任何想法? 谢谢!

Answer 1:

渣,

看来,当你移动鼠标比Windows快事件的问题可能是WM_INPUT处理它。 例如,假设鼠标在一帧中移动2个像素。 您将有一英寸的1 /第五千七(在你的情况)的损失,因为对于一个 WM_INPUT事件处理,你会移动两个像素。

为了解决这个问题,你应该检查多少像素移动鼠标,每次WM_INPUT消息发送到该程序的时间。 你所要做的是使一个RAWINPUTDEVICE变量,并设置结构,因此有关于鼠标的信息。

以下代码注册RAWINPUTDEVICE因此它可被用WM_INPUT

RAWINPUTDEVICE Rid[1];
Rid[0].usUsagePage = HID_USAGE_PAGE_GENERIC;
Rid[0].usUsage = HID_USAGE_GENERIC_MOUSE; 
Rid[0].dwFlags = RIDEV_INPUTSINK;   
Rid[0].hwndTarget = hWnd;
RegisterRawInputDevices(Rid, 1, sizeof(Rid[0]);

下面的代码实际上可以使用Rid变量2确定鼠标已经多少像素自从上次移动WM_INPUT已启动。

case WM_INPUT: 
{
    UINT dwSize = 40;
    static BYTE lpb[40];

    GetRawInputData((HRAWINPUT)lParam, RID_INPUT, 
                    lpb, &dwSize, sizeof(RAWINPUTHEADER));

    RAWINPUT* raw = (RAWINPUT*)lpb;

    if (raw->header.dwType == RIM_TYPEMOUSE) 
    {
        int xPosRelative = raw->data.mouse.lLastX; // Could be 1, or could be more than 1
        int yPosRelative = raw->data.mouse.lLastY; // Could be 1, or could be more than 1!
    } 
    break;
}

请注意,这个代码是在MSDN上提出这个题目(以下链接)相同的代码。

现在,您可以有某种类型的具有鼠标的x位置和y位置(以像素为单位)全局变量。 然后,您只需通过DPI划分这些变量,你必须从英寸偏移量,只要你设置的全局变量为0。


一个完全更简单的方法将处理WM_MOUSEMOVE事件来代替。 它可以很容易得到鼠标的确切位置(以像素为单位,当然)。 利用这一点,你可以从起始位置的像素值减去这个。

例:

DPI = 5700。

初始位置=(100像素,300像素)。

3秒=后位置(500像素,400像素)。

英寸的量在这些3秒=( - 100像素)/5700英寸,(400像素 - 300像素)/5700英寸(500像素)移动

一般规则 : - / DPI英寸英寸的量S秒=(final_pixels_x inital_pixels_x)后移

水平地(initial_pixels_y - final_pixels_y)/ DPI英寸垂直

这里,final_pixels_x为s秒后的鼠标的x位置,并且final_pixels Y是S秒后的y位置。


总之你做错了什么,你错误地假定每个WM_INPUT事件是指在1个像素由鼠标走过。

如果我因为某种原因误解了这个问题,你知道,你已经得到正确的像素量移动,请留下评论,我会尽我所能,试图解决我的答案。 不过,我还是会建议使用WM_MOUSEMOVE而不是WM_INPUT ,因为它是专门为鼠标和适用“指针加速”,你可以在最下方的链接阅读。

谢谢你问你的问题,tcs08

MSDN代码和说明用于与WM_INPUT鼠标输入

MSDN代码和说明用于与WM_MOUSEMOVE鼠标输入



文章来源: How to accurately measure mouse movement in inches or centimetres for a mouse with a known DPI