# HG changeset patch # User Radek Brich # Date 1357254839 -3600 # Node ID 43b2279b06e1e746b197f237b22869f3842c957a # Parent d77f1ae3786c8351e8a5ec7874b712acfe8eb19b Clean up Emitter class, simplify event handling. Fix Container.focusnext() method. Add events test (handler auto-registration, order). diff -r d77f1ae3786c -r 43b2279b06e1 demo_checkbox.py --- a/demo_checkbox.py Wed Jan 02 11:48:36 2013 +0100 +++ b/demo_checkbox.py Fri Jan 04 00:13:59 2013 +0100 @@ -10,7 +10,7 @@ class MyApplication(Application): def __init__(self): Application.__init__(self) - self.top.connect('keypress', self.on_top_keypress) + self.top.add_handler('keypress', self.on_top_keypress) self.top.layout = VerticalLayout(homogeneous=False) diff -r d77f1ae3786c -r 43b2279b06e1 demo_editor.py --- a/demo_editor.py Wed Jan 02 11:48:36 2013 +0100 +++ b/demo_editor.py Fri Jan 04 00:13:59 2013 +0100 @@ -8,49 +8,27 @@ from tuikit.application import Application from tuikit.editfield import EditField -from tuikit.window import Window -from tuikit.button import Button -from tuikit.scrollbar import VScrollbar from tuikit.textedit import TextEdit class MyApplication(Application): def __init__(self): Application.__init__(self) - self.top.connect('keypress', self.on_top_keypress) + self.top.add_handler('keypress', self.on_top_keypress) #edit = EditField(50, 'DlouhyTest12') #self.top.add(edit) - t = open('tuikit/widget.py').read() textedit = TextEdit(100, 40, t) self.top.add(textedit) textedit.x = 2 self.textedit = textedit - #win = Window() - #self.top.add(win) - - #button = Button('click!') - #win.add(button) - #button.x = 10 - #button.y = 7 - - #button.connect('click', self.buttonclick) - #self.button = button - - #subwin = Window(8,8) - #win.add(subwin) - - - def buttonclick(self): - self.button.label = 'YES' - - def on_top_keypress(self, ev): if ev.keyname == 'escape': self.terminate() + return True if __name__ == '__main__': diff -r d77f1ae3786c -r 43b2279b06e1 demo_input.py --- a/demo_input.py Wed Jan 02 11:48:36 2013 +0100 +++ b/demo_input.py Fri Jan 04 00:13:59 2013 +0100 @@ -10,7 +10,7 @@ class MyApplication(Application): def __init__(self): Application.__init__(self) - self.top.connect('keypress', self.on_top_keypress) + self.top.add_handler('keypress', self.on_top_keypress) self.text = '' textedit = TextEdit(100, 40, self.text) @@ -18,13 +18,13 @@ textedit.x = 2 self.textedit = textedit - def on_top_keypress(self, ev): if ev.char == 'q': self.terminate() self.text += 'keyname: %(keyname)s char: %(char)s\n' % ev self.textedit.settext(self.text) self.textedit.scrolltoend() + return True if __name__ == '__main__': diff -r d77f1ae3786c -r 43b2279b06e1 demo_layout.py --- a/demo_layout.py Wed Jan 02 11:48:36 2013 +0100 +++ b/demo_layout.py Fri Jan 04 00:13:59 2013 +0100 @@ -10,12 +10,13 @@ class MyApplication(Application): def __init__(self): Application.__init__(self) - self.top.connect('keypress', self.on_top_keypress) + self.top.add_handler('keypress', self.on_top_keypress) #self.top.borders = (1,1,1,1) self.top.layout = VerticalLayout(homogeneous=False) + self._row_num = 0 self.buildrow() self.buildrow(expand=True) self.buildrow(expand=True, fill=True) @@ -25,17 +26,20 @@ self.buildrow(homogeneous=True, fill=True, spacing=2) def buildrow(self, homogeneous=False, spacing=0, expand=False, fill=False): - hbox1 = Container() - hbox1.sizereq.h = 2 - hbox1.layout = HorizontalLayout(homogeneous=homogeneous, spacing=spacing) - self.top.add(hbox1) + hbox = Container() + hbox.sizereq.h = 2 + hbox.layout = HorizontalLayout(homogeneous=homogeneous, spacing=spacing) + self._row_num += 1 + hbox.name = 'hbox' + str(self._row_num) + self.top.add(hbox) for i in range(5): btn = Button('Btn' + str(i) * i * i) - hbox1.add(btn, expand=expand, fill=fill) + hbox.add(btn, expand=expand, fill=fill) def on_top_keypress(self, ev): if ev.keyname == 'escape' or ev.char == 'q': self.terminate() + return True if __name__ == '__main__': diff -r d77f1ae3786c -r 43b2279b06e1 demo_menu.py --- a/demo_menu.py Wed Jan 02 11:48:36 2013 +0100 +++ b/demo_menu.py Fri Jan 04 00:13:59 2013 +0100 @@ -10,7 +10,7 @@ class MyApplication(Application): def __init__(self): Application.__init__(self) - self.top.connect('keypress', self.on_top_keypress) + self.top.add_handler('keypress', self.on_top_keypress) menubar = MenuBar() self.top.add(menubar) @@ -50,22 +50,10 @@ self.top.layout = VerticalLayout() - - #button = Button('click!') - #win.add(button) - #button.x = 10 - #button.y = 7 - - #button.connect('click', self.buttonclick) - #self.button = button - - #subwin = Window(8,8) - #win.add(subwin) - - def on_top_keypress(self, ev): if ev.keyname == 'escape': self.terminate() + return True if __name__ == '__main__': diff -r d77f1ae3786c -r 43b2279b06e1 demo_tableview.py --- a/demo_tableview.py Wed Jan 02 11:48:36 2013 +0100 +++ b/demo_tableview.py Fri Jan 04 00:13:59 2013 +0100 @@ -12,7 +12,7 @@ class MyApplication(Application): def __init__(self): Application.__init__(self) - self.top.connect('keypress', self.on_top_keypress) + self.top.add_handler('keypress', self.on_top_keypress) data = [] for y in range(100): @@ -34,6 +34,7 @@ def on_top_keypress(self, ev): if ev.keyname == 'escape': self.terminate() + return True if __name__ == '__main__': diff -r d77f1ae3786c -r 43b2279b06e1 demo_treeview.py --- a/demo_treeview.py Wed Jan 02 11:48:36 2013 +0100 +++ b/demo_treeview.py Fri Jan 04 00:13:59 2013 +0100 @@ -10,7 +10,7 @@ class MyApplication(Application): def __init__(self): Application.__init__(self) - self.top.connect('keypress', self.on_top_keypress) + self.top.add_handler('keypress', self.on_top_keypress) model = TreeModel() model.add('/', ['a', 'b']) @@ -34,6 +34,7 @@ def on_top_keypress(self, ev): if ev.keyname == 'escape': self.terminate() + return True if __name__ == '__main__': diff -r d77f1ae3786c -r 43b2279b06e1 demo_window.py --- a/demo_window.py Wed Jan 02 11:48:36 2013 +0100 +++ b/demo_window.py Fri Jan 04 00:13:59 2013 +0100 @@ -13,7 +13,7 @@ class MyApplication(Application): def __init__(self): Application.__init__(self) - self.top.connect('keypress', self.globalkeypress) + self.top.add_handler('keypress', self.on_top_keypress) #edit = EditField(50, 'DlouhyTest12') #self.top.add(edit) @@ -26,20 +26,22 @@ button.x = 10 button.y = 7 - button.connect('click', self.buttonclick) + button.add_handler('click', self.on_button_click) self.button = button subwin = Window(8,8) win.add(subwin) - def buttonclick(self): + def on_button_click(self, ev): self.button.label = 'YES' + return True - def globalkeypress(self, keyname, char): - if keyname == 'escape': + def on_top_keypress(self, ev): + if ev.keyname == 'escape': self.terminate() + return True if __name__ == '__main__': @@ -47,7 +49,7 @@ os.environ['ESCDELAY'] = '25' # do not wait 1 second after pressing Escape key app = MyApplication() #app.start() - + cProfile.run('app.start()', 'demo_window.appstats') p = pstats.Stats('demo_window.appstats') p.sort_stats('time', 'cumulative').print_stats(20) diff -r d77f1ae3786c -r 43b2279b06e1 docs/emitter.rst --- a/docs/emitter.rst Wed Jan 02 11:48:36 2013 +0100 +++ b/docs/emitter.rst Fri Jan 04 00:13:59 2013 +0100 @@ -7,7 +7,7 @@ widget -.. automodule:: tuikit.emitter +.. autoclass:: tuikit.events.Emitter :members: :show-inheritance: diff -r d77f1ae3786c -r 43b2279b06e1 docs/events.rst --- a/docs/events.rst Wed Jan 02 11:48:36 2013 +0100 +++ b/docs/events.rst Fri Jan 04 00:13:59 2013 +0100 @@ -1,5 +1,5 @@ -Event handling -============== +Events +====== Draw event ---------- diff -r d77f1ae3786c -r 43b2279b06e1 docs/index.rst --- a/docs/index.rst Wed Jan 02 11:48:36 2013 +0100 +++ b/docs/index.rst Fri Jan 04 00:13:59 2013 +0100 @@ -18,7 +18,7 @@ colors .. inheritance-diagram:: tuikit.application - tuikit.emitter + tuikit.events tuikit.widget tuikit.container tuikit.window diff -r d77f1ae3786c -r 43b2279b06e1 tests/events.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/tests/events.py Fri Jan 04 00:13:59 2013 +0100 @@ -0,0 +1,61 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- + +import sys +sys.path.append('..') + +from tuikit.events import Emitter, KeyboardEvent + +class A(Emitter): + def __init__(self): + self.add_events('keypress', KeyboardEvent) + + def on_keypress(self, ev): + """A""" + print('A on', ev.keyname, self) + + def after_keypress(self, ev): + """A""" + print('A after', ev.keyname, self) + + +class B(A): + def __init__(self): + super().__init__() + + def on_keypress(self, ev): + """B""" + print('B on', ev.keyname, self) + #return True + + def after_keypress(self, ev): + """B""" + print('B after', ev.keyname, self) + + +class C(B): + def __init__(self): + super().__init__() + + +def on_keypress(ev): + """global""" + print('global on', ev.keyname) + + +def after_keypress(ev): + """global""" + print('global after', ev.keyname) + + +if __name__ == '__main__': + c = C() + c.add_handler('keypress', after_keypress, last=True) + c.add_handler('keypress', on_keypress) + + for x in c._event_handlers['keypress']: + print(x, x.__doc__) + + print() + c.emit('keypress', keyname='XKey', char=None) + diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/button.py --- a/tuikit/button.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/button.py Fri Jan 04 00:13:59 2013 +0100 @@ -36,8 +36,7 @@ self.add_events('click', Event) - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): pad = self.width - len(self.label) - len(self.prefix) - len(self.suffix) lpad, rpad = self._divide_padding(pad) ev.driver.pushcolor(self.getcolor()) @@ -57,21 +56,18 @@ ev.driver.puts(ev.x + pos, ev.y, self.suffix) ev.driver.popcolor() - def _handle_mousedown(self, ev): - super()._handle_mousedown(ev) + def on_mousedown(self, ev): self.highlight = True self.redraw() - def _handle_mouseup(self, ev): - super()._handle_mouseup(ev) + def on_mouseup(self, ev): self.highlight = False self.redraw() if self.enclose(ev.px, ev.py): self.emit('click') - def _handle_keypress(self, ev): - super()._handle_keypress(ev) + def on_keypress(self, ev): if ev.keyname == 'enter': self.emit('click') diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/checkbox.py --- a/tuikit/checkbox.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/checkbox.py Fri Jan 04 00:13:59 2013 +0100 @@ -18,8 +18,7 @@ self.bg = 'normal' self.bghi = 'active' - def _handle_click(self, ev): - super()._handle_click(ev) + def on_click(self, ev): if self.checked: self.checked = False self.prefix = '[ ] ' diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/combobox.py --- a/tuikit/combobox.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/combobox.py Fri Jan 04 00:13:59 2013 +0100 @@ -22,7 +22,7 @@ self._btn.suffix = '' self._btn.x = width - 3 self._btn.width = 3 - self._btn.connect('click', self._on_btn_click) + self._btn.add_handler('click', self._on_btn_click) self.add(self._btn) self._menu = Menu(items) diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/container.py --- a/tuikit/container.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/container.py Fri Jan 04 00:13:59 2013 +0100 @@ -72,7 +72,8 @@ this cycling: * False means there wasn't any child to focus - before end of list, so first child was focused. + before end of list. Focus was either not changed + or first child was focused. * True when focus is set to next child in normal way or when self.trap_focus is set. @@ -82,16 +83,18 @@ """ idx_current = self.children.index(self.focuschild) - idx_new = idx_current + 1 + idx_new = idx_current cycled = False - while idx_current != idx_new: + while True: + idx_new += 1 if idx_new >= len(self.children): idx_new = 0 cycled = True + if idx_current == idx_new: + return False if self.children[idx_new].can_focus(): self.children[idx_new].set_focus() return self.trap_focus or not cycled - idx_new += 1 def draw(self, driver, x, y): """Draw the container and its children. @@ -126,13 +129,11 @@ driver.popcolorprefix() driver.clipstack.pop() - def _handle_resize(self, ev): - super()._handle_resize(ev) + def on_resize(self, ev): for child in self.children: child.emit('resize') - def _handle_keypress(self, ev): - super()._handle_keypress(ev) + def on_keypress(self, ev): if self.focuschild is not None: handled = self.focuschild.emit('keypress', ev) if handled: @@ -140,8 +141,7 @@ if ev.keyname == 'tab': return self.focus_next() - def _handle_mousedown(self, ev): - super()._handle_mousedown(ev) + def on_mousedown(self, ev): handled = False for child in reversed(self.children): if child.enclose(ev.wx, ev.wy): @@ -152,23 +152,20 @@ break return handled - def _handle_mouseup(self, ev): - super()._handle_mouseup(ev) + def on_mouseup(self, ev): if self.mousechild: childev = ev.childevent(self.mousechild) self.mousechild.emit('mouseup', childev) self.mousechild = None return True - def _handle_mousemove(self, ev): - super()._handle_mousemove(ev) + def on_mousemove(self, ev): if self.mousechild: childev = ev.childevent(self.mousechild) self.mousechild.emit('mousemove', childev) return True - def _handle_mousewheel(self, ev): - super()._handle_mousewheel(ev) + def on_mousewheel(self, ev): handled = False for child in reversed(self.children): if child.enclose(ev.wx, ev.wy): diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/editbox.py --- a/tuikit/editbox.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/editbox.py Fri Jan 04 00:13:59 2013 +0100 @@ -28,8 +28,7 @@ self.set_text(text) - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): for j in range(self.height): if self.yofs + j >= len(self.lines): break @@ -43,8 +42,7 @@ self.cursor = (self.get_cpos() - self.xofs, self.cline - self.yofs) - def _handle_keypress(self, ev): - super()._handle_keypress(ev) + def on_keypress(self, ev): if ev.keyname: if ev.keyname == 'left': self.move_left() @@ -89,8 +87,7 @@ self.redraw() - def _handle_mousewheel(self, ev): - super()._handle_mousewheel(ev) + def on_mousewheel(self, ev): # up if ev.button == 4: self.move_up() diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/editfield.py --- a/tuikit/editfield.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/editfield.py Fri Jan 04 00:13:59 2013 +0100 @@ -22,12 +22,10 @@ self.pos = len(value) # position of cursor in value self.ofs = 0 # position of value beginning on screen - def _handle_resize(self, ev): - super()._handle_resize(ev) + def on_resize(self, ev): self.tw = self.width - 2 - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): ev.driver.pushcolor('normal') # draw value val = self.value + ' ' * self.tw # add spaces to fill rest of field @@ -48,8 +46,7 @@ self.cursor = (1 + self.pos - self.ofs, 0) ev.driver.popcolor() - def _handle_keypress(self, ev): - super()._handle_keypress(ev) + def on_keypress(self, ev): handled = False if ev.keyname: handled = True diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/events.py --- a/tuikit/events.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/events.py Fri Jan 04 00:13:59 2013 +0100 @@ -9,6 +9,7 @@ """ import logging +import inspect class Event: @@ -88,57 +89,69 @@ """Event emitter mixin class.""" def add_events(self, *events): - """Add events which may be registered by user. + """Add events which may be emitted on instances of this class. This should be called only by subclasses. - This serves also as initializer, other methods of Emitter + It also serves as initializer, other methods of Emitter will not work if add_events was not called. *events -- Arguments must be given in pairs. Each pair consists of event_name, event_class: - event_name -- a string used in connect(), emit() + event_name -- a string used in add_handler(), emit() etc. event_class -- class of event payload + It will also inspect base classes of instance on which add_events() + is called, adding all methods meeting naming convention to handler list. + The convention for method names is "on_event_name", "after_event_name". + Prefix on/after determines whether the handler is added as first or last. + """ + if len(events) % 2: + raise ValueError('add_events(): Event names and classes must be passed in pairs.') if not hasattr(self, '_event_handlers'): self._event_handlers = dict() self._event_class = dict() for event_name, event_class in zip(events[::2], events[1::2]): + if not isinstance(event_name, str): + raise TypeError('add_events(): Event name must be a string: %r.' % event_name) + if not issubclass(event_class, Event): + raise TypeError('add_events(): Class %s does not inherit from Event.' % event_class) self._event_handlers[event_name] = [] self._event_class[event_name] = event_class - # add default dummy handler if no handler exists for this event - handler_name = '_handle_' + event_name - if not hasattr(Emitter, handler_name): - setattr(Emitter, handler_name, lambda self, ev: False) + self._add_default_handlers(event_name) - def connect(self, event_name, handler): - """Connect event handler to event name. + def add_handler(self, event_name, handler, last=False): + """Add handler to event name. - Add handler to the end of handler list. + last=False -- Add handler as first in handler list. + last=True -- Add handler to the end of handler list. """ if event_name in self._event_handlers: - self._event_handlers[event_name].append(handler) + if last: + self._event_handlers[event_name].append(handler) + else: + self._event_handlers[event_name].insert(0, handler) else: raise KeyError('Unknown event: %s', event_name) - def disconnect(self, event_name, handler=None): - """Remove event handler from the list. - - If no handler is given, remove all handlers. - - """ + def remove_handler(self, event_name, handler): + """Remove event handler from the list.""" if event_name in self._event_handlers: - if handler: - self._event_handlers[event_name].remove(handler) - else: - self._event_handlers[event_name][:] = [] + self._event_handlers[event_name].remove(handler) else: raise KeyError('Unknown event: %s', event_name) - def is_connected(self, event_name): - """Test if any handlers are connected to event name. + def remove_all_handlers(self, event_name): + """Remove all handlers for event.""" + if event_name in self._event_handlers: + self._event_handlers[event_name][:] = [] + else: + raise KeyError('Unknown event: %s', event_name) + + def has_handlers(self, event_name): + """Test if any handlers are attached to event name. Return True if event handler list is not empty, False otherwise. @@ -153,17 +166,20 @@ """Emit the event. Call all handlers from event's handler list, - starting from first added handler. + starting from last added handler, going to those added + before, ending with those added with last=True. + + Stop if any handler returns True. Return True when one of the handlers returns True, False otherwise. - This creates new instance of event_class given to + Creates new instance of event_class given to add_events() and passes all arguments after event_name to its __init__ method. Unless first of these arguments is Event instance - in which case no object is created and the instance + in which case no object is created and the Event instance is passed to handlers. """ @@ -172,18 +188,50 @@ self.__class__.__name__, getattr(self, 'name', None) or id(self)) # create event from specified event class, or use first argument - if len(args) and isinstance(args[0], Event): + if len(args) == 1 and isinstance(args[0], Event): event = args[0] else: event = self._event_class[event_name](*args, **kwargs) + # set originator to instance on which emit() was called event.originator = self - # try default handler, stop if satisfied - handled = getattr(self, '_handle_' + event_name)(event) - if handled: - return True - # try custom handlers, stop if satisfied + # call handlers from first to last, stop if satisfied for handler in self._event_handlers[event_name]: handled = handler(event) if handled: return True + return False + def _add_default_handlers(self, event_name): + """Add default handlers from the instance and its base classes. + + Handlers are looked up in methods by their names. + Method name is composited from prefix and event_name. + Prefix is one of "on_" or "after_". + Depending on prefix the handler is added to top or bottom of handler stack. + + See _add_default_handler method for more information. + + """ + for cls in reversed(inspect.getmro(self.__class__)): + self._add_default_handler(cls, 'on_', event_name, last=False) + self._add_default_handler(cls, 'after_', event_name, last=True) + + def _add_default_handler(self, cls, prefix, event_name, last): + """Add handler from one of base classes to handler list. + + cls -- one of self's base classes + prefix -- method name prefix + event_name -- event name + last -- if True, add handler to end of handler list (will be called last) + + Look for method of name prefix + event_name in class 'cls', + if exists, add it to handler list. + + """ + method_name = prefix + event_name + if method_name in cls.__dict__: + unbound_handler = cls.__dict__[method_name] + if callable(unbound_handler): + handler = unbound_handler.__get__(self, cls) + self.add_handler(event_name, handler, last) + diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/label.py --- a/tuikit/label.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/label.py Fri Jan 04 00:13:59 2013 +0100 @@ -9,8 +9,7 @@ self.label = label - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): ev.driver.pushcolor('normal') ev.driver.puts(ev.x, ev.y, self.label) ev.driver.popcolor() diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/layout.py --- a/tuikit/layout.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/layout.py Fri Jan 04 00:13:59 2013 +0100 @@ -23,7 +23,7 @@ @container.setter def container(self, value): self._container = value - self._container.connect('resize', self._on_container_resize) + self._container.add_handler('resize', self._on_container_resize) def _on_container_resize(self, ev): self.resize() diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/menu.py --- a/tuikit/menu.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/menu.py Fri Jan 04 00:13:59 2013 +0100 @@ -20,8 +20,7 @@ self.add_events('activate', GenericEvent) - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): ev.driver.pushcolor(self.bg) ev.driver.frame(ev.x, ev.y, self.width, self.height) i = 1 @@ -41,8 +40,7 @@ i += 1 ev.driver.popcolor() - def _handle_keypress(self, ev): - super()._handle_keypress(ev) + def on_keypress(self, ev): if ev.keyname == 'up': self.move_selected(-1) if ev.keyname == 'down': @@ -51,16 +49,13 @@ self.run_selected() self.redraw() - def _handle_mousedown(self, ev): - super()._handle_mousedown(ev) + def on_mousedown(self, ev): self.select_at_pos(ev.wy - 1) - def _handle_mousemove(self, ev): - super()._handle_mousemove(ev) + def on_mousemove(self, ev): self.select_at_pos(ev.wy - 1) - def _handle_mouseup(self, ev): - super()._handle_mousemove(ev) + def on_mouseup(self, ev): ok = self.select_at_pos(ev.wy - 1) if ok: self.run_selected() diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/menubar.py --- a/tuikit/menubar.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/menubar.py Fri Jan 04 00:13:59 2013 +0100 @@ -25,12 +25,11 @@ item[1].y = self.y + 1 item[1].allow_layout = False item[1].hidden = True - item[1].connect('focus', self.on_submenu_focus) + item[1].add_handler('focus', self.on_submenu_focus) item[1].menubar = self i += len(item[0]) + 4 - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): ev.driver.pushcolor(self.bg) i = 0 for item in self.items: @@ -46,8 +45,7 @@ ev.driver.popcolor() - def _handle_keypress(self, ev): - super()._handle_draw(ev) + def on_keypress(self, ev): if ev.keyname == 'left': self.move_selected(-1) elif ev.keyname == 'right': @@ -66,12 +64,10 @@ self.select(item) self.redraw() - def _handle_mousedown(self, ev): - super()._handle_mousedown(ev) + def on_mousedown(self, ev): self._select_xy(ev.wx, ev.wy) - def _handle_mousemove(self, ev): - super()._handle_mousemove(ev) + def on_mousemove(self, ev): self._select_xy(ev.wx, ev.wy) def _select_xy(self, wx, wy): @@ -83,8 +79,7 @@ self.select(item) i += w - def _handle_unfocus(self, ev): - super()._handle_unfocus(ev) + def on_unfocus(self, ev): if self.selected and ev.new == self.selected[1]: return self.unselect() diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/pager.py --- a/tuikit/pager.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/pager.py Fri Jan 04 00:13:59 2013 +0100 @@ -41,7 +41,7 @@ widget.hidden = True btn = Button(kw['title']) - btn.connect('click', lambda: self.select(widget)) + btn.add_handler('click', lambda: self.select(widget)) self.buttons.add(btn, fill=True) def select(self, child): diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/scrollbar.py --- a/tuikit/scrollbar.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/scrollbar.py Fri Jan 04 00:13:59 2013 +0100 @@ -51,16 +51,14 @@ self._thumbpos = int(round(self._pos / self._max * (self.height - 3))) self.redraw() - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): ev.driver.putch(ev.x, ev.y, ev.driver.unigraph.UP_ARROW) for i in range(ev.y + 1, ev.y + self.height - 1): ev.driver.putch(ev.x, i, ev.driver.unigraph.LIGHT_SHADE) ev.driver.putch(ev.x, ev.y + 1 + self._thumbpos, ev.driver.unigraph.BLOCK) ev.driver.putch(ev.x, ev.y + self.height - 1, ev.driver.unigraph.DOWN_ARROW) - def _handle_mousedown(self, ev): - super()._handle_mousedown(ev) + def on_mousedown(self, ev): self.dragging = False self.move = None # arrow buttons @@ -76,8 +74,7 @@ self.dragging = True return - def _handle_mouseup(self, ev): - super()._handle_mouseup(ev) + def on_mouseup(self, ev): if self.dragging: self.drag(ev.wy) self.dragging = False @@ -87,8 +84,7 @@ self.move = None return - def _handle_mousemove(self, ev): - super()._handle_mousemove(ev) + def on_mousemove(self, ev): if self.dragging: self.drag(ev.wy) diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/scrollview.py --- a/tuikit/scrollview.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/scrollview.py Fri Jan 04 00:13:59 2013 +0100 @@ -16,18 +16,17 @@ Container.__init__(self, width, height) self.vscroll = VScrollbar(height) - self.vscroll.connect('change', self._on_vscroll_change) + self.vscroll.add_handler('change', self._on_vscroll_change) self.vscroll.allow_layout = False self.add(self.vscroll) def add(self, widget, **kwargs): super().add(widget, **kwargs) if widget != self.vscroll: - widget.connect('sizereq', self._on_child_sizereq) - widget.connect('spotmove', self._on_child_spotmove) + widget.add_handler('sizereq', self._on_child_sizereq) + widget.add_handler('spotmove', self._on_child_spotmove) - def _handle_resize(self, ev): - super()._handle_resize(ev) + def on_resize(self, ev): self.vscroll.x = self.size.w - 1 self.vscroll.height = self.height self._update_vscroll_max() diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/tableview.py --- a/tuikit/tableview.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/tableview.py Fri Jan 04 00:13:59 2013 +0100 @@ -91,10 +91,10 @@ def setmodel(self, value): if self._model: - self._model.disconnect('change', self.redraw) + self._model.remove_handler('change', self.redraw) self._model = value if self._model: - self._model.connect('change', self.redraw) + self._model.add_handler('change', self.redraw) model = property(getmodel, setmodel) @@ -158,8 +158,7 @@ screen.popcolor() x += col.size + self.spacing - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): ev.driver.pushcolor('normal') self.rowcount = self.model.getcount() numrows = min(self.rowcount - self.offset.y, self.size.h - self.headsize) @@ -175,15 +174,17 @@ y += 1 ev.driver.popcolor() - def _handle_keypress(self, ev): - super()._handle_keypress(ev) - if ev.keyname: - if ev.keyname == 'up': self.move_up() - if ev.keyname == 'down': self.move_down() - if ev.keyname == 'left': self.move_left() - if ev.keyname == 'right': self.move_right() - if ev.keyname == 'pageup': self.move_pageup() - if ev.keyname == 'pagedown': self.move_pagedown() + def on_keypress(self, ev): + key_map = { + 'up': self.move_up, + 'down': self.move_down, + 'left': self.move_left, + 'right': self.move_right, + 'pageup': self.move_pageup, + 'pagedown': self.move_pagedown} + if ev.keyname in key_map: + key_map[ev.keyname]() + return True self.redraw() def set_yofs(self, yofs): diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/textedit.py --- a/tuikit/textedit.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/textedit.py Fri Jan 04 00:13:59 2013 +0100 @@ -13,14 +13,14 @@ self.add(self.editbox) self.editbox.x = 1 self.editbox.y = 1 - self.editbox.connect('scroll', self.on_editbox_scroll) - self.editbox.connect('areasize', self.on_editbox_areasize) + self.editbox.add_handler('scroll', self.on_editbox_scroll) + self.editbox.add_handler('areasize', self.on_editbox_areasize) self.vscroll = VScrollbar(height - 2) self.add(self.vscroll) self.vscroll.x = width - 1 self.vscroll.y = 1 - self.vscroll.connect('change', self.on_vscroll_change) + self.vscroll.add_handler('change', self.on_vscroll_change) self.on_editbox_areasize(None) @@ -30,8 +30,7 @@ def scrolltoend(self): self.editbox.move_pagelast() - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): ev.driver.frame(ev.x, ev.y, self.width, self.height) def on_editbox_scroll(self, ev): diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/treeview.py --- a/tuikit/treeview.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/treeview.py Fri Jan 04 00:13:59 2013 +0100 @@ -205,10 +205,10 @@ @model.setter def model(self, value): if self._model: - self._model.disconnect('node_added', self.on_model_node_added) + self._model.remove_handler('node_added', self.on_model_node_added) self._model = value if self._model: - self._model.connect('node_added', self.on_model_node_added) + self._model.add_handler('node_added', self.on_model_node_added) try: self.cursor_node = self._model.root.children[0] except IndexError: @@ -247,8 +247,7 @@ pass self._update_sizereq() - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): ev.driver.pushcolor('normal') lines = 0 # bit array, bit 0 - draw vertical line on first column, etc. @@ -283,14 +282,15 @@ ev.driver.popcolor() - def _handle_keypress(self, ev): - super()._handle_keypress(ev) - if ev.keyname: - if ev.keyname == 'up': self.move_up() - if ev.keyname == 'down': self.move_down() - if ev.keyname == 'left': self.move_left() - if ev.keyname == 'right': self.move_right() - + def on_keypress(self, ev): + key_map = { + 'up': self.move_up, + 'down': self.move_down, + 'left': self.move_left, + 'right': self.move_right} + if ev.keyname in key_map: + key_map[ev.keyname]() + return True self.redraw() def prev_node(self, node): diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/widget.py --- a/tuikit/widget.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/widget.py Fri Jan 04 00:13:59 2013 +0100 @@ -36,7 +36,7 @@ #: Size request. This is default size of the widget. Will be fulfilled if possible. #: Size(w, h). Integers >= 1 or None (meaning use minumal size). self._sizereq = Size(10, 10) - self._sizereq.connect('change', lambda ev: self.emit('sizereq')) + self._sizereq.add_handler('change', lambda ev: self.emit('sizereq')) #: When false, the widget is not considered in layout. self.allow_layout = True @@ -157,7 +157,7 @@ """Draw the widget. This method should not be overriden by subclasses, - use _handle_draw instead. + use on_draw method instead. """ if self.hidden: @@ -172,8 +172,8 @@ else: driver.hidecursor() - def _handle_mousedown(self, ev): - self.set_focus() + def on_mousedown(self, ev): + self.grab_focus() ### focus diff -r d77f1ae3786c -r 43b2279b06e1 tuikit/window.py --- a/tuikit/window.py Wed Jan 02 11:48:36 2013 +0100 +++ b/tuikit/window.py Fri Jan 04 00:13:59 2013 +0100 @@ -3,8 +3,6 @@ from tuikit.container import Container from tuikit.button import Button -import logging - class Window(Container): @@ -35,7 +33,7 @@ self.closebtn.allow_layout = False self.closebtn.x = self.width - 5 self.closebtn.width = 3 - self.closebtn.connect('click', self.on_closebtn_click) + self.closebtn.add_handler('click', self.on_closebtn_click) self.closebtn.bg = 'controls' self.closebtn.bghi = 'controls-active' self.add(self.closebtn) @@ -55,8 +53,7 @@ self.closebtn.hidden = not value - def _handle_draw(self, ev): - super()._handle_draw(ev) + def on_draw(self, ev): ev.driver.pushcolor('normal') ev.driver.frame(ev.x, ev.y, self.width, self.height) @@ -75,11 +72,7 @@ ev.driver.popcolor() - def _handle_mousedown(self, ev): - handled = super()._handle_mousedown(ev) - if handled: - return True - + def after_mousedown(self, ev): self.dragstart = (ev.wx, ev.wy) if self.resizable and ev.wx >= self.width - 1 and ev.wy >= self.height - 1: self.resizing = True @@ -90,11 +83,7 @@ self.redraw(True) - def _handle_mouseup(self, ev): - handled = super()._handle_mouseup(ev) - if handled: - return True - + def after_mouseup(self, ev): if self.resizing: self.width = self.origsize[0] + ev.wx - self.dragstart[0] self.height = self.origsize[1] + ev.wy - self.dragstart[1] @@ -108,11 +97,7 @@ self.redraw(True) - def _handle_mousemove(self, ev): - handled = super()._handle_mousemove(ev) - if handled: - return True - + def after_mousemove(self, ev): if ev.px == self.x + self.dragstart[0] \ and ev.py == self.y + self.dragstart[1]: return @@ -131,8 +116,7 @@ self.redraw(True) - def _handle_resize(self, ev): - super()._handle_resize(ev) + def on_resize(self, ev): self.closebtn.x = self.width - 5