mirror of
https://github.com/wxWidgets/wxWidgets.git
synced 2026-09-23 14:45:04 +08:00
Fix bug with broken AUI sash drag in some layout
Don't end the AUI resize action when the new size can't be computed, as can happen for a perfectly ordinary layout: it's enough to have a resizable pane followed in its dock by a fixed one. This is the case for the panes in the bottom row of the "aui" sample itself, after all panes are shown using the corresponding "Perspectives" menu item. This fixes a serious user-visible problem as mouse renamed captured forever and the application was left with the resize cursor and with keyboard input going to the capturing window. Add a unit test checking for this problem: without the fix in this commit, "stillCaptured" remained true in it. Closes #27025. Co-authored-by: Vadim Zeitlin <vadim@wxwidgets.org>
This commit is contained in:
committed by
Vadim Zeitlin
co-authored by
Vadim Zeitlin
parent
10c4a5611a
commit
9992152ce3
@@ -5239,10 +5239,7 @@ bool wxAuiManager::DoEndResizeAction(wxMouseEvent& event)
|
||||
|
||||
// prevent division by zero
|
||||
if (dock_pixels == 0 || total_proportion == 0 || borrow_pane == -1)
|
||||
{
|
||||
m_action = actionNone;
|
||||
return false;
|
||||
}
|
||||
|
||||
// calculate the new proportion of the pane
|
||||
int new_proportion = (new_pixsize*total_proportion)/dock_pixels;
|
||||
|
||||
@@ -83,6 +83,12 @@ public:
|
||||
}
|
||||
|
||||
void ClickWithoutMoving(wxAuiDockUIPart* part)
|
||||
{
|
||||
DragBy(part, wxPoint());
|
||||
}
|
||||
|
||||
// Simulate a complete drag of the given sash by the given offset.
|
||||
void DragBy(wxAuiDockUIPart* part, const wxPoint& offset)
|
||||
{
|
||||
const wxPoint pos = part->rect.GetPosition() +
|
||||
wxPoint(part->rect.GetWidth()/2, part->rect.GetHeight()/2);
|
||||
@@ -93,13 +99,13 @@ public:
|
||||
OnLeftDown(down);
|
||||
|
||||
wxMouseEvent motion(wxEVT_MOTION);
|
||||
motion.m_x = pos.x;
|
||||
motion.m_y = pos.y;
|
||||
motion.m_x = pos.x + offset.x;
|
||||
motion.m_y = pos.y + offset.y;
|
||||
OnMotion(motion);
|
||||
|
||||
wxMouseEvent up(wxEVT_LEFT_UP);
|
||||
up.m_x = pos.x;
|
||||
up.m_y = pos.y;
|
||||
up.m_x = pos.x + offset.x;
|
||||
up.m_y = pos.y + offset.y;
|
||||
OnLeftUp(up);
|
||||
}
|
||||
};
|
||||
@@ -201,6 +207,39 @@ TEST_CASE_METHOD(AuiManagerTestCase, "wxAuiManager::SizerClick", "[aui]")
|
||||
CHECK( manager.GetPane(second).dock_proportion == secondProportion );
|
||||
}
|
||||
|
||||
TEST_CASE_METHOD(AuiManagerTestCase, "wxAuiManager::SizerDragReleasesMouse", "[aui]")
|
||||
{
|
||||
// Use a dock in which the resizable pane is followed by a fixed one: there
|
||||
// is then no pane after it to take the space from and DoEndResizeAction()
|
||||
// gives up -- but this must still not leave the mouse captured once the
|
||||
// drag is over.
|
||||
wxWindow* const first = new wxPanel(frame.get());
|
||||
wxWindow* const second = new wxPanel(frame.get());
|
||||
wxWindow* const center = new wxPanel(frame.get());
|
||||
|
||||
REQUIRE( manager.AddPane(first, wxAuiPaneInfo().Top().
|
||||
MinSize(200, 100).CaptionVisible(false).PaneBorder(false)) );
|
||||
REQUIRE( manager.AddPane(second, wxAuiPaneInfo().Top().Fixed().
|
||||
MinSize(200, 100).CaptionVisible(false).PaneBorder(false)) );
|
||||
REQUIRE( manager.AddPane(center, wxAuiPaneInfo().CenterPane()) );
|
||||
|
||||
manager.Update();
|
||||
|
||||
wxAuiDockUIPart* const sizer = manager.FindPaneSizer();
|
||||
REQUIRE( sizer );
|
||||
|
||||
manager.DragBy(sizer, wxPoint(20, 0));
|
||||
|
||||
const bool stillCaptured = wxWindow::GetCapture() == frame.get();
|
||||
|
||||
// Don't let the rest of the tests run with the mouse captured even if the
|
||||
// check below fails.
|
||||
if ( stillCaptured )
|
||||
frame->ReleaseMouse();
|
||||
|
||||
CHECK( !stillCaptured );
|
||||
}
|
||||
|
||||
TEST_CASE_METHOD(AuiNotebookTestCase, "wxAuiNotebook::DoGetBestSize", "[aui]")
|
||||
{
|
||||
wxPanel *p = new wxPanel(nb.get());
|
||||
|
||||
Reference in New Issue
Block a user