Resize text fields in the element editor by dragging a corner

In the element editor, a dynamic text field that is the only selected
item gets the corner handles of TextResizeHandles: dragging one sets
the width the field wraps to, keeping the opposite corner in place;
double-clicking a handle goes back to the automatic width. One undo
step per drag, on the editor's undo stack.

ElementScene keeps the handles of the same text when the undo stack
changes: pushing the resize itself calls managePrimitivesGroups()
again, and deleting the handles there would delete them while they are
still emitting.

No file format change (text_width on <dynamic_text> already exists).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
Beat Hangartner
2026-10-05 17:59:28 +02:00
parent 0708338bce
commit 3c67147824
2 changed files with 47 additions and 0 deletions
+44
View File
@@ -23,6 +23,7 @@
#include "../NameList/ui/namelistwidget.h"
#include "../QPropertyUndoCommand/qpropertyundocommand.h"
#include "../QetGraphicsItemModeler/qetgraphicshandleritem.h"
#include "../QetGraphicsItemModeler/textresizehandles.h"
#include "editorcommands.h"
#include "elementcontent.h"
#include "elementprimitivedecorator.h"
@@ -1498,9 +1499,52 @@ void ElementScene::managePrimitivesGroups()
m_decorator -> setPos(0, 0);
m_decorator -> setItems(selected_items);
}
manageTextResizeHandles(selected_items);
m_decorator_lock -> unlock();
}
/**
@brief ElementScene::manageTextResizeHandles
Show the corner handles that change the width of a text field when it
is the only selected item, and it is not being typed in.
Called again when the undo stack changes, including from the push of a
resize itself: the handles of the same text are then kept, not deleted
while they are still emitting.
@param selected_items
*/
void ElementScene::manageTextResizeHandles(const QList<QGraphicsItem *> &selected_items)
{
QGraphicsTextItem *text = nullptr;
if (selected_items.size() == 1 &&
selected_items.first()->type() == PartDynamicTextField::Type)
{
text = static_cast<PartDynamicTextField *>(selected_items.first());
}
if (text && (text->textInteractionFlags() & Qt::TextEditable))
text = nullptr;
if (m_text_resize_handles && m_text_resize_handles->parentItem() == text) {
m_text_resize_handles->updateHandlesPos();
return;
}
if (m_text_resize_handles) {
m_text_resize_handles->hide();
m_text_resize_handles->deleteLater();
m_text_resize_handles.clear();
}
if (text)
{
m_text_resize_handles = new TextResizeHandles(text);
connect(m_text_resize_handles, &TextResizeHandles::resizeFinished, this,
[this, text](qreal old_width, qreal new_width, QPointF old_pos, QPointF new_pos)
{
m_undo_stack.push(new TextResizeCommand(text, old_width, new_width, old_pos, new_pos));
});
}
}
/**
@brief ElementScene::stackAction
Push the provided \a command on the undo stack.
+3
View File
@@ -33,6 +33,7 @@ class QETElementEditor;
class ESEventInterface;
class QKeyEvent;
class CustomElementGraphicPart;
class TextResizeHandles;
/**
@brief The ElementScene class
This class is the canvas allowing the visual edition of an electrical element.
@@ -90,6 +91,7 @@ class ElementScene : public QGraphicsScene
m_y_grid;
QPointer<CustomElementGraphicPart> m_single_selected_item;
QPointer<TextResizeHandles> m_text_resize_handles;
bool m_hotspot_visible = true;
bool m_background_frame_visible = false;
@@ -180,6 +182,7 @@ class ElementScene : public QGraphicsScene
void slot_editAuthorInformations();
void slot_editProperties();
void managePrimitivesGroups();
void manageTextResizeHandles(const QList<QGraphicsItem *> &selected_items);
void stackAction(ElementEditionCommand *);
signals: