57 lines
1.4 KiB
Ruby
57 lines
1.4 KiB
Ruby
class EventBus
|
|
def initialize
|
|
# store callbacks with owner: {event => [ {callback:, owner:} ] }
|
|
@events = Hash.new { |h, k| h[k] = [] }
|
|
@retrievable_events = {}
|
|
end
|
|
|
|
# Emit an event
|
|
def emit(event, *args)
|
|
@events[event].each do |h|
|
|
h[:callback].call(*args)
|
|
end
|
|
end
|
|
|
|
# Subscribe to an event
|
|
def on(event, owner: nil, &callback)
|
|
owner ||= callback.binding.eval("self")
|
|
@events[event] << { callback: callback, owner: owner }
|
|
end
|
|
|
|
# Subscribe to an event that should only be called once
|
|
def once(event, owner = nil, &callback)
|
|
wrapper = nil
|
|
wrapper = proc do |*args|
|
|
callback.call(*args)
|
|
off(event, &wrapper)
|
|
end
|
|
on(event, owner: owner, &wrapper)
|
|
end
|
|
|
|
def off(event, &callback)
|
|
@events[event].reject! { |h| h[:callback] == callback }
|
|
end
|
|
|
|
# Register a retrievable event (only one allowed)
|
|
def on_retrievable(event, owner = nil, &callback)
|
|
owner ||= callback.binding.eval("self")
|
|
@retrievable_events[event] = { callback: callback, owner: owner }
|
|
end
|
|
|
|
# Get data from a retrievable event
|
|
def get(event, *args)
|
|
if @retrievable_events[event]
|
|
@retrievable_events[event][:callback].call(*args)
|
|
else
|
|
nil
|
|
end
|
|
end
|
|
|
|
# Unsubscribe from an object's events
|
|
def unlisten_owner(owner)
|
|
@events.each do |event, handlers|
|
|
handlers.reject! { |h| h[:owner] == owner }
|
|
end
|
|
@retrievable_events.delete_if { |_, h| h[:owner] == owner }
|
|
end
|
|
end |