diff options
author | Mason Larobina <mason.larobina@gmail.com> | 2009-09-07 04:31:26 +0800 |
---|---|---|
committer | Mason Larobina <mason.larobina@gmail.com> | 2009-09-07 04:31:26 +0800 |
commit | 97f12f6eee2c7ae24ac195b9cb76e41e86f58863 (patch) | |
tree | b6c4b4bef7b47abcdb55322c6f9f4bf1e670bd6d /examples | |
parent | 13cd8f34e86fe9bd17fffd770eb0c1ee57bd1815 (diff) |
Functions in plugins that look like "export_<name>" become uzbl.<name>
Diffstat (limited to 'examples')
-rwxr-xr-x | examples/data/uzbl/scripts/event_manager.py | 96 | ||||
-rw-r--r-- | examples/data/uzbl/scripts/plugins/bind.py | 49 |
2 files changed, 104 insertions, 41 deletions
diff --git a/examples/data/uzbl/scripts/event_manager.py b/examples/data/uzbl/scripts/event_manager.py index e293002..5145653 100755 --- a/examples/data/uzbl/scripts/event_manager.py +++ b/examples/data/uzbl/scripts/event_manager.py @@ -46,6 +46,7 @@ import select import re import types import socket +import pprint from traceback import print_exc @@ -193,7 +194,22 @@ class PluginManager(dict): self.load_plugins() -class UzblInstance: +def export_wrapper(uzbl, function): + '''Return an object that appends the uzbl meta-instance to the front of + the argument queue. I.e. (*args, **kargs) -> (uzbl, *args, **kargs)''' + + class Export(object): + def __init__(self, uzbl, function): + self.function = function + self.uzbl = uzbl + + def call(self, *args, **kargs): + return self.function(self.uzbl, *args, **kargs) + + return Export(uzbl, function).call + + +class UzblInstance(object): '''Event manager for a uzbl instance.''' # Singleton plugin manager. @@ -202,6 +218,9 @@ class UzblInstance: def __init__(self): '''Initialise event manager.''' + # Hold functions exported by plugins. + self._exports = {} + class ConfigDict(dict): def __init__(self, setcmd): self._setcmd = setcmd @@ -251,6 +270,17 @@ class UzblInstance: self._init_plugins() + def __getattribute__(self, name): + '''Expose any exported functions before class functions.''' + + if not name.startswith('_'): + exports = object.__getattribute__(self, '_exports') + if name in exports: + return exports[name] + + return object.__getattribute__(self, name) + + def _get_config(self): '''Return the uzbl config dictionary.''' @@ -260,11 +290,27 @@ class UzblInstance: def _init_plugins(self): - '''Call the init() function in every plugin.''' + '''Call the init() function in every plugin and expose all exposable + functions in the plugins root namespace.''' + + # Map all plugin exports + for (name, plugin) in self.plugins.items(): + for attr in dir(plugin): + if not attr.startswith('export_') or attr == 'export_': + continue + + obj = getattr(plugin, attr) + if type(obj) in [types.LambdaType, types.FunctionType]: + obj = export_wrapper(self, obj) + + self._exports[attr[7:]] = obj - for plugin in self.plugins.keys(): + echo("exposed attribute(s): %s" % ', '.join(self._exports.keys())) + + # Now call the init function in all plugins. + for (name, plugin) in self.plugins.items(): try: - self.plugins[plugin].init(self) + plugin.init(self) except: print_exc() @@ -338,43 +384,6 @@ class UzblInstance: del self.handlers[event][id] - def bind(self, glob, cmd=None): - '''Support for classic uzbl binds. - - For example: - bind ZZ = exit -> bind('ZZ', 'exit') - bind o _ = uri %s -> bind('o _', 'uri %s') - bind fl* = sh 'echo %s' -> bind('fl*', "sh 'echo %s'") - bind fl* = -> bind('fl*') - - And it is also possible to execute a function on activation: - bind('DD', myhandler) - - NOTE: This wont work yet but the groundwork has been layed out. - ''' - - if not cmd: - if glob in self.binds.keys(): - echo("deleted bind: %r" % self.binds[glob]) - del self.binds[glob] - - d = {'glob': glob, 'once': True, 'hasargs': True, 'cmd': cmd} - - if glob.endswith('*'): - d['pre'] = glob.rstrip('*') - d['once'] = False - - elif glob.endswith('_'): - d['pre'] = glob.rstrip('_') - - else: - d['pre'] = glob - d['hasargs'] = False - - self.binds[glob] = d - echo("added bind: %r" % d) - - def set(self, key, value): '''Sets key "key" with value "value" in the uzbl instance.''' @@ -450,6 +459,11 @@ class UzblInstance: self.uzbl_socket = args self._flush() + elif event == 'SHUTDOWN': + for (name, plugin) in self.plugins.items(): + if hasattr(plugin, "cleanup"): + plugin.cleanup(uzbl) + self.dispatch_event(event, args) diff --git a/examples/data/uzbl/scripts/plugins/bind.py b/examples/data/uzbl/scripts/plugins/bind.py new file mode 100644 index 0000000..cf2a1ab --- /dev/null +++ b/examples/data/uzbl/scripts/plugins/bind.py @@ -0,0 +1,49 @@ +'''Plugin provides support for classic uzbl binds. + +For example: + bind ZZ = exit -> bind('ZZ', 'exit') + bind o _ = uri %s -> bind('o _', 'uri %s') + bind fl* = sh 'echo %s' -> bind('fl*', "sh 'echo %s'") + bind fl* = -> bind('fl*') + +And it is also possible to execute a function on activation: + bind('DD', myhandler) +''' + +uzbls = {} + +def export_bind(uzbl, glob, cmd=None): + + if uzbl not in uzbls: + uzbls[uzbl] = {} + binds = uzbls[uzbl] + + if not cmd: + if glob in binds.keys(): + echo("deleted bind: %r" % self.binds[glob]) + del binds[glob] + + d = {'glob': glob, 'once': True, 'hasargs': True, 'cmd': cmd} + + if glob.endswith('*'): + d['pre'] = glob.rstrip('*') + d['once'] = False + + elif glob.endswith('_'): + d['pre'] = glob.rstrip('_') + + else: + d['pre'] = glob + d['hasargs'] = False + + binds[glob] = d + print "added bind: %r" % d + + +def init(uzbl): + + uzbl.bind("test", lambda _: True) + +def cleanup(uzbl): + if uzbl in uzbls: + del uzbl |