From 2d2d3f3e6d1637e60e5ccce9084c7a2ea0b92b66 Mon Sep 17 00:00:00 2001 From: rooosyf Date: Thu, 3 Nov 2022 18:47:42 +0100 Subject: [PATCH 1/3] core: items: wrapLabel function added --- eddy/core/items/common.py | 20 ++++++++++++++------ eddy/core/items/nodes/common/label.py | 23 ++++++++++++++++++++++- 2 files changed, 36 insertions(+), 7 deletions(-) diff --git a/eddy/core/items/common.py b/eddy/core/items/common.py index 50f41b00..724962e9 100644 --- a/eddy/core/items/common.py +++ b/eddy/core/items/common.py @@ -296,6 +296,8 @@ def __init__(self, template='', movable=True, editable=True, parent=None): self.setFont(Font(weight=Font.Light)) self.setText(self.template) self.setTextInteractionFlags(QtCore.Qt.NoTextInteraction) + self.setToolTip(template) + self.wrapLabel() self.customFont = False @@ -306,7 +308,7 @@ def setCustomFont(self, font): if not font==self.font(): npos = self.pos() self.setFont(font) - self.setAlignment(self.alignment()) + self.wrapLabel() self.setPos(npos) self.customFont = True @@ -327,7 +329,7 @@ def sceneEvent(self, event: QtCore.QEvent) -> bool: # UPDATE THE DOCUMENT FONT AND ADJUST ITEM SIZE AND POSITION npos = self.pos() self.setFont(nfont) - self.setAlignment(self.alignment()) + self.wrapLabel() self.setPos(npos) # CASCADE THE EVENT TO EACH CHILD ITEM for item in self.childItems(): @@ -380,12 +382,12 @@ def focusOutEvent(self, focusEvent): self.focusInData = None self.setSelectedText(False) - self.setAlignment(self.alignment()) + self.wrapLabel() self.setTextInteractionFlags(QtCore.Qt.NoTextInteraction) self.diagram.setMode(DiagramMode.Idle) self.diagram.sgnUpdated.emit() - self.setAlignment(self.alignment()) + self.wrapLabel() self.setTextInteractionFlags(QtCore.Qt.NoTextInteraction) super().focusOutEvent(focusEvent) @@ -525,8 +527,6 @@ def setAlignment(self, alignment): :type alignment: int """ self._alignment = alignment - self.setTextWidth(-1) - self.setTextWidth(self.boundingRect().width()) format_ = QtGui.QTextBlockFormat() format_.setAlignment(alignment) cursor = self.textCursor() @@ -602,6 +602,14 @@ def width(self): """ return self.boundingRect().width() + def wrapLabel(self): + """ + Wrap label into node. + """ + self.setTextWidth(-1) + self.setTextWidth(self.boundingRect().width()) + self.setAlignment(self.alignment()) + def __repr__(self): """ Returns repr(self). diff --git a/eddy/core/items/nodes/common/label.py b/eddy/core/items/nodes/common/label.py index 8869dd62..996e14d3 100644 --- a/eddy/core/items/nodes/common/label.py +++ b/eddy/core/items/nodes/common/label.py @@ -33,9 +33,13 @@ ########################################################################## -from PyQt5 import QtCore +from PyQt5 import ( + QtCore, + QtGui, +) from eddy.core.commands.labels import CommandLabelChange +from eddy.core.datatypes.graphol import Item from eddy.core.datatypes.misc import DiagramMode from eddy.core.functions.misc import isEmpty from eddy.core.items.common import AbstractLabel @@ -100,6 +104,23 @@ def updatePos(self, moved=False): if not moved: self.setPos(self.defaultPos()) + def wrapLabel(self): + """ + Wrap label into node. + """ + super().wrapLabel() + if self.parentItem() and self.parentItem().type() in [Item.ConceptNode, + Item.IndividualNode, + Item.ValueDomainNode, + Item.LiteralNode, + Item.FacetNode]: + self.setTextWidth(max(60, self.parentItem().boundingRect().width())) + fm = QtGui.QFontMetrics(self.font()) + lines = max(40, self.parentItem().height()) // fm.height() - 1 + maxLen = int(self.textWidth() * lines) + elidedText = fm.elidedText(self.template, QtCore.Qt.ElideRight, maxLen) + self.setText(elidedText) + self.setAlignment(self.alignment()) class PredicateLabel(NodeLabel): """ From fa6beb3acdd57128390a0fc6ef7757b27744a2df Mon Sep 17 00:00:00 2001 From: rooosyf Date: Thu, 3 Nov 2022 18:48:54 +0100 Subject: [PATCH 2/3] core: items: nodes: wrapLabel on node resize --- eddy/core/items/nodes/concept.py | 1 + eddy/core/items/nodes/individual.py | 1 + eddy/core/items/nodes/literal.py | 1 + eddy/core/items/nodes/role.py | 1 + 4 files changed, 4 insertions(+) diff --git a/eddy/core/items/nodes/concept.py b/eddy/core/items/nodes/concept.py index ade383f0..c78b3b38 100644 --- a/eddy/core/items/nodes/concept.py +++ b/eddy/core/items/nodes/concept.py @@ -381,6 +381,7 @@ def resize(self, mousePos): self.polygon.setGeometry(polygon) self.updateNode(selected=True, handle=self.mp_Handle, anchors=(self.mp_Data, D)) + self.label.wrapLabel() self.updateTextPos(moved=moved) def setIdentity(self, identity): diff --git a/eddy/core/items/nodes/individual.py b/eddy/core/items/nodes/individual.py index 853af477..c33935ae 100644 --- a/eddy/core/items/nodes/individual.py +++ b/eddy/core/items/nodes/individual.py @@ -610,6 +610,7 @@ def resize(self, mousePos): self.polygon.setGeometry(polygon) self.updateNode(selected=True, handle=self.mp_Handle, anchors=(self.mp_Data, D)) + self.label.wrapLabel() self.updateTextPos(moved=moved) def setIdentity(self, identity): diff --git a/eddy/core/items/nodes/literal.py b/eddy/core/items/nodes/literal.py index bfd4e85a..27cef386 100644 --- a/eddy/core/items/nodes/literal.py +++ b/eddy/core/items/nodes/literal.py @@ -691,6 +691,7 @@ def resize(self, mousePos): self.polygon.setGeometry(polygon) self.updateNode(selected=True, handle=self.mp_Handle, anchors=(self.mp_Data, D)) + self.label.wrapLabel() self.updateTextPos(moved=moved) def setIdentity(self, identity): diff --git a/eddy/core/items/nodes/role.py b/eddy/core/items/nodes/role.py index 90d7140e..d2999c62 100644 --- a/eddy/core/items/nodes/role.py +++ b/eddy/core/items/nodes/role.py @@ -571,6 +571,7 @@ def resize(self, mousePos): self.polygon.setGeometry(polygon) self.updateNode(selected=True, handle=self.mp_Handle, anchors=(self.mp_Data, D)) + self.label.wrapLabel() self.updateTextPos(moved=moved) def setAsymmetric(self, asymmetric): From d6fb42e1f83e5078b49ad41c5adaeeac1e7c37db Mon Sep 17 00:00:00 2001 From: Manuel Namici Date: Thu, 22 Dec 2022 20:49:17 +0100 Subject: [PATCH 3/3] core: items: nodes: label: rework automatic label-wrapping logic --- eddy/core/items/nodes/common/label.py | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/eddy/core/items/nodes/common/label.py b/eddy/core/items/nodes/common/label.py index 996e14d3..50b271a4 100644 --- a/eddy/core/items/nodes/common/label.py +++ b/eddy/core/items/nodes/common/label.py @@ -33,6 +33,8 @@ ########################################################################## +from math import ceil + from PyQt5 import ( QtCore, QtGui, @@ -49,6 +51,9 @@ class NodeLabel(AbstractLabel): """ This class implements the label to be attached to the graphol nodes. """ + MinWidth = 60.0 # Minimum label width (in pixels) + MinHeight = 40.0 # Minimum label height (in pixels) + def __init__(self, template='', pos=None, movable=True, editable=True, parent=None): """ Initialize the label. @@ -114,12 +119,13 @@ def wrapLabel(self): Item.ValueDomainNode, Item.LiteralNode, Item.FacetNode]: - self.setTextWidth(max(60, self.parentItem().boundingRect().width())) + width = max(self.MinWidth, self.parentItem().width()) + height = max(self.MinHeight, self.parentItem().height()) fm = QtGui.QFontMetrics(self.font()) - lines = max(40, self.parentItem().height()) // fm.height() - 1 - maxLen = int(self.textWidth() * lines) - elidedText = fm.elidedText(self.template, QtCore.Qt.ElideRight, maxLen) - self.setText(elidedText) + lineWidth = fm.width(self.template) / ceil(fm.width(self.template) / width) + maxWidth = int(lineWidth * (height // fm.lineSpacing())) + self.setText(fm.elidedText(self.template, QtCore.Qt.TextElideMode.ElideRight, maxWidth)) + self.setTextWidth(width) self.setAlignment(self.alignment()) class PredicateLabel(NodeLabel):