From 4c0f51c47632df626a5523759f791b6f1d77758f Mon Sep 17 00:00:00 2001 From: ispyisail Date: Fri, 2 Oct 2026 06:12:09 +1300 Subject: [PATCH] Arc: show the middle handle only with the size handles, uncovering the one under it The middle handle of a half arc sits exactly on the middle of the top or bottom edge of the ellipse -- a resize handle in Size mode, a skew handle in RotateSkew mode -- and, drawn last, it covered that handle (arummler, discussion #1203). It is now shown in Size mode only, where the resize handle under it is hidden instead: the middle handle already changes that height, with the ends kept in place. RotateSkew mode shows its skew handle again. Co-Authored-By: Claude Opus 5.5 --- sources/qetgraphicsitem/qetshapeitem.cpp | 26 ++++++++++++++++++++++-- sources/qetgraphicsitem/qetshapeitem.h | 2 +- 2 files changed, 25 insertions(+), 3 deletions(-) diff --git a/sources/qetgraphicsitem/qetshapeitem.cpp b/sources/qetgraphicsitem/qetshapeitem.cpp index b2f3a152d..8c1be55e4 100644 --- a/sources/qetgraphicsitem/qetshapeitem.cpp +++ b/sources/qetgraphicsitem/qetshapeitem.cpp @@ -1746,11 +1746,33 @@ void QetShapeItem::rebuildHandles() updateArcBulgeVisibility(); } +/** + @brief QetShapeItem::updateArcBulgeVisibility + The middle handle of a half arc is shown with the Size handles only. + It sits exactly on one of them -- the middle of the top or bottom + edge (left or right for an upright arc) -- and on the top skew handle + in RotateSkew mode, and being drawn last it covered whichever one it + sat on. In Size mode the Resize handle under it is hidden instead: + the middle handle already changes that same height, keeping the ends + in place. +*/ void QetShapeItem::updateArcBulgeVisibility() { const int index = m_handleRoles.indexOf(HandleRole::ArcBulge); - if (index >= 0 && index < m_handler_vector.size()) - m_handler_vector.at(index)->setVisible(isAxisHalfArc()); + if (index < 0 || index >= m_handler_vector.size()) + return; + + const bool shown = isAxisHalfArc() && m_handleMode == HandleMode::Size; + m_handler_vector.at(index)->setVisible(shown); + + const QPointF middle = handlePositionFor(HandleRole::ArcBulge, 0); + for (int i = 0; i < m_handler_vector.size() && i < m_handleRoles.size(); ++i) + { + if (m_handleRoles.at(i) != HandleRole::Resize) + continue; + const QPointF p = handlePositionFor(HandleRole::Resize, m_handleSlot.at(i)); + m_handler_vector.at(i)->setVisible(!shown || QLineF(p, middle).length() > 0.01); + } } /** diff --git a/sources/qetgraphicsitem/qetshapeitem.h b/sources/qetgraphicsitem/qetshapeitem.h index ba4c2ae87..7d5d90c81 100644 --- a/sources/qetgraphicsitem/qetshapeitem.h +++ b/sources/qetgraphicsitem/qetshapeitem.h @@ -131,7 +131,7 @@ class QetShapeItem : public QetGraphicsItem Rotate, SkewEdge, Pivot, // RotateSkew mode CornerRadius, // Rectangle, always shown alongside Size handles ArcEndpoint, // Ellipse, always shown - ArcBulge, // Ellipse, shown only on a half arc (see isAxisHalfArc()) + ArcBulge, // Ellipse, Size mode, shown only on a half arc (see isAxisHalfArc()) PathAnchor, PathControlIn, PathControlOut // Polygon/Path, node-edit mode (see setPathNodes()) };