Changeset 2074
- Timestamp:
- 09/01/07 13:43:29 (1 year ago)
- Files:
-
- gaphor/trunk/gaphor/UML/properties.py (modified) (9 diffs)
- gaphor/trunk/gaphor/UML/tests/test_properties.py (modified) (4 diffs)
- gaphor/trunk/gaphor/services/tests/test_undomanager.py (modified) (8 diffs)
- gaphor/trunk/gaphor/services/undomanager.py (modified) (2 diffs)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
gaphor/trunk/gaphor/UML/properties.py
r2067 r2074 176 176 return 177 177 178 #undoattributeaction(self, obj, self._get(obj))179 178 if value == self.default: 180 179 delattr(obj, self._name) … … 187 186 old = self._get(obj) 188 187 try: 189 #undoattributeaction(self, obj, self._get(obj))190 188 delattr(obj, self._name) 191 189 except AttributeError: … … 194 192 component.handle(AttributeChangeEvent(obj, self, old, self.default)) 195 193 self.notify(obj) 196 197 198 #class undosetassociationaction(undoaction):199 # """200 # Undo a 'set' action in an association.201 # """202 #203 # def undo(self):204 # #log.debug('undosetassociationaction del: %s %s %s' % (self.obj, self.prop.name, self.value))205 # self.prop._del(self.obj, self.value)206 # return self.redo207 #208 # def redo(self):209 # #log.debug('undosetassociationaction set: %s %s %s' % (self.obj, self.prop.name, self.value))210 # self.prop._set(self.obj, self.value)211 ## return self.undo212 213 214 #class undodelassociationaction(undoaction):215 # """Undo a 'del' action in an association.216 # """217 #218 # def undo(self):219 # #log.debug('undodelassociationaction set: %s %s %s' % (self.obj, self.prop.name, self.value))220 # self.prop._set(self.obj, self.value)221 # return self.redo222 #223 # def redo(self):224 # #log.debug('undodelassociationaction del: %s %s %s' % (self.obj, self.prop.name, self.value))225 # self.prop._del(self.obj, self.value)226 # return self.undo227 194 228 195 … … 300 267 This method is called from the opposite association property. 301 268 """ 302 #print '__set__', self, obj, value 269 #print '__set__', self, obj, value, self._get(obj) 303 270 if not (isinstance(value, self.type) or \ 304 271 (value is None and self.upper == 1)): … … 309 276 310 277 # do nothing if we are assigned our current value: 278 # Still do your thing, since undo handlers expect that. 311 279 if value is old: 312 280 return 313 281 314 282 if old: 315 if not from_opposite and self.opposite: 316 getattr(type(old), self.opposite)._del(old, obj, from_opposite=True) 317 old.disconnect(self.__on_unlink, obj) 318 if self.composite: 319 obj.disconnect(self.__on_composite_unlink, old) 320 321 if value is None: 322 return 323 324 setattr(obj, self._name, value) 283 self._del(obj, old, from_opposite=from_opposite, do_notify=False) 284 325 285 if do_notify: 326 286 event = AssociationSetEvent(obj, self, old, value) 287 288 if value is None: 289 if do_notify: 290 self.notify(obj) 291 component.handle(event) 292 return 293 294 setattr(obj, self._name, value) 295 327 296 else: 328 297 # Set the actual value … … 351 320 component.handle(event) 352 321 353 def _del(self, obj, value, from_opposite=False ):322 def _del(self, obj, value, from_opposite=False, do_notify=True): 354 323 """ 355 324 Delete is used for element deletion and for removal of … … 368 337 getattr(type(value), self.opposite)._del(value, obj, from_opposite=True) 369 338 339 event = None 370 340 if self.upper > 1: 371 341 c = self._get(obj) … … 377 347 pass 378 348 else: 379 component.handle(AssociationDeleteEvent(obj, self, value)) 349 if do_notify: 350 event = AssociationDeleteEvent(obj, self, value) 380 351 381 352 # Remove items collection if empty … … 388 359 pass 389 360 else: 390 component.handle(AssociationSetEvent(obj, self, value, None)) 361 if do_notify: 362 event = AssociationSetEvent(obj, self, value, None) 391 363 392 364 value.disconnect(self.__on_unlink, obj) 393 365 if self.composite: 394 366 obj.disconnect(self.__on_composite_unlink, value) 395 self.notify(obj) 367 if do_notify and event: 368 self.notify(obj) 369 component.handle(event) 396 370 397 371 def __on_unlink(self, value, pspec, obj): gaphor/trunk/gaphor/UML/tests/test_properties.py
r2067 r2074 22 22 assert b.two is a 23 23 24 a.one = None 25 assert a.one is None 26 assert b.two is None 27 28 a.one = b 29 assert a.one is b 30 assert b.two is a 31 32 del a.one 33 assert a.one is None 34 assert b.two is None 35 36 24 37 def test_association_n_x(self): 25 38 # … … 38 51 assert b in a.one 39 52 assert b.two is a 53 40 54 41 55 def test_association_1_1(self): … … 79 93 assert len(a._observers.get('__unlink__')) == 0 80 94 assert len(b._observers.get('__unlink__')) == 0 95 81 96 82 97 def test_association_1_n(self): … … 150 165 else: 151 166 assert 0, 'should not be removed' 167 152 168 153 169 def test_association_n_n(self): gaphor/trunk/gaphor/services/tests/test_undomanager.py
r1859 r2074 43 43 assert undo_manager._current_transaction is None 44 44 45 undo_manager.shutdown() 46 45 47 def test_not_in_transaction(self): 46 48 undo_manager = UndoManager() … … 56 58 assert undo_manager.can_undo() 57 59 assert len(undo_manager._current_transaction._actions) == 1 60 61 undo_manager.shutdown() 58 62 59 63 … … 96 100 assert undone[0] == -1, undone 97 101 102 undo_manager.shutdown() 103 104 98 105 def test_undo_attribute(self): 99 106 import types … … 120 127 assert a.attr == 'five' 121 128 122 def test_undo_aassociation_1_x(self): 129 undo_manager.shutdown() 130 131 def test_undo_association_1_x(self): 123 132 from gaphor.UML.properties import association 124 133 from gaphor.UML.element import Element … … 144 153 assert a.one is b 145 154 assert b.two is a 155 assert len(undo_manager._undo_stack) == 1 156 assert len(undo_manager._undo_stack[0]._actions) == 2, undo_manager._undo_stack[0]._actions 146 157 147 158 undo_manager.undo_transaction() 148 159 assert a.one is None 149 160 assert b.two is None 150 151 undo_manager.redo_transaction() 161 assert undo_manager.can_redo() 162 assert len(undo_manager._redo_stack) == 1 163 assert len(undo_manager._redo_stack[0]._actions) == 2, undo_manager._redo_stack[0]._actions 164 165 undo_manager.redo_transaction() 166 assert len(undo_manager._undo_stack) == 1 167 assert len(undo_manager._undo_stack[0]._actions) == 2, undo_manager._undo_stack[0]._actions 168 assert b.two is a 152 169 assert a.one is b 153 assert b.two is a 170 171 undo_manager.shutdown() 154 172 155 173 def test_undo_association_1_n(self): … … 177 195 assert a1 in b1.two 178 196 assert b1 is a1.one 197 assert len(undo_manager._undo_stack) == 1 198 assert len(undo_manager._undo_stack[0]._actions) == 2, undo_manager._undo_stack[0]._actions 179 199 180 200 undo_manager.undo_transaction() 181 201 assert len(b1.two) == 0 182 202 assert a1.one is None 203 assert undo_manager.can_redo() 204 assert len(undo_manager._redo_stack) == 1 205 assert len(undo_manager._redo_stack[0]._actions) == 2, undo_manager._redo_stack[0]._actions 183 206 184 207 undo_manager.redo_transaction() … … 195 218 assert b1 is a2.one 196 219 220 undo_manager.shutdown() 221 222 197 223 def test_element_factory_undo(self): 198 224 from gaphor.UML.elementfactory import ElementFactory … … 221 247 assert ef.lselect()[0] is p 222 248 249 undo_manager.shutdown() 250 251 252 def test_uml_associations(self): 253 254 from zope import component 255 from gaphor.UML.event import AssociationChangeEvent 256 from gaphor.UML.properties import association, derivedunion 257 from gaphor.UML import Element 258 259 class A(Element): 260 is_unlinked = False 261 def unlink(self): 262 self.is_unlinked = True 263 Element.unlink(self) 264 265 A.a1 = association('a1', A, upper=1) 266 A.a2 = association('a2', A, upper=1) 267 A.b1 = association('b1', A, upper='*') 268 A.b2 = association('b2', A, upper='*') 269 A.b3 = association('b3', A, upper=1) 270 271 A.derived_a = derivedunion('derived_a', 0, 1, A.a1, A.a2) 272 A.derived_b = derivedunion('derived_b', 0, '*', A.b1, A.b2, A.b3) 273 274 events = [] 275 @component.adapter(AssociationChangeEvent) 276 def handler(event, events=events): 277 events.append(event) 278 279 Application.register_handler(handler) 280 try: 281 a = A() 282 283 undo_manager = UndoManager() 284 undo_manager.init(Application) 285 undo_manager.begin_transaction() 286 287 a.a1 = A() 288 undo_manager.commit_transaction() 289 290 assert len(events) == 2 291 assert events[0].property is A.derived_a 292 assert events[1].property is A.a1 293 assert undo_manager.can_undo() 294 295 undo_manager.undo_transaction() 296 assert not undo_manager.can_undo() 297 assert undo_manager.can_redo() 298 assert len(events) == 4, len(events) 299 assert events[2].property is A.derived_a 300 assert events[3].property is A.a1 301 302 finally: 303 Application.unregister_handler(handler) 304 undo_manager.shutdown() 305 306 223 307 # vim:sw=4:et gaphor/trunk/gaphor/services/undomanager.py
r1892 r2074 208 208 209 209 def discard_transaction(self): 210 211 210 if not self._current_transaction: 212 211 raise TransactionError, 'No transaction to discard' … … 348 347 obj = event.element 349 348 value = event.old_value 349 #print 'got new set event', association, obj, value 350 350 def _undo_association_set_event(): 351 351 #print 'undoing action', obj, value
