Software /
code /
prosody
File
util/events.lua @ 5877:615a0774e4cc
util.timer: Updated to use util.indexedbheap to provide a more complete API. Timers can now be stopped or rescheduled. Callbacks are now pcall'd. Adding/removing timers from within timer callbacks works better. Optional parameter can be passed when creating timer which gets passed to callback, eliminating the need for closures in various timer uses. Timers are now much more lightweight.
author | Waqas Hussain <waqas20@gmail.com> |
---|---|
date | Wed, 30 Oct 2013 17:44:42 -0400 |
parent | 5776:bd0ff8ae98a8 |
child | 6638:9d2b56fd6b47 |
line wrap: on
line source
-- Prosody IM -- Copyright (C) 2008-2010 Matthew Wild -- Copyright (C) 2008-2010 Waqas Hussain -- -- This project is MIT/X11 licensed. Please see the -- COPYING file in the source package for more information. -- local pairs = pairs; local t_insert = table.insert; local t_sort = table.sort; local setmetatable = setmetatable; local next = next; module "events" function new() local handlers = {}; local event_map = {}; local function _rebuild_index(handlers, event) local _handlers = event_map[event]; if not _handlers or next(_handlers) == nil then return; end local index = {}; for handler in pairs(_handlers) do t_insert(index, handler); end t_sort(index, function(a, b) return _handlers[a] > _handlers[b]; end); handlers[event] = index; return index; end; setmetatable(handlers, { __index = _rebuild_index }); local function add_handler(event, handler, priority) local map = event_map[event]; if map then map[handler] = priority or 0; else map = {[handler] = priority or 0}; event_map[event] = map; end handlers[event] = nil; end; local function remove_handler(event, handler) local map = event_map[event]; if map then map[handler] = nil; handlers[event] = nil; if next(map) == nil then event_map[event] = nil; end end end; local function add_handlers(handlers) for event, handler in pairs(handlers) do add_handler(event, handler); end end; local function remove_handlers(handlers) for event, handler in pairs(handlers) do remove_handler(event, handler); end end; local function fire_event(event_name, event_data) local h = handlers[event_name]; if h then for i=1,#h do local ret = h[i](event_data); if ret ~= nil then return ret; end end end end; return { add_handler = add_handler; remove_handler = remove_handler; add_handlers = add_handlers; remove_handlers = remove_handlers; fire_event = fire_event; _handlers = handlers; _event_map = event_map; }; end return _M;