C :使用全局鼠标钩的窗口重新位置
c++: window re-position with global mouse hook
我正在尝试开发桌面分隔线之类的应用程序。我使用了全局鼠标钩(低级鼠标钩),因为当将窗口拖动到特定位置后,左键向上时,窗口位于特定位置并调整大小。首先,当左键向上时,我尝试将窗口重新位置到桌面屏幕的左角。我使用setWindowpos方法重新定位和调整大小,它不正常。当我释放左键时,窗口位于特定位置,但立即返回原始位置。在调试应用程序时,它很好地进入了屏幕的左角。我不知道为什么会发生这种情况。以下是我的代码。
LRESULT CALLBACK LowLevelMouseProc(int code, WPARAM wParam, LPARAM lParam)
{
if ( code != HC_ACTION )
return CallNextHookEx(hMouseHook, code, wParam, lParam);
switch (wParam)
{
case WM_LBUTTONDOWN:
{
TRACE("Downn");
// To get window handle from current mouse position
::GetCursorPos(&mouse_pos);
hCurrentWnd = ::WindowFromPoint(mouse_pos);
LButton_Down = true;
Window_Drag = false; // Initialize Window_Drag variable
Mouse_Drag = false;
while (hCurrentWnd != 0)
{
style = ::GetWindowLong(hCurrentWnd, GWL_STYLE);
const int x = style & (WS_POPUP | WS_CHILD);
if ((x == WS_OVERLAPPED) || (x == WS_POPUP)) break;
// we also want to manipulate mdi childs that
// aren't maximized
if ((!(style & WS_MAXIMIZE)) && (::GetWindowLong(hCurrentWnd, GWL_EXSTYLE) & WS_EX_MDICHILD)) break;
hCurrentWnd = ::GetParent(hCurrentWnd);
}
if (IgnoreWindow())
{
return CallNextHookEx(hMouseHook, code, wParam, lParam);
}
// check if the alt key is pressed while a mouse button is pressed
// and switch to the appropriate mode
switch (wParam)
{
case WM_LBUTTONDOWN:
LButton_Down = true;
break;
default:
return CallNextHookEx(hMouseHook, code, wParam, lParam);
}
if (hCurrentWnd == 0)
{
return CallNextHookEx(hMouseHook, code, wParam, lParam);
}
HWND parent = ::GetParent(hCurrentWnd);
// remember the window size and position
::GetWindowRect(hCurrentWnd, &rDown);
if ( ( parent ) && ( ( style & WS_POPUP ) == 0 ) )
{
::ScreenToClient(parent, (POINT*)&rDown.left);
::ScreenToClient(parent, (POINT*)&rDown.right);
}
// we're getting serious - capture the mouse
SetCapture(hCurrentWnd);
return CallNextHookEx(hMouseHook, code, wParam, lParam);
}
case WM_MOUSEMOVE:
{
TRACE("Moven");
if ( !LButton_Down )
{
return CallNextHookEx(hMouseHook, code, wParam, lParam);
}
else {
Mouse_Drag = true;
TRACE("Mouse Drag - Truen");
::GetWindowRect(hCurrentWnd, &rCurWdrag);
if ((rDown.left == rCurWdrag.left) && (rDown.top == rCurWdrag.top))
{
Window_Drag = false;
TRACE("Window Drag - Falsen");
}
else {
Window_Drag = true;
TRACE("Window Drag - Truen");
}
}
return CallNextHookEx( hMouseHook, code, wParam, lParam) ;
}
case WM_LBUTTONUP:
{
TRACE("Upn");
LButton_Down = false;
if ( Window_Drag && Mouse_Drag )
{
Window_Drag = false;
Mouse_Drag = false;
::SetWindowPos(hCurrentWnd, 0, 0, 0, 500, 500, SWP_ASYNCWINDOWPOS);
TRACE("Window Drag - Falsen");
TRACE("Mouse Drag - Falsen");
}
else
{
Window_Drag = false;
Mouse_Drag = false;
TRACE("Window Drag 1 - Falsen");
TRACE("Mouse Drag 1 - Falsen");
}
ReleaseCapture();
return CallNextHookEx(NULL, code, wParam, lParam);
}
default:
{
LButton_Down = false;
Window_Drag = false;
Mouse_Drag = false;
return CallNextHookEx(hMouseHook, code, wParam, lParam);
}
}
}
这是全局鼠标钩的一部分安装的
BOOL CMFCApplication4Dlg::OnInitDialog()
{
CDialogEx::OnInitDialog();
// Set the icon for this dialog. The framework does this automatically
// when the application's main window is not a dialog
SetIcon(m_hIcon, TRUE); // Set big icon
SetIcon(m_hIcon, FALSE); // Set small icon
// TODO: Add extra initialization here
LButton_Down = false;
Mouse_Drag = false;
Window_Drag = false;
hMouseHook = SetWindowsHookEx(WH_MOUSE_LL, (HOOKPROC)LowLevelMouseProc, NULL, (DWORD)NULL);
return TRUE; // return TRUE unless you set the focus to a control
}
我该怎么办?
拖动窗口时,系统将消息发送到窗口。发布左鼠标按钮后,我将WM__EXITSIZEMOVE消息发送到捕获左鼠标UP事件的窗口。完成此MSG的过程后,我使用SetWindowPos方法重新定位窗口,并且效果很好。仅此而已。
相关文章:
- C++:将 UDP 袜子转移到新位置
- lua_newuserdata QMetaObject 上的新放置位置
- 将数据复制到磁盘上新位置的语法
- (虚拟)父级中的新位置
- 在 Omnet++ 中的模拟时间内更改/设置节点的新位置
- 每次我分配新的位置时,都会隐式地称为destuructor
- 放置新位置的错误警告
- 给定一个用三角形镶嵌的补丁,如何修改其新的顶点位置
- 如何正确删除一行控件并在该位置动态创建一个新控件
- 自复制文件到新位置tchar不兼容
- 在不隔离内存的情况下使用新的位置是安全的吗?
- 使用新的位置时Sigbus
- 即使在同一类型上,也可以将击曲线调用新的位置
- 我可以使用新的位置添加到向量
- 将字符数复制到新字符串位置的字符串操作,例如 S[0]
- 使用新的位置来创建静态常量指针,指向静态内存缓冲区
- 如何根据父对象的相对变化计算子对象的新全局位置
- 在容器中使用新放置位置
- 如何在此处使用新展示位置
- 在不同大小的类上放置新的位置