summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCaolán McNamara <caolanm@redhat.com>2021-09-03 17:27:54 +0100
committerAdolfo Jayme Barrientos <fitojb@ubuntu.com>2021-09-09 11:39:41 +0200
commit71968455be0e696423011775b957d5b738b9f457 (patch)
treee28a73d8e7c483cd836bd467cef9e831f39c55db
parent58d98eda287b68404c98900f65b146f53b016778 (diff)
tdf#142458 Set correct ScrolledWindow BorderWidth in the ctor
and keep it updated when the relevant properties that affect it change. This avoids the problem that the borderwidth can change during "Paint" (which is something we strongly want to avoid). a problem since: commit f39f21d92ec83c3a5062f29dd26214fc83012c06 Date: Thu Nov 19 11:51:13 2020 +0100 tdf#138010 (IV) VclScrolledWindow: Use actual border width and then remove the potential change of BorderWidth during paint Change-Id: I2ec317d86687fdb75e6323905f6d1c3b8fc655e1 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/121557 Tested-by: Jenkins Reviewed-by: Adolfo Jayme Barrientos <fitojb@ubuntu.com>
-rw-r--r--include/vcl/layout.hxx3
-rw-r--r--vcl/source/window/layout.cxx78
2 files changed, 45 insertions, 36 deletions
diff --git a/include/vcl/layout.hxx b/include/vcl/layout.hxx
index ec4722b48849..064904b14812 100644
--- a/include/vcl/layout.hxx
+++ b/include/vcl/layout.hxx
@@ -500,8 +500,7 @@ public:
private:
virtual Size calculateRequisition() const override;
virtual void setAllocation(const Size &rAllocation) override;
- // sets new border size and adapts scrollbar and child widget position/size as needed
- void updateBorderWidth(tools::Long nBorderWidth);
+ int CalcBorderWidth() const;
DECL_LINK(ScrollBarHdl, ScrollBar*, void);
void InitScrollBars(const Size &rRequest);
virtual bool EventNotify(NotifyEvent& rNEvt) override;
diff --git a/vcl/source/window/layout.cxx b/vcl/source/window/layout.cxx
index 3f70e767e344..ae147dd093e5 100644
--- a/vcl/source/window/layout.cxx
+++ b/vcl/source/window/layout.cxx
@@ -1808,7 +1808,6 @@ IMPL_LINK( VclExpander, ClickHdl, CheckBox&, rBtn, void )
VclScrolledWindow::VclScrolledWindow(vcl::Window *pParent)
: VclBin(pParent, WB_HIDE | WB_CLIPCHILDREN | WB_AUTOHSCROLL | WB_AUTOVSCROLL | WB_TABSTOP)
, m_bUserManagedScrolling(false)
- , m_nBorderWidth(1)
, m_eDrawFrameStyle(DrawFrameStyle::NONE)
, m_eDrawFrameFlags(DrawFrameFlags::NONE)
, m_pVScroll(VclPtr<ScrollBar>::Create(this, WB_HIDE | WB_VERT))
@@ -1826,6 +1825,18 @@ VclScrolledWindow::VclScrolledWindow(vcl::Window *pParent)
Link<ScrollBar*,void> aLink( LINK( this, VclScrolledWindow, ScrollBarHdl ) );
m_pVScroll->SetScrollHdl(aLink);
m_pHScroll->SetScrollHdl(aLink);
+
+ m_nBorderWidth = CalcBorderWidth();
+}
+
+int VclScrolledWindow::CalcBorderWidth() const
+{
+ const tools::Rectangle aRect(tools::Rectangle(Point(0, 0), Size(100, 100)));
+ DecorationView aDecoView(const_cast<OutputDevice*>(GetOutDev()));
+ // don't actually draw anything, just measure what size it would be and the diff is the desired border size to reserve
+ const tools::Rectangle aContentRect = aDecoView.DrawFrame(aRect, m_eDrawFrameStyle, m_eDrawFrameFlags | DrawFrameFlags::NoDraw);
+ const auto nBorderWidth = (aRect.GetWidth() - aContentRect.GetWidth()) / 2;
+ return std::max<int>(nBorderWidth, 1);
}
void VclScrolledWindow::dispose()
@@ -2029,24 +2040,35 @@ Size VclScrolledWindow::getVisibleChildSize() const
bool VclScrolledWindow::set_property(const OString &rKey, const OUString &rValue)
{
- if (rKey == "shadow-type")
- {
- // despite the style names, this looks like the best mapping
- if (rValue == "in")
- m_eDrawFrameStyle = DrawFrameStyle::Out;
- else if (rValue == "out")
- m_eDrawFrameStyle = DrawFrameStyle::In;
- else if (rValue == "etched-in")
- m_eDrawFrameStyle = DrawFrameStyle::DoubleOut;
- else if (rValue == "etched-out")
- m_eDrawFrameStyle = DrawFrameStyle::DoubleIn;
- else if (rValue == "none")
- m_eDrawFrameStyle = DrawFrameStyle::NONE;
- return true;
- }
- else if (rKey == "name")
+ if (rKey == "shadow-type" || rKey == "name")
{
- m_eDrawFrameFlags = rValue == "monoborder" ? DrawFrameFlags::Mono : DrawFrameFlags::NONE;
+ if (rKey == "shadow-type")
+ {
+ // despite the style names, this looks like the best mapping
+ if (rValue == "in")
+ m_eDrawFrameStyle = DrawFrameStyle::Out;
+ else if (rValue == "out")
+ m_eDrawFrameStyle = DrawFrameStyle::In;
+ else if (rValue == "etched-in")
+ m_eDrawFrameStyle = DrawFrameStyle::DoubleOut;
+ else if (rValue == "etched-out")
+ m_eDrawFrameStyle = DrawFrameStyle::DoubleIn;
+ else if (rValue == "none")
+ m_eDrawFrameStyle = DrawFrameStyle::NONE;
+ }
+ else if (rKey == "name")
+ {
+ m_eDrawFrameFlags = rValue == "monoborder" ? DrawFrameFlags::Mono : DrawFrameFlags::NONE;
+ }
+
+ auto nBorderWidth = CalcBorderWidth();
+ if (m_nBorderWidth != nBorderWidth)
+ {
+ m_nBorderWidth = nBorderWidth;
+ queue_resize();
+ }
+
+ return true;
}
bool bRet = VclBin::set_property(rKey, rValue);
@@ -2077,27 +2099,15 @@ bool VclScrolledWindow::EventNotify(NotifyEvent& rNEvt)
return bDone || VclBin::EventNotify( rNEvt );
}
-void VclScrolledWindow::updateBorderWidth(tools::Long nBorderWidth)
-{
- if (m_nBorderWidth == nBorderWidth || nBorderWidth < 1)
- return;
-
- m_nBorderWidth = nBorderWidth;
- // update scrollbars and child window
- doSetAllocation(GetSizePixel(), false);
-};
-
void VclScrolledWindow::Paint(vcl::RenderContext& rRenderContext, const tools::Rectangle& rRect)
{
+ VclBin::Paint(rRenderContext, rRect);
const tools::Rectangle aRect(tools::Rectangle(Point(0,0), GetSizePixel()));
DecorationView aDecoView(&rRenderContext);
const tools::Rectangle aContentRect = aDecoView.DrawFrame(aRect, m_eDrawFrameStyle, m_eDrawFrameFlags);
-
- // take potentially changed frame size into account before rendering content
- const tools::Long nFrameWidth = (aRect.GetWidth() - aContentRect.GetWidth()) / 2;
- updateBorderWidth(nFrameWidth);
-
- VclBin::Paint(rRenderContext, rRect);
+ const auto nBorderWidth = (aRect.GetWidth() - aContentRect.GetWidth()) / 2;
+ SAL_WARN_IF(nBorderWidth > m_nBorderWidth, "vcl.layout", "desired border at paint " <<
+ nBorderWidth << " is larger than expected " << m_nBorderWidth);
}
void VclViewport::setAllocation(const Size &rAllocation)