##// END OF EJS Templates
Merge pull request #8124 from jdfreder/dynamic...
Min RK -
r20932:a748bc5d merge
parent child Browse files
Show More
@@ -292,6 +292,13 b' class Widget(LoggingConfigurable):'
292 292 True if the callback should be unregistered."""
293 293 self._display_callbacks.register_callback(callback, remove=remove)
294 294
295 def add_trait(self, traitname, trait):
296 """Dynamically add a trait attribute to the Widget."""
297 super(Widget, self).add_trait(traitname, trait)
298 if trait.get_metadata('sync'):
299 self.keys.append(traitname)
300 self.send_state(traitname)
301
295 302 #-------------------------------------------------------------------------
296 303 # Support methods
297 304 #-------------------------------------------------------------------------
@@ -1563,3 +1563,55 b' class TestForwardDeclaredTypeList(TraitTestBase):'
1563 1563 ###
1564 1564 # End Forward Declaration Tests
1565 1565 ###
1566
1567 class TestDynamicTraits(TestCase):
1568
1569 def setUp(self):
1570 self._notify1 = []
1571
1572 def notify1(self, name, old, new):
1573 self._notify1.append((name, old, new))
1574
1575 def test_notify_all(self):
1576
1577 class A(HasTraits):
1578 pass
1579
1580 a = A()
1581 self.assertTrue(not hasattr(a, 'x'))
1582 self.assertTrue(not hasattr(a, 'y'))
1583
1584 # Dynamically add trait x.
1585 a.add_trait('x', Int())
1586 self.assertTrue(hasattr(a, 'x'))
1587 self.assertTrue(isinstance(a, (A, )))
1588
1589 # Dynamically add trait y.
1590 a.add_trait('y', Float())
1591 self.assertTrue(hasattr(a, 'y'))
1592 self.assertTrue(isinstance(a, (A, )))
1593 self.assertEqual(a.__class__.__name__, A.__name__)
1594
1595 # Create a new instance and verify that x and y
1596 # aren't defined.
1597 b = A()
1598 self.assertTrue(not hasattr(b, 'x'))
1599 self.assertTrue(not hasattr(b, 'y'))
1600
1601 # Verify that notification works like normal.
1602 a.on_trait_change(self.notify1)
1603 a.x = 0
1604 self.assertEqual(len(self._notify1), 0)
1605 a.y = 0.0
1606 self.assertEqual(len(self._notify1), 0)
1607 a.x = 10
1608 self.assertTrue(('x', 0, 10) in self._notify1)
1609 a.y = 10.0
1610 self.assertTrue(('y', 0.0, 10.0) in self._notify1)
1611 self.assertRaises(TraitError, setattr, a, 'x', 'bad string')
1612 self.assertRaises(TraitError, setattr, a, 'y', 'bad string')
1613 self._notify1 = []
1614 a.on_trait_change(self.notify1, remove=True)
1615 a.x = 20
1616 a.y = 20.0
1617 self.assertEqual(len(self._notify1), 0)
@@ -804,6 +804,12 b' class HasTraits(py3compat.with_metaclass(MetaHasTraits, object)):'
804 804 else:
805 805 return trait.get_metadata(key, default)
806 806
807 def add_trait(self, traitname, trait):
808 """Dynamically add a trait attribute to the HasTraits instance."""
809 self.__class__ = type(self.__class__.__name__, (self.__class__,),
810 {traitname: trait})
811 trait.set_default_value(self)
812
807 813 #-----------------------------------------------------------------------------
808 814 # Actual TraitTypes implementations/subclasses
809 815 #-----------------------------------------------------------------------------
General Comments 0
You need to be logged in to leave comments. Login now