您好,登錄后才能下訂單哦!
本文實例為大家分享了wxWidgets實現無標題欄窗口拖動的具體代碼,供大家參考,具體內容如下
最近需要做一個自定義的標題欄,而其中最重要的就是要實現窗口的拖動。默認情況下有標題欄,都可以通過拖動系統默認的標題欄,但是自定義的標題欄需要自己實現拖動。
實現無標題窗口的拖動,在MFC中可以在鼠標在窗口中拖動時,發送虛假的消息給窗口來進行實現(注:MFC可以發送鼠標在標題欄拖動的消息)。但是在wxWidgets中,暫時沒有看到類似的消息。因工作需要,才學習wxWidgets不久。如果有知道相關消息的朋友,請發消息告訴。而自己實現拖動,大致可以分為三個步驟。
1、在鼠標左鍵按下時,記錄下鼠標位置,使用CaptureMouse來進行鼠標捕獲 。注意,這里如果不捕獲鼠標,那么也能實現拖動窗口,但是會出現一個小問題,就是當鼠標在窗口邊緣快速的拖出窗口的時候,窗口不能進行移動。因為系統對鼠標的移動事件的發送是有事件間隔的,窗口收到該消息時鼠標已經離開了窗口,所以不能正確拖動。一定要記得設置鼠標捕獲。
2、當鼠標拖動的時候(在鼠標事件中判斷鼠標左鍵按下且在拖拽),計算鼠標新的位置相對之前的位移向量,并移動窗口到相應的位置。
3、處理鼠標左鍵抬起事件,在鼠標抬起事件中使用ReleaseMouse來釋放之前捕獲的鼠標。
4、處理EVT_MOUSE_CAPTURE_LOST(func)事件,在其中釋放鼠標捕獲。官方文檔有說明,對鼠標進行捕獲必須處理該事件,并在其中釋放鼠標捕獲。因為彈出對話框等情況會導致鼠標是按下的,但是父窗口卻失去了鼠標焦點的狀況,所以必須處理該事件釋放鼠標。
下面給出我自己實現的一個可以通過鼠標拖拽實現移動的無標題欄窗口的代碼,可以對照上邊的介紹看一下具體的實現。這個類實現的是拖動自己,當然可以利用在計算坐標之后獲取父窗口來進行移動,那樣就可以實現鼠標在子窗口上拖動來實現整個窗口的移動。也就是自定義的標題欄應該具有的基本功能。
頭文件:MyTitleWnd.h
#pragma once #include <wx/wx.h> class MyTitleWnd:public wxFrame { public: MyTitleWnd(wxWindow *parent,wxWindowID id=wxID_ANY); virtual ~MyTitleWnd(); void OnMouseMove(wxMouseEvent& event); void OnMouseLeave(wxMouseEvent& event); void OnMouseLDown(wxMouseEvent& event); void OnMouseLUp(wxMouseEvent& event); void OnMouseCaptureLost(wxMouseCaptureLostEvent& event); private: wxPoint mLastPt; wxString mText; DECLARE_EVENT_TABLE() };
源文件:MyTitleWnd.cpp
#include "MyTitleWnd.h" BEGIN_EVENT_TABLE(MyTitleWnd, wxFrame) EVT_MOUSE_CAPTURE_LOST(MyTitleWnd::OnMouseCaptureLost) //EVT_LEFT_DOWN(MyTitleWnd::OnMouseLDown) EVT_LEFT_UP(MyTitleWnd::OnMouseLUp) EVT_MOUSE_EVENTS(MyTitleWnd::OnMouseMove) EVT_LEAVE_WINDOW(MyTitleWnd::OnMouseLeave) END_EVENT_TABLE() MyTitleWnd::MyTitleWnd(wxWindow *parent, wxWindowID id/*=wxID_ANY*/) :wxFrame(parent, id,"", wxDefaultPosition, wxDefaultSize, wxBORDER_NONE) { } MyTitleWnd::~MyTitleWnd() { } void MyTitleWnd::OnMouseMove(wxMouseEvent &event) { if(event.LeftIsDown()&&event.Dragging()) { wxPoint pt = event.GetPosition(); wxPoint wndLeftTopPt = GetPosition(); int distanceX = pt.x - mLastPt.x; int distanceY = pt.y - mLastPt.y; wxPoint desPt; desPt.x = distanceX + wndLeftTopPt.x; desPt.y = distanceY + wndLeftTopPt.y; this->Move(desPt); } if (event.LeftDown()) { this->CaptureMouse(); mLastPt = event.GetPosition(); } } void MyTitleWnd::OnMouseLeave(wxMouseEvent& event) { if (event.LeftIsDown() && event.Dragging()) { wxPoint pt = event.GetPosition(); wxPoint wndLeftTopPt = GetPosition(); int distanceX = pt.x - mLastPt.x; int distanceY = pt.y - mLastPt.y; wxPoint desPt; desPt.x = distanceX + wndLeftTopPt.x; desPt.y = distanceY + wndLeftTopPt.y; this->Move(desPt); } } void MyTitleWnd::OnMouseLDown(wxMouseEvent& event) { this->CaptureMouse(); } void MyTitleWnd::OnMouseLUp(wxMouseEvent& event) { if (HasCapture()) ReleaseMouse(); } void MyTitleWnd::OnMouseCaptureLost(wxMouseCaptureLostEvent& event) { if (HasCapture()) ReleaseMouse(); }
好了,最后貼出效果圖。
以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持億速云。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。