Make wxToolBar::SetToolBitmapSize() take size in logical pixels

Previously it interpreted its argument as being in DIPs, which was
perhaps more convenient, but inconsistent with most of the other
functions and broke the general rule that FromDIP() should be used with
all hard-coded sizes.

Update the sample to use FromDIP() when calling it now, improve the
documentation and fix a bug in AdjustToolBitmapSize() which resulted in
not increasing the bitmap size when moving toolbar sample using "large"
toolbar size from a standard DPI display to a high DPI one: the old code
considered that the new size was the same as the old one and returned
before comparing it with m_requestedBitmapSize, which resulted in the
bitmaps not changing size at all instead of doubling their size as they
were expected to.
This commit is contained in:
Vadim Zeitlin
2022-04-19 23:36:02 +01:00
parent a0abd711f7
commit eb6506e677
4 changed files with 36 additions and 27 deletions

View File

@@ -465,8 +465,8 @@ public:
int GetMaxRows() const { return m_maxRows; } int GetMaxRows() const { return m_maxRows; }
int GetMaxCols() const { return m_maxCols; } int GetMaxCols() const { return m_maxCols; }
// get/set the size of the bitmaps used by the toolbar: should be called // get/set the size of the bitmaps used by the toolbar, in logical pixels:
// before adding any tools to the toolbar // should be called before realizing the toolbar if it's called at all
virtual void SetToolBitmapSize(const wxSize& size); virtual void SetToolBitmapSize(const wxSize& size);
virtual wxSize GetToolBitmapSize() const; virtual wxSize GetToolBitmapSize() const;
@@ -704,13 +704,14 @@ protected:
int m_toolPacking, int m_toolPacking,
m_toolSeparation; m_toolSeparation;
// the currently used size of the toolbar bitmaps: the name is unfortunate // the currently used size of the toolbar bitmaps in logical pixels: the
// but keep it for compatibility // name is unfortunate but keep it for compatibility
wxCoord m_defaultWidth, m_defaultHeight; wxCoord m_defaultWidth, m_defaultHeight;
private: private:
// the size of the bitmaps requested by the application by calling // the size of the bitmaps requested by the application by calling
// SetToolBitmapSize() // SetToolBitmapSize() expressed in DIPs because we want to keep using the
// same value even if the DPI changes
wxSize m_requestedBitmapSize; wxSize m_requestedBitmapSize;
wxDECLARE_EVENT_TABLE(); wxDECLARE_EVENT_TABLE();

View File

@@ -878,19 +878,24 @@ public:
//@} //@}
/** /**
Sets the default size of each tool bitmap. The default bitmap size is 16 Sets the default size of each tool bitmap.
by 15 pixels.
It is usually unnecessary to call this function, as the tools will It is usually unnecessary to call this function, as the tools will
always be made big enough to fit the size of the bitmaps used in them. always be made big enough to fit the size of the bitmaps used in them.
If you do call it, note that @a size does @e not need to be multiplied If you do call it, it must be done before toolbar is Realize()'d.
by the DPI-dependent factor even under MSW, where it would normally be
necessary, as the toolbar adjusts this size to the current DPI Example of using this function to force the bitmaps to be at least
automatically. 32 pixels wide and tall:
@code
toolbar->SetToolBitmapSize(FromDIP(wxSize(32, 32)));
toolbar->AddTool(wxID_NEW, "New", wxBitmapBundle::FromXXX(...));
...
toolbar->Realize();
@endcode
@param size @param size
The size of the bitmaps in the toolbar. The size of the bitmaps in the toolbar in logical pixels.
@see GetToolBitmapSize(), GetToolSize() @see GetToolBitmapSize(), GetToolSize()
*/ */

View File

@@ -438,10 +438,12 @@ void MyFrame::PopulateToolbar(wxToolBarBase* toolBar)
toolBarBitmaps[Tool_about] = wxBitmapBundle::FromSVG(svg_data, sizeBitmap); toolBarBitmaps[Tool_about] = wxBitmapBundle::FromSVG(svg_data, sizeBitmap);
#endif // wxHAS_SVG #endif // wxHAS_SVG
// Note that there is no need for FromDIP() here, wxMSW will adjust the // We don't have to call this function at all when using the default bitmap
// size on its own and under the other platforms there is no need for // size (i.e. when m_smallToolbar == true), but it's harmless to do it.
// scaling the coordinates anyhow. //
toolBar->SetToolBitmapSize(sizeBitmap); // Note that sizeBitmap is in DIPs, so we need to use FromDIP() to scale it
// up for the current DPI, if necessary.
toolBar->SetToolBitmapSize(FromDIP(sizeBitmap));
toolBar->AddTool(wxID_NEW, "New", toolBar->AddTool(wxID_NEW, "New",
toolBarBitmaps[Tool_new], wxNullBitmap, wxITEM_DROPDOWN, toolBarBitmaps[Tool_new], wxNullBitmap, wxITEM_DROPDOWN,

View File

@@ -440,7 +440,9 @@ void wxToolBarBase::DoSetToolBitmapSize(const wxSize& size)
void wxToolBarBase::SetToolBitmapSize(const wxSize& size) void wxToolBarBase::SetToolBitmapSize(const wxSize& size)
{ {
m_requestedBitmapSize = size; // We store this value in DIPs to avoid having to update it when the DPI
// changes.
m_requestedBitmapSize = ToDIP(size);
DoSetToolBitmapSize(size); DoSetToolBitmapSize(size);
} }
@@ -479,28 +481,27 @@ void wxToolBarBase::AdjustToolBitmapSize()
( (
this, this,
bundles, bundles,
sizeOrig ToDIP(sizeOrig)
); );
// Don't do anything if it doesn't change, our current size is supposed // GetConsensusSizeFor() returns physical size, but we want to operate
// to satisfy any constraints we might have anyhow. // with logical pixels as everything else is expressed in them.
if ( sizePreferred == sizeOrig )
return;
// This size is supposed to be in logical units for the platforms where
// they differ from physical ones, so convert it.
// //
// Note that this could introduce rounding problems but, in fact, // Note that this could introduce rounding problems but, in fact,
// neither wxGTK nor wxOSX (that are the only ports where contents // neither wxGTK nor wxOSX (that are the only ports where contents
// scale factor may be different from 1) use this size at all // scale factor may be different from 1) use this size at all
// currently, so it shouldn't matter. But if/when they are modified to // currently, so it shouldn't matter. But if/when they are modified to
// use the size computed here, this would need to be revisited. // use the size computed here, this would need to be revisited.
sizePreferred /= GetContentScaleFactor(); sizePreferred = FromPhys(sizePreferred);
// Don't decrease the bitmap below the size requested by the application // Don't decrease the bitmap below the size requested by the application
// as using larger bitmaps shouldn't shrink them to the small default // as using larger bitmaps shouldn't shrink them to the small default
// size. // size.
sizePreferred.IncTo(m_requestedBitmapSize); sizePreferred.IncTo(FromDIP(m_requestedBitmapSize));
// No need to change the bitmaps size if it doesn't really change.
if ( sizePreferred == sizeOrig )
return;
// Call DoSetToolBitmapSize() and not SetToolBitmapSize() to avoid // Call DoSetToolBitmapSize() and not SetToolBitmapSize() to avoid
// changing the requested bitmap size: if we set our own adjusted size // changing the requested bitmap size: if we set our own adjusted size