Controls flicker/disappear in AUI toolbar when resizing sashes on MSW (Issue #26142)

25 views
Skip to first unread message

dsa-t

unread,
Feb 1, 2026, 1:01:45 AMFeb 1
to wx-...@googlegroups.com, Subscribed
dsa-t created an issue (wxWidgets/wxWidgets#26142)

Description

Add to MyFrame::MyFrame in auidemo.cpp:

    wxBitmapComboBox* choice = new wxBitmapComboBox(tb4, ID_SampleItem + 35, wxEmptyString, wxDefaultPosition,
        wxDefaultSize, 0, nullptr,
        wxCB_READONLY);

    choice->Append("Good choice", tb4_bmp1);
    choice->Append("Better choice", tb4_bmp1);
    tb4->AddControl(choice);
    tb4->Realize();

and #include "wx/bmpcbox.h"

See flickering controls in aui toolbars when resizing sashes:

https://github.com/user-attachments/assets/7e5aef25-031e-4f03-9f79-ac232b4cd04e

Flickering is seen on other UI elements too, but less pronounced.

Platform and version information

  • wxWidgets version you use: 3.3 (master)
  • wxWidgets port you use: wxMSW
  • OS and its version: Windows 11


Reply to this email directly, view it on GitHub, or unsubscribe.
You are receiving this because you are subscribed to this thread.Message ID: <wxWidgets/wxWidgets/issues/26142@github.com>

VZ

unread,
Feb 18, 2026, 12:10:21 PM (4 days ago) Feb 18
to wx-...@googlegroups.com, Subscribed
vadz left a comment (wxWidgets/wxWidgets#26142)

I can indeed see this, thanks, will take a look.


Reply to this email directly, view it on GitHub, or unsubscribe.

You are receiving this because you are subscribed to this thread.Message ID: <wxWidgets/wxWidgets/issues/26142/3922041475@github.com>

VZ

unread,
Feb 20, 2026, 11:30:22 AM (2 days ago) Feb 20
to wx-...@googlegroups.com, Subscribed
vadz left a comment (wxWidgets/wxWidgets#26142)

I thought we'd need something like this to fix it:

diff --git a/src/aui/auibar.cpp b/src/aui/auibar.cpp
index bdfabf94f9..c66c2d8810 100644
--- a/src/aui/auibar.cpp
+++ b/src/aui/auibar.cpp
@@ -2541,12 +2541,35 @@ void wxAuiToolBar::UpdateBackgroundBitmap(const wxSize& size)
 
 void wxAuiToolBar::OnPaint(wxPaintEvent& WXUNUSED(evt))
 {
-    wxAutoBufferedPaintDC dc(this);
+    wxPaintDC dc(this);
     wxRect cli_rect(wxPoint(0,0), GetClientSize());
 
 
     bool horizontal = m_orientation == wxHORIZONTAL;
 
+    // Subtract all regions containing controls from the clipping region so
+    // that we don't draw over them to avoid flicker.
+    wxRegion regionWithoutControls;
+    for (const auto& item : m_items)
+    {
+        if (!item.m_sizerItem)
+            continue;
+
+        if (item.m_kind != wxITEM_CONTROL)
+            continue;
+
+        wxRect item_rect = item.m_sizerItem->GetRect();
+        if (regionWithoutControls.IsEmpty())
+            regionWithoutControls = wxRegion(cli_rect);
+
+        regionWithoutControls.Subtract(item_rect);
+    }
+
+    // We leave it empty if there are no controls at all to not bother with
+    // clipping in that case.
+    if ( !regionWithoutControls.IsEmpty() )
+        dc.SetDeviceClippingRegion(regionWithoutControls);
+
     dc.DrawBitmap(m_backgroundBitmap, 0, 0);
 
     int gripperSize = m_art->GetElementSizeForWindow(wxAUI_TBART_GRIPPER_SIZE, this);

but it turns out that it's enough just to remove Refresh() from wxAuiToolBar::OnSize() to fix the flicker. I don't fully understand why, i.e. I understand why this Refresh() is bad/results in flicker, but I don't understand why we don't see flicker due to the use of wxAutoBufferedPaintDC as it paints the entire toolbar before the controls paint over it — but I just don't see it any more after doing just this:

diff --git a/src/aui/auibar.cpp b/src/aui/auibar.cpp
index bdfabf94f9..4f3bdebf16 100644
--- a/src/aui/auibar.cpp
+++ b/src/aui/auibar.cpp
@@ -2407,8 +2407,6 @@ void wxAuiToolBar::OnSize(wxSizeEvent& WXUNUSED(evt))
     // We need to update the bitmap if the size has changed.
     UpdateBackgroundBitmap(wxSize(x, y));
 
-    Refresh(false);
-
     // idle events aren't sent while user is resizing frame (why?),
     // but resizing toolbar here causes havoc,
     // so force idle handler to run after size handling complete

However this results in drawing artefacts due to the old chevron marks not being erased, so finally I've kept Refresh() but only if it's really needed, see the linked PR. It seems to work for me in the sample, but could you please test it in the real application too and see if it creates any new problems? TIA!


Reply to this email directly, view it on GitHub, or unsubscribe.

You are receiving this because you are subscribed to this thread.Message ID: <wxWidgets/wxWidgets/issues/26142/3935889613@github.com>

Reply all
Reply to author
Forward
0 new messages