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.
—
Reply to this email directly, view it on GitHub, or unsubscribe.
You are receiving this because you are subscribed to this thread.![]()
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.![]()
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.![]()