Fix wxMSW toolbar drop down arrow appearance in dark mode

We have no choice but to draw it ourselves, using the appropriate
colour, as by default it is drawn in black which has almost no contrast
with the background when using dark mode.

Closes #24901.
This commit is contained in:
Stefan Ziegler
2024-10-23 19:31:07 +02:00
committed by Vadim Zeitlin
parent cdf8d0a0fe
commit c301af42f9
+59 -2
View File
@@ -1687,14 +1687,22 @@ bool wxToolBar::MSWOnNotify(int WXUNUSED(idCtrl),
return true;
case CDDS_ITEMPREPAINT:
{
// If we get here, we must have returned CDRF_NOTIFYITEMDRAW
// from above, so we're using the dark mode and need to
// customize the colours for it.
nmtbcd->clrText =
nmtbcd->clrTextHighlight = wxColourToRGB(GetForegroundColour());
nmtbcd->clrHighlightHotTrack = wxSysColourToRGB(wxSYS_COLOUR_HOTLIGHT);
*result = CDRF_DODEFAULT | TBCDRF_USECDCOLORS | TBCDRF_HILITEHOTTRACK;
const wxColour colBg = m_hasBgCol
? GetBackgroundColour()
: wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE);
nmtbcd->clrHighlightHotTrack = wxColourToRGB(colBg.ChangeLightness(115));
*result = CDRF_DODEFAULT |
CDRF_NOTIFYPOSTPAINT |
TBCDRF_USECDCOLORS |
TBCDRF_HILITEHOTTRACK;
// Draw custom checked button background when it is not hot:
// by default it is drawn in a light colour not appropriate for
@@ -1712,6 +1720,55 @@ bool wxToolBar::MSWOnNotify(int WXUNUSED(idCtrl),
}
return true;
}
case CDDS_ITEMPOSTPAINT:
{
// custom draw the drop-down arrow here, as it is always black
WinStruct<TBBUTTONINFO> bi;
bi.dwMask = TBIF_STYLE | TBIF_COMMAND;
const auto itemIndex =
::SendMessage(GetHwnd(), TB_GETBUTTONINFO,
(WPARAM)nmtbcd->nmcd.dwItemSpec, (LPARAM)&bi);
if ( itemIndex >= 0 && bi.fsStyle & TBSTYLE_DROPDOWN )
{
RECT ddrc = { 0 };
::SendMessage(GetHwnd(), TB_GETITEMDROPDOWNRECT,
(WPARAM)itemIndex, (LPARAM)&ddrc);
wxColour colBg = m_hasBgCol
? GetBackgroundColour()
: wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE);
if ( nmtbcd->nmcd.uItemState & CDIS_HOT )
{
// Make this slightly different from the colour used
// for the button itself above.
colBg = colBg.ChangeLightness(120);
}
AutoHBRUSH bgBrush(wxColourToRGB(colBg));
::FillRect(nmtbcd->nmcd.hdc, &ddrc, bgBrush);
int arrowCenterX = (ddrc.left + ddrc.right) / 2;
int arrowCenterY = (ddrc.top + ddrc.bottom) / 2;
POINT ptsArrow[3] =
{
{ arrowCenterX - FromDIP(3), arrowCenterY - FromDIP(2) },
{ arrowCenterX + FromDIP(3), arrowCenterY - FromDIP(2) },
{ arrowCenterX, arrowCenterY + FromDIP(2) }
};
AutoHBRUSH fgBrush(wxColourToRGB(GetForegroundColour()));
AutoHPEN hPen(wxColourToRGB(GetForegroundColour()));
::SelectObject(nmtbcd->nmcd.hdc, hPen);
::SelectObject(nmtbcd->nmcd.hdc, fgBrush);
::Polygon(nmtbcd->nmcd.hdc, ptsArrow, 3);
}
*result = CDRF_DODEFAULT;
return true;
}
}
return false;