61 @param parent reference to the parent object |
62 @param parent reference to the parent object |
62 @type QGraphicsItem |
63 @type QGraphicsItem |
63 """ |
64 """ |
64 super().__init__(parent) |
65 super().__init__(parent) |
65 self.model = model |
66 self.model = model |
66 |
67 |
67 if colors is None: |
68 if colors is None: |
68 self._colors = (QColor(Qt.GlobalColor.black), |
69 self._colors = (QColor(Qt.GlobalColor.black), QColor(Qt.GlobalColor.white)) |
69 QColor(Qt.GlobalColor.white)) |
|
70 else: |
70 else: |
71 self._colors = colors |
71 self._colors = colors |
72 self.setPen(QPen(self._colors[0])) |
72 self.setPen(QPen(self._colors[0])) |
73 |
73 |
74 self.font = Preferences.getGraphics("Font") |
74 self.font = Preferences.getGraphics("Font") |
75 self.margin = 5 |
75 self.margin = 5 |
76 self.associations = [] |
76 self.associations = [] |
77 self.shouldAdjustAssociations = False |
77 self.shouldAdjustAssociations = False |
78 self.__id = -1 |
78 self.__id = -1 |
79 |
79 |
80 self.setRect(x, y, 60, 30) |
80 self.setRect(x, y, 60, 30) |
81 |
81 |
82 if rounded: |
82 if rounded: |
83 p = self.pen() |
83 p = self.pen() |
84 p.setCapStyle(Qt.PenCapStyle.RoundCap) |
84 p.setCapStyle(Qt.PenCapStyle.RoundCap) |
85 p.setJoinStyle(Qt.PenJoinStyle.RoundJoin) |
85 p.setJoinStyle(Qt.PenJoinStyle.RoundJoin) |
86 |
86 |
87 self.setFlag(QGraphicsItem.GraphicsItemFlag.ItemIsMovable, True) |
87 self.setFlag(QGraphicsItem.GraphicsItemFlag.ItemIsMovable, True) |
88 self.setFlag(QGraphicsItem.GraphicsItemFlag.ItemIsSelectable, True) |
88 self.setFlag(QGraphicsItem.GraphicsItemFlag.ItemIsSelectable, True) |
89 self.setFlag( |
89 self.setFlag(QGraphicsItem.GraphicsItemFlag.ItemSendsGeometryChanges, True) |
90 QGraphicsItem.GraphicsItemFlag.ItemSendsGeometryChanges, True) |
90 |
91 |
|
92 def getName(self): |
91 def getName(self): |
93 """ |
92 """ |
94 Public method to retrieve the item name. |
93 Public method to retrieve the item name. |
95 |
94 |
96 @return item name |
95 @return item name |
97 @rtype str |
96 @rtype str |
98 """ |
97 """ |
99 if self.model: |
98 if self.model: |
100 return self.model.name |
99 return self.model.name |
101 else: |
100 else: |
102 return "" |
101 return "" |
103 |
102 |
104 def setSize(self, width, height): |
103 def setSize(self, width, height): |
105 """ |
104 """ |
106 Public method to set the rectangles size. |
105 Public method to set the rectangles size. |
107 |
106 |
108 @param width width of the rectangle |
107 @param width width of the rectangle |
109 @type float |
108 @type float |
110 @param height height of the rectangle |
109 @param height height of the rectangle |
111 @type float |
110 @type float |
112 """ |
111 """ |
113 rect = self.rect() |
112 rect = self.rect() |
114 rect.setSize(QSizeF(width, height)) |
113 rect.setSize(QSizeF(width, height)) |
115 self.setRect(rect) |
114 self.setRect(rect) |
116 |
115 |
117 def addAssociation(self, assoc): |
116 def addAssociation(self, assoc): |
118 """ |
117 """ |
119 Public method to add an association to this widget. |
118 Public method to add an association to this widget. |
120 |
119 |
121 @param assoc association to be added |
120 @param assoc association to be added |
122 @type AssociationWidget |
121 @type AssociationWidget |
123 """ |
122 """ |
124 if assoc and assoc not in self.associations: |
123 if assoc and assoc not in self.associations: |
125 self.associations.append(assoc) |
124 self.associations.append(assoc) |
126 |
125 |
127 def removeAssociation(self, assoc): |
126 def removeAssociation(self, assoc): |
128 """ |
127 """ |
129 Public method to remove an association to this widget. |
128 Public method to remove an association to this widget. |
130 |
129 |
131 @param assoc association to be removed |
130 @param assoc association to be removed |
132 @type AssociationWidget |
131 @type AssociationWidget |
133 """ |
132 """ |
134 if assoc and assoc in self.associations: |
133 if assoc and assoc in self.associations: |
135 self.associations.remove(assoc) |
134 self.associations.remove(assoc) |
136 |
135 |
137 def removeAssociations(self): |
136 def removeAssociations(self): |
138 """ |
137 """ |
139 Public method to remove all associations of this widget. |
138 Public method to remove all associations of this widget. |
140 """ |
139 """ |
141 for assoc in self.associations[:]: |
140 for assoc in self.associations[:]: |
142 assoc.unassociate() |
141 assoc.unassociate() |
143 assoc.hide() |
142 assoc.hide() |
144 del assoc |
143 del assoc |
145 |
144 |
146 def adjustAssociations(self): |
145 def adjustAssociations(self): |
147 """ |
146 """ |
148 Public method to adjust the associations to widget movements. |
147 Public method to adjust the associations to widget movements. |
149 """ |
148 """ |
150 if self.shouldAdjustAssociations: |
149 if self.shouldAdjustAssociations: |
151 for assoc in self.associations: |
150 for assoc in self.associations: |
152 assoc.widgetMoved() |
151 assoc.widgetMoved() |
153 self.shouldAdjustAssociations = False |
152 self.shouldAdjustAssociations = False |
154 |
153 |
155 def moveBy(self, dx, dy): |
154 def moveBy(self, dx, dy): |
156 """ |
155 """ |
157 Public overriden method to move the widget relative. |
156 Public overriden method to move the widget relative. |
158 |
157 |
159 @param dx relative movement in x-direction |
158 @param dx relative movement in x-direction |
160 @type float |
159 @type float |
161 @param dy relative movement in y-direction |
160 @param dy relative movement in y-direction |
162 @type float |
161 @type float |
163 """ |
162 """ |
164 super().moveBy(dx, dy) |
163 super().moveBy(dx, dy) |
165 self.adjustAssociations() |
164 self.adjustAssociations() |
166 |
165 |
167 def setPos(self, x, y): |
166 def setPos(self, x, y): |
168 """ |
167 """ |
169 Public overriden method to set the items position. |
168 Public overriden method to set the items position. |
170 |
169 |
171 @param x absolute x-position |
170 @param x absolute x-position |
172 @type float |
171 @type float |
173 @param y absolute y-position |
172 @param y absolute y-position |
174 @type float |
173 @type float |
175 """ |
174 """ |
176 super().setPos(x, y) |
175 super().setPos(x, y) |
177 self.adjustAssociations() |
176 self.adjustAssociations() |
178 |
177 |
179 def itemChange(self, change, value): |
178 def itemChange(self, change, value): |
180 """ |
179 """ |
181 Public method called when an items state changes. |
180 Public method called when an items state changes. |
182 |
181 |
183 @param change the item's change |
182 @param change the item's change |
184 @type QGraphicsItem.GraphicsItemChange |
183 @type QGraphicsItem.GraphicsItemChange |
185 @param value the value of the change |
184 @param value the value of the change |
186 @return adjusted values |
185 @return adjusted values |
187 """ |
186 """ |
188 if change == QGraphicsItem.GraphicsItemChange.ItemPositionChange: |
187 if change == QGraphicsItem.GraphicsItemChange.ItemPositionChange: |
189 # 1. remember to adjust associations |
188 # 1. remember to adjust associations |
190 self.shouldAdjustAssociations = True |
189 self.shouldAdjustAssociations = True |
191 |
190 |
192 # 2. ensure the new position is inside the scene |
191 # 2. ensure the new position is inside the scene |
193 scene = self.scene() |
192 scene = self.scene() |
194 if scene: |
193 if scene: |
195 rect = scene.sceneRect() |
194 rect = scene.sceneRect() |
196 if not rect.contains(value): |
195 if not rect.contains(value): |
197 # keep the item inside the scene |
196 # keep the item inside the scene |
198 value.setX(min(rect.right(), max(value.x(), rect.left()))) |
197 value.setX(min(rect.right(), max(value.x(), rect.left()))) |
199 value.setY(min(rect.bottom(), max(value.y(), rect.top()))) |
198 value.setY(min(rect.bottom(), max(value.y(), rect.top()))) |
200 return value |
199 return value |
201 |
200 |
202 return QGraphicsItem.itemChange(self, change, value) |
201 return QGraphicsItem.itemChange(self, change, value) |
203 |
202 |
204 def paint(self, painter, option, widget=None): |
203 def paint(self, painter, option, widget=None): |
205 """ |
204 """ |
206 Public method to paint the item in local coordinates. |
205 Public method to paint the item in local coordinates. |
207 |
206 |
208 @param painter reference to the painter object |
207 @param painter reference to the painter object |
209 @type QPainter |
208 @type QPainter |
210 @param option style options |
209 @param option style options |
211 @type QStyleOptionGraphicsItem |
210 @type QStyleOptionGraphicsItem |
212 @param widget optional reference to the widget painted on |
211 @param widget optional reference to the widget painted on |
213 @type QWidget |
212 @type QWidget |
214 """ |
213 """ |
215 pen = self.pen() |
214 pen = self.pen() |
216 if ( |
215 if ( |
217 (option.state & QStyle.StateFlag.State_Selected) == |
216 option.state & QStyle.StateFlag.State_Selected |
218 QStyle.StateFlag.State_Selected |
217 ) == QStyle.StateFlag.State_Selected: |
219 ): |
|
220 pen.setWidth(2) |
218 pen.setWidth(2) |
221 else: |
219 else: |
222 pen.setWidth(1) |
220 pen.setWidth(1) |
223 |
221 |
224 painter.setPen(pen) |
222 painter.setPen(pen) |
225 painter.setBrush(self.brush()) |
223 painter.setBrush(self.brush()) |
226 painter.drawRect(self.rect()) |
224 painter.drawRect(self.rect()) |
227 self.adjustAssociations() |
225 self.adjustAssociations() |
228 |
226 |
229 def setId(self, itemId): |
227 def setId(self, itemId): |
230 """ |
228 """ |
231 Public method to assign an ID to the item. |
229 Public method to assign an ID to the item. |
232 |
230 |
233 @param itemId assigned ID |
231 @param itemId assigned ID |
234 @type int |
232 @type int |
235 """ |
233 """ |
236 self.__id = itemId |
234 self.__id = itemId |
237 |
235 |
238 def getId(self): |
236 def getId(self): |
239 """ |
237 """ |
240 Public method to get the item ID. |
238 Public method to get the item ID. |
241 |
239 |
242 @return ID of the item |
240 @return ID of the item |
243 @rtype int |
241 @rtype int |
244 """ |
242 """ |
245 return self.__id |
243 return self.__id |
246 |
244 |
247 def getItemType(self): |
245 def getItemType(self): |
248 """ |
246 """ |
249 Public method to get the item's type. |
247 Public method to get the item's type. |
250 |
248 |
251 @return item type |
249 @return item type |
252 @rtype str |
250 @rtype str |
253 """ |
251 """ |
254 return self.ItemType |
252 return self.ItemType |
255 |
253 |
256 def parseItemDataString(self, version, data): |
254 def parseItemDataString(self, version, data): |
257 """ |
255 """ |
258 Public method to parse the given persistence data. |
256 Public method to parse the given persistence data. |
259 |
257 |
260 @param version version of the data |
258 @param version version of the data |
261 @type str |
259 @type str |
262 @param data persisted data to be parsed |
260 @param data persisted data to be parsed |
263 @type str |
261 @type str |
264 @return flag indicating success |
262 @return flag indicating success |
265 @rtype bool |
263 @rtype bool |
266 """ |
264 """ |
267 return True |
265 return True |
268 |
266 |
269 def toDict(self): |
267 def toDict(self): |
270 """ |
268 """ |
271 Public method to collect data to be persisted. |
269 Public method to collect data to be persisted. |
272 |
270 |
273 @return dictionary containing data to be persisted |
271 @return dictionary containing data to be persisted |
274 @rtype dict |
272 @rtype dict |
275 """ |
273 """ |
276 return { |
274 return { |
277 "id": self.getId(), |
275 "id": self.getId(), |
278 "x": self.x(), |
276 "x": self.x(), |
279 "y": self.y(), |
277 "y": self.y(), |
280 "type": self.getItemType(), |
278 "type": self.getItemType(), |
281 "model_name": self.model.getName(), |
279 "model_name": self.model.getName(), |
282 } |
280 } |
283 |
281 |
284 @classmethod |
282 @classmethod |
285 def fromDict(cls, data, colors=None): |
283 def fromDict(cls, data, colors=None): |
286 """ |
284 """ |
287 Class method to create a generic UML item from persisted data. |
285 Class method to create a generic UML item from persisted data. |
288 |
286 |
289 @param data dictionary containing the persisted data as generated |
287 @param data dictionary containing the persisted data as generated |
290 by toDict() |
288 by toDict() |
291 @type dict |
289 @type dict |
292 @param colors tuple containing the foreground and background colors |
290 @param colors tuple containing the foreground and background colors |
293 @type tuple of (QColor, QColor) |
291 @type tuple of (QColor, QColor) |
294 @return created UML item |
292 @return created UML item |
295 @rtype UMLItem |
293 @rtype UMLItem |
296 """ |
294 """ |
297 try: |
295 try: |
298 model = UMLModel(data["model_name"]) |
296 model = UMLModel(data["model_name"]) |
299 itm = cls(model=model, |
297 itm = cls(model=model, x=0, y=0, colors=colors) |
300 x=0, |
|
301 y=0, |
|
302 colors=colors) |
|
303 itm.setPos(data["x"], data["y"]) |
298 itm.setPos(data["x"], data["y"]) |
304 itm.setId(data["id"]) |
299 itm.setId(data["id"]) |
305 return itm |
300 return itm |
306 except KeyError: |
301 except KeyError: |
307 return None |
302 return None |