[prev in list] [next in list] [prev in thread] [next in thread] 

List:       kde-commits
Subject:    [calligra/krita-scripting-rempt] krita/plugins/extensions/pykrita/src/krita: Add more of the initial
From:       Boudewijn Rempt <boud () valdyas ! org>
Date:       2014-07-29 14:03:44
Message-ID: E1XC80G-0003UD-C1 () scm ! kde ! org
[Download RAW message or body]

Git commit 3ea3219259e62887f664d568e69b87a8d9834abf by Boudewijn Rempt.
Committed on 29/07/2014 at 12:57.
Pushed by rempt into branch 'krita-scripting-rempt'.

Add more of the initializer stuff from pate

M  +3    -6    krita/plugins/extensions/pykrita/src/krita/__init__.py
A  +49   -0    krita/plugins/extensions/pykrita/src/krita/api.py
A  +142  -0    krita/plugins/extensions/pykrita/src/krita/configuration.py
A  +108  -0    krita/plugins/extensions/pykrita/src/krita/decorators.py

http://commits.kde.org/calligra/3ea3219259e62887f664d568e69b87a8d9834abf

diff --git a/krita/plugins/extensions/pykrita/src/krita/__init__.py \
b/krita/plugins/extensions/pykrita/src/krita/__init__.py index 1c9a9d5..b846e25 100644
--- a/krita/plugins/extensions/pykrita/src/krita/__init__.py
+++ b/krita/plugins/extensions/pykrita/src/krita/__init__.py
@@ -2,12 +2,9 @@ import pykrita
 import os
 import sys
 
-
-def pykritaEventHandler(event):
-    def _decorator(func):
-        setattr(pykrita, event, func)
-        del func
-    return _decorator
+from .api import *
+from .configuration import *
+from .decorators import *
 
 def kDebug(text):
     '''Use KDE way to show debug info
diff --git a/krita/plugins/extensions/pykrita/src/krita/api.py \
b/krita/plugins/extensions/pykrita/src/krita/api.py new file mode 100644
index 0000000..53bb8c4
--- /dev/null
+++ b/krita/plugins/extensions/pykrita/src/krita/api.py
@@ -0,0 +1,49 @@
+# -*- coding: utf-8 -*-
+# This file is part of Pate, Kate' Python scripting plugin.
+#
+# Copyright (C) 2006 Paul Giannaros <paul@giannaros.org>
+# Copyright (C) 2013 Shaheed Haque <srhaque@theiet.org>
+# Copyright (C) 2013 Alex Turbov <i.zaufi@gmail.com>
+#
+# This library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Library General Public
+# License as published by the Free Software Foundation; either
+# version 2 of the License, or (at your option) version 3.
+#
+# This library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# Library General Public License for more details.
+#
+# You should have received a copy of the GNU Library General Public License
+# along with this library; see the file COPYING.LIB.  If not, write to
+# the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+# Boston, MA 02110-1301, USA.
+
+'''Provide shortcuts to access kate internals from plugins'''
+
+import contextlib
+import os
+import sys
+
+import pykrita
+
+def objectIsAlive(obj):
+    ''' Test whether an object is alive; that is, whether the pointer
+    to the object still exists. '''
+    import sip
+    try:
+       sip.unwrapinstance(obj)
+    except RuntimeError:
+       return False
+    return True
+
+
+def kDebug(text):
+    '''Use KDE way to show debug info
+
+        TODO Add a way to control debug output from partucular plugins (?)
+    '''
+    plugin = sys._getframe(1).f_globals['__name__']
+    pate.kDebug('{}: {}'.format(plugin, text))
+
diff --git a/krita/plugins/extensions/pykrita/src/krita/configuration.py \
b/krita/plugins/extensions/pykrita/src/krita/configuration.py new file mode 100644
index 0000000..9e94abc
--- /dev/null
+++ b/krita/plugins/extensions/pykrita/src/krita/configuration.py
@@ -0,0 +1,142 @@
+# -*- coding: utf-8 -*-
+# Copyright (C) 2006 Paul Giannaros <paul@giannaros.org>
+# Copyright (C) 2013 Shaheed Haque <srhaque@theiet.org>
+# Copyright (C) 2013 Alex Turbov <i.zaufi@gmail.com>
+#
+# This library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Library General Public
+# License as published by the Free Software Foundation; either
+# version 2 of the License, or (at your option) version 3.
+#
+# This library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# Library General Public License for more details.
+#
+# You should have received a copy of the GNU Library General Public License
+# along with this library; see the file COPYING.LIB.  If not, write to
+# the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+# Boston, MA 02110-1301, USA.
+
+'''Configuration related stuff'''
+
+import pykrita                                                 # Built-in module
+import sys
+
+
+class Configuration:
+    '''A Configuration object provides a plugin-specific persistent
+    configuration dictionary. The configuration is saved and loaded from disk
+    automatically.
+
+    Do not instantiate your own Configuration object; a plugin simply uses
+    pykrita.configuration and the class automatically creates a plugin-specific
+    dictionary to support it.
+
+    Use a string key. Any Python type that can be pickled is can be used as a
+    value -- dictionaries, lists, numbers, strings, sets, and so on.
+    '''
+
+    def __init__(self, root):
+        self.root = root
+
+    def __getitem__(self, key):
+        plugin = sys._getframe(1).f_globals['__name__']
+        return self.root.get(plugin, {})[key]
+
+    def __setitem__(self, key, value):
+        plugin = sys._getframe(1).f_globals['__name__']
+        if plugin not in self.root:
+            self.root[plugin] = {}
+        self.root[plugin][key] = value
+
+    def __delitem__(self, key):
+        plugin = sys._getframe(1).f_globals['__name__']
+        del self.root.get(plugin, {})[key]
+
+    def __contains__(self, key):
+        plugin = sys._getframe(1).f_globals['__name__']
+        return key in self.root.get(plugin, {})
+
+    def __len__(self):
+        plugin = sys._getframe(1).f_globals['__name__']
+        return len(self.root.get(plugin, {}))
+
+    def __iter__(self):
+        plugin = sys._getframe(1).f_globals['__name__']
+        return iter(self.root.get(plugin, {}))
+
+    def __str__(self):
+        plugin = sys._getframe(1).f_globals['__name__']
+        return str(self.root.get(plugin, {}))
+
+    def __repr__(self):
+        plugin = sys._getframe(1).f_globals['__name__']
+        return repr(self.root.get(plugin, {}))
+
+    def keys(self):
+        '''Return the keys from the configuration dictionary.'''
+        plugin = sys._getframe(1).f_globals['__name__']
+        return self.root.get(plugin, {}).keys()
+
+    def values(self):
+        '''Return the values from the configuration dictionary.'''
+        plugin = sys._getframe(1).f_globals['__name__']
+        return self.root.get(plugin, {}).values()
+
+    def items(self):
+        '''Return the items from the configuration dictionary.'''
+        plugin = sys._getframe(1).f_globals['__name__']
+        return self.root.get(plugin, {}).items()
+
+    def get(self, key, default=None):
+        '''Fetch a configuration item using it's string key, returning
+        a given default if not found.
+
+        Parameters:
+            * key -             String key for item.
+            * default -         Value to return if key is not found.
+
+        Returns:
+            The item value for key, or the given default if not found.
+        '''
+        plugin = sys._getframe(1).f_globals['__name__']
+        try:
+            return self.root.get(plugin, {})[key]
+        except KeyError:
+            return default
+
+    def pop(self, key):
+        '''Delete a configuration item using it's string key.
+
+        Parameters:
+            * key -             String key for item.
+        Returns:
+            The value of the removed item.
+        Throws:
+            KeyError if key doesn't exist.
+        '''
+        plugin = sys._getframe(1).f_globals['__name__']
+        value = self.root.get(plugin, {})[key]
+        del self.root.get(plugin, {})[key]
+        return value
+
+    def save(self):
+        pykrita.saveConfiguration()
+
+    def _name(self):
+        return sys._getframe(1).f_globals['__name__']
+
+
+globalConfiguration = pykrita.configuration
+'''Configuration for all plugins.
+
+This can also be used by one plugin to access another plugin's configurations.
+'''
+
+configuration = Configuration(pykrita.configuration)
+'''Persistent configuration dictionary for this plugin.'''
+
+
+sessionConfiguration = Configuration(pykrita.sessionConfiguration)
+'''Per session persistent configuration dictionary for this plugin.'''
diff --git a/krita/plugins/extensions/pykrita/src/krita/decorators.py \
b/krita/plugins/extensions/pykrita/src/krita/decorators.py new file mode 100644
index 0000000..648d54b
--- /dev/null
+++ b/krita/plugins/extensions/pykrita/src/krita/decorators.py
@@ -0,0 +1,108 @@
+# -*- coding: utf-8 -*-
+# Copyright (C) 2006 Paul Giannaros <paul@giannaros.org>
+# Copyright (C) 2013 Shaheed Haque <srhaque@theiet.org>
+# Copyright (C) 2013 Alex Turbov <i.zaufi@gmail.com>
+#
+# This library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Library General Public
+# License as published by the Free Software Foundation; either
+# version 2 of the License, or (at your option) version 3.
+#
+# This library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# Library General Public License for more details.
+#
+# You should have received a copy of the GNU Library General Public License
+# along with this library; see the file COPYING.LIB.  If not, write to
+# the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+# Boston, MA 02110-1301, USA.
+
+'''Decorators used in plugins'''
+
+import functools
+import inspect
+import sys
+import traceback
+
+from PyQt4 import QtCore, QtGui
+
+import pykrita
+
+from .api import *
+
+#
+# initialization related stuff
+#
+
+def pykritaEventHandler(event):
+    def _decorator(func):
+        setattr(pykrita, event, func)
+        del func
+    return _decorator
+
+
+def _callAll(plugin, functions, *args, **kwargs):
+    if plugin in functions:
+        for f in functions[plugin]:
+            try:
+                f(*args, **kwargs)
+            except:
+                traceback.print_exc()
+                sys.stderr.write('\n')
+                # TODO Return smth to a caller, so in case of
+                # failed initialization it may report smth to the
+                # C++ level and latter can show an error to the user...
+                continue
+
+
+def _simpleEventListener(func):
+    # automates the most common decorator pattern: calling a bunch
+    # of functions when an event has occurred
+    func.functions = dict()
+    func.fire = functools.partial(_callAll, functions=func.functions)
+    func.clear = func.functions.clear
+    return func
+
+
+def _registerCallback(plugin, event, func):
+    if plugin not in event.functions:
+        event.functions[plugin] = set()
+
+    event.functions[plugin].add(func)
+    return func
+
+
+@_simpleEventListener
+def init(func):
+    ''' The function will be called when particular plugin has loaded
+        and the configuration has been initiated
+    '''
+    plugin = sys._getframe(1).f_globals['__name__']
+    kDebug('@init: {}/{}'.format(plugin, func.__name__))
+    return _registerCallback(plugin, init, func)
+
+
+@_simpleEventListener
+def unload(func):
+    ''' The function will be called when particular plugin is being
+        unloaded from memory. Clean up any widgets that you have added
+        to the interface (toolviews etc).
+
+        ATTENTION Be really careful trying to access any window, view
+            or document from the @unload handler: in case of application
+            quit everything is dead already!
+    '''
+    plugin = sys._getframe(1).f_globals['__name__']
+    kDebug('@unload: {}/{}'.format(plugin, func.__name__))
+    def _module_cleaner():
+        kDebug('@unload/cleaner: {}/{}'.format(plugin, func.__name__))
+        if plugin in init.functions:
+            kDebug('@unload/init-cleaner: {}/{}'.format(plugin, func.__name__))
+            del init.functions[plugin]
+
+        func()
+
+    return _registerCallback(plugin, unload, _module_cleaner)
+
+


[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic