Module: EventConnector
- Included in:
- Wx::EvtHandler
- Defined in:
- lib/wx_sugar/event_connector.rb
Overview
EventConnector
This module is meant to make it easier to connect ruby methods to WxWidgets events generated by user interaction. It introduces a consistent syntax for linking events to handlers, using the listen
method:
listen(evt, source, handler) { block }
The parameter evt
is the type of event that should be listened for, for example the click of a button. To ask to listen to ‘click’ events, pass the argument :click
The parameter source
is the widget whose events should be listened for. This might be a particular button. If source
is set to nil, and lots of widgets might generate this kind of event (for example, if you have multiple buttons), it assumes that ANY button’s clicking should be handled.
The final part of dealing with user events is specifying what should be done when the event occurs. One way is to pass the handler
argument, which should be the name of a method (as a string or symbol) which will handle the event. The other way is to pass a block which should be called when the event is triggered.
This handling method or block may, optionally, accept a single argument, which will be the Event object generated by the event.
Explanation
This module is meant to take some of the pain out of hooking up event handlers to objects. There are subtle differences in WxWidgets in how different types of events are passed to widgets. Some events (typically those fired by controls, subclasses of CommandEvent
) are passed upwards to any containing window that is interested. Others, WxWidgets assumes, are only of interest to the window that generates the event: most events related to frames (ActivateEvent, for example) and miscellaneous windows (Sashes, ScrollWindows) fall under this category.
Defined Under Namespace
Modules: ClassMethods
Class Method Summary collapse
Instance Method Summary collapse
-
#initialize(*args) ⇒ Object
TODO - not called - needs to be done by redefining new.
-
#listen(evt, source = self, handler = nil, &block) ⇒ Object
Listen to events of type
evt
(eg. ‘click’, ‘mousedown’), on the widgetsource
, and handle it byhandler
orblock
The handling code can be specified in a number of different ways: If neitherhandler
orblock
is passed, then the method will attempt to attach events to a listener method called “on_EVT”, where EVT is ‘click’, ‘mousedown’ etc).
Class Method Details
.included(klass) ⇒ Object
55 56 57 58 |
# File 'lib/wx_sugar/event_connector.rb', line 55 def self.included(klass) klass.extend ClassMethods # need a general way to safely interpose in Module methods end |
Instance Method Details
#initialize(*args) ⇒ Object
TODO - not called - needs to be done by redefining new
148 149 150 151 152 153 |
# File 'lib/wx_sugar/event_connector.rb', line 148 def initialize(*args) super(*args) self.class.event_hooks.each do | sym, handler | listen(self, sym, handler) end end |
#listen(evt, source = self, handler = nil, &block) ⇒ Object
Listen to events of type evt
(eg. ‘click’, ‘mousedown’), on the widget source
, and handle it by handler
or block
The handling code can be specified in a number of different ways: If neither handler
or block
is passed, then the method will attempt to attach events to a listener method called “on_EVT”, where EVT is ‘click’, ‘mousedown’ etc).
listen(:click, ) # assumes on_click is defined
If handler is specified as a symbol, the listener will call this named method when the event is triggered
listen(:click, , :on_click_my_button)
If a block is passed, it will be run when the event is triggered.
listen(:click, ) { p "click my button" }
Methods or blocks that are defined as handlers may optionally receive one argument, the Wx event object (see the WxWidgets documentation for more details on this object):
listen(:checkbox, my_checkbox) { | e | puts e.is_checked }
Or in a handler method:
def on_checkbox(e)
if e.is_checked
puts "The checkbox is now checked"
end
end
92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 |
# File 'lib/wx_sugar/event_connector.rb', line 92 def listen(evt, source = self, handler = nil, &block) warn "listen is deprecated, use evt_xxx directly (#{caller[0]})" # get the WxWidget evt_xxx method that will be called for binding event = "evt_#{evt}" if self.respond_to?(event) # try to bind to recipient's methods evt_meth = method(event) elsif source and source.respond_to?(event) evt_meth = source.method(event) else Kernel.raise NameError, "Widget #{self} doesn't generate events of type '#{evt}'" end # get the block or method that will handle the event begin if block handler_meth = block elsif handler handler_meth = self.method(handler) else handler ||= "on_#{evt}" handler_meth = self.method(handler) end rescue NameError Kernel.raise NameError, "#{self} has no handler #{handler}" end # Optionally allow block or handler methods to receive the event # object as an argument if handler_meth.arity == 0 proc = lambda { handler_meth.call() } else proc = lambda { | e | handler_meth.call(e) } end if source source_id = source.get_id else source_id = -1 end begin # Some WxWidgest event connector methods expect the ID of the # triggering widget, others don't. So we try both ways to hide # this complexity evt_meth.call( source_id, &proc ) rescue ArgumentError # Try with no ID specified. evt_meth.call( &proc ) end end |