gedit r6467 - in branches/new_plugins: . bindings/python gedit plugin-loaders/python plugin-loaders/python/bindings



Author: jessevdk
Date: Wed Aug 27 17:25:57 2008
New Revision: 6467
URL: http://svn.gnome.org/viewvc/gedit?rev=6467&view=rev

Log:
Added python plugin loader


Added:
   branches/new_plugins/plugin-loaders/python/Makefile.am
   branches/new_plugins/plugin-loaders/python/bindings/
      - copied from r6433, /branches/new_plugins/bindings/python/
   branches/new_plugins/plugin-loaders/python/bindings/Makefile.am
      - copied, changed from r6466, /branches/new_plugins/bindings/python/Makefile.am
   branches/new_plugins/plugin-loaders/python/bindings/gedit.defs
      - copied, changed from r6466, /branches/new_plugins/bindings/python/gedit.defs
   branches/new_plugins/plugin-loaders/python/bindings/gedit.override
      - copied, changed from r6466, /branches/new_plugins/bindings/python/gedit.override
   branches/new_plugins/plugin-loaders/python/bindings/geditmessage.override
   branches/new_plugins/plugin-loaders/python/bindings/geditplugin.override
   branches/new_plugins/plugin-loaders/python/gedit-plugin-loader-python.c
   branches/new_plugins/plugin-loaders/python/gedit-plugin-loader-python.h
   branches/new_plugins/plugin-loaders/python/gedit-plugin-python.c
   branches/new_plugins/plugin-loaders/python/gedit-plugin-python.h
   branches/new_plugins/plugin-loaders/python/pythonloader.gedit-plugin-loader.desktop.in
Removed:
   branches/new_plugins/bindings/python/
Modified:
   branches/new_plugins/Makefile.am
   branches/new_plugins/configure.ac
   branches/new_plugins/gedit/Makefile.am

Modified: branches/new_plugins/Makefile.am
==============================================================================
--- branches/new_plugins/Makefile.am	(original)
+++ branches/new_plugins/Makefile.am	Wed Aug 27 17:25:57 2008
@@ -1,7 +1,7 @@
 ## Process this file with automake to produce Makefile.in
 ACLOCAL_AMFLAGS = -I m4
 
-SUBDIRS = bindings gedit pixmaps po help data plugins docs
+SUBDIRS = plugin-loaders gedit pixmaps po help data plugins docs
 
 distuninstallcheck_listfiles = find . -type f -print | grep -v scrollkeeper
 

Modified: branches/new_plugins/configure.ac
==============================================================================
--- branches/new_plugins/configure.ac	(original)
+++ branches/new_plugins/configure.ac	Wed Aug 27 17:25:57 2008
@@ -353,8 +353,6 @@
 
 AC_CONFIG_FILES([
 Makefile
-bindings/Makefile
-bindings/python/Makefile
 data/gedit.desktop.in
 data/gedit-bugreport.sh
 data/gedit.pc
@@ -370,6 +368,8 @@
 pixmaps/Makefile
 plugin-loaders/Makefile
 plugin-loaders/c/Makefile
+plugin-loaders/python/Makefile
+plugin-loaders/python/bindings/Makefile
 plugins/changecase/Makefile
 plugins/docinfo/Makefile
 plugins/externaltools/Makefile

Modified: branches/new_plugins/gedit/Makefile.am
==============================================================================
--- branches/new_plugins/gedit/Makefile.am	(original)
+++ branches/new_plugins/gedit/Makefile.am	Wed Aug 27 17:25:57 2008
@@ -28,23 +28,21 @@
 	$(AM_CFLAGS)
 endif
 
-gedit_SOURCES = gedit.c
+gedit_SOURCES = \
+	gedit.c			\
+	gedit-message-bus.c	\
+	gedit-message.c
+
 gedit_LDADD = libgedit.la smclient/libeggsmclient.la $(GEDIT_LIBS)
 
 gedit_LDFLAGS = -export-dynamic -no-undefined -export-symbols-regex "^[[^_]].*"
 
-
 libgedit_la_LDFLAGS = -export-dynamic -no-undefined -export-symbols-regex "^[[^_]].*"
 
 libgedit_la_LIBADD =			\
 	$(GEDIT_LIBS)			\
 	dialogs/libdialogs.la
 
-if ENABLE_PYTHON
-libgedit_la_LIBADD += \
-	$(top_builddir)/bindings/python/gedit.la
-endif
-
 BUILT_SOURCES = 			\
 	gedit-enum-types.c		\
 	gedit-enum-types.h		\
@@ -79,12 +77,6 @@
 	gedittextregion.h		\
 	gedit-session.h
 
-# if ENABLE_PYTHON
-# NOINST_H_FILES += \
-#	gedit-python-module.h		\
-#	gedit-python-plugin.h 
-# endif
-
 INST_H_FILES =				\
 	gedit-app.h			\
 	gedit-convert.h			\
@@ -144,8 +136,6 @@
 	gedit-history-entry.c		\
 	gedit-io-error-message-area.c	\
 	gedit-language-manager.c	\
-	gedit-message.c			\
-	gedit-message-bus.c		\
 	gedit-message-area.c		\
 	gedit-metadata-manager.c	\
 	gedit-object-module.c		\
@@ -175,15 +165,6 @@
 	$(NOINST_H_FILES)		\
 	$(INST_H_FILES)
 
-
-# if ENABLE_PYTHON
-# libgedit_la_SOURCES += \
-#	gedit-python-module.c		\
-#	gedit-python-module.h		\
-#	gedit-python-plugin.c		\
-#	gedit-python-plugin.h	
-# endif
-
 gedit-enum-types.h: gedit-enum-types.h.template $(INST_H_FILES) $(GLIB_MKENUMS)
 	(cd $(srcdir) && $(GLIB_MKENUMS) --template gedit-enum-types.h.template $(INST_H_FILES)) > $@
 	

Added: branches/new_plugins/plugin-loaders/python/Makefile.am
==============================================================================
--- (empty file)
+++ branches/new_plugins/plugin-loaders/python/Makefile.am	Wed Aug 27 17:25:57 2008
@@ -0,0 +1,48 @@
+# C plugin loader
+
+SUBDIRS = bindings
+loaderdir = $(libdir)/gedit-2/plugin-loaders
+
+INCLUDES = \
+	-I$(top_srcdir) 						\
+	-I$(top_builddir)						\
+	-I$(top_srcdir)/gedit						\
+	-I$(top_builddir)/gedit						\
+	$(GEDIT_CFLAGS) 						\
+	$(WARN_CFLAGS)							\
+	$(DISABLE_DEPRECATED_CFLAGS)					\
+	$(PYGTK_CFLAGS)							\
+	$(PYTHON_CFLAGS)						\
+	-DGEDIT_LOCALEDIR=\""$(prefix)/$(DATADIRNAME)/locale"\"
+
+loader_LTLIBRARIES = libpythonloader.la
+
+
+NOINST_H_FILES = \
+	gedit-plugin-loader-python.h	\
+	gedit-plugin-python.h
+
+libpythonloader_la_SOURCES = \
+	gedit-plugin-loader-python.c 	\
+	gedit-plugin-python.c
+	$(NOINST_H_FILES)
+
+libpythonloader_la_LDFLAGS = $(LOADER_LIBTOOL_FLAGS)
+libpythonloader_la_LIBADD = \
+	$(GEDIT_LIBS) 			\
+	$(srcdir)/bindings/gedit.la
+
+loader_in_files = pythonloader.gedit-plugin-loader.desktop.in
+
+%.gedit-plugin-loader: %.gedit-plugin-loader.desktop.in $(INTLTOOL_MERGE) $(wildcard $(top_srcdir)/po/*po) ; $(INTLTOOL_MERGE) $(top_srcdir)/po $< $@ -d -u -c $(top_builddir)/po/.intltool-merge-cache
+
+loader_DATA = $(loader_in_files:.gedit-plugin-loader.desktop.in=.gedit-plugin-loader)
+
+EXTRA_DIST = \
+	$(loader_in_files)
+
+CLEANFILES = \
+	$(loader_DATA)
+
+DISTCLEANFILES = \
+	$(loader_DATA)

Copied: branches/new_plugins/plugin-loaders/python/bindings/Makefile.am (from r6466, /branches/new_plugins/bindings/python/Makefile.am)
==============================================================================
--- /branches/new_plugins/bindings/python/Makefile.am	(original)
+++ branches/new_plugins/plugin-loaders/python/bindings/Makefile.am	Wed Aug 27 17:25:57 2008
@@ -18,20 +18,22 @@
 	$(PYGTK_LIBS)
 
 gedit_la_CFLAGS = \
-	-I$(top_srcdir)			\
-	-I$(top_builddir)		\
-	-I$(top_srcdir)/gedit		\
-	-I$(top_builddir)/gedit		\
-	$(GEDIT_CFLAGS)			\
-	$(NO_STRICT_ALIASING_CFLAGS)	\
-	$(PYGTK_CFLAGS)			\
-	$(PYTHON_CFLAGS)		\
+	-I$(top_srcdir)					\
+	-I$(top_builddir)				\
+	-I$(top_srcdir)/gedit				\
+	-I$(top_builddir)/gedit				\
+	-I$(top_srcdir)/plugin-loaders/python	\
+	-I$(top_builddir)/plugin-loaders/python	\
+	$(GEDIT_CFLAGS)					\
+	$(NO_STRICT_ALIASING_CFLAGS)			\
+	$(PYGTK_CFLAGS)					\
+	$(PYTHON_CFLAGS)				\
 	$(AM_CFLAGS)
 
 $(top_builddir)/gedit/gedit-enum-types.h:
 	cd $(top_builddir)/gedit && $(MAKE) gedit-enum-types.h
 
-gedit.c: gedit.defs gedit.override $(top_builddir)/gedit/gedit-enum-types.h
+gedit.c: gedit.defs gedit.override geditplugin.override geditmessage.override $(top_builddir)/gedit/gedit-enum-types.h
 	( cd $(srcdir) && $(PYGTK_CODEGEN) \
 		--register $(PYGTK_DEFSDIR)/pango-types.defs \
 		--register $(PYGTK_DEFSDIR)/gdk-types.defs \
@@ -57,6 +59,7 @@
 	gedit/gedit-document.h		\
 	gedit/gedit-encodings.h		\
 	gedit/gedit-plugin.h		\
+	$(srcdir)/../gedit-plugin-python.h \
 	gedit/gedit-view.h		\
 	gedit/gedit-statusbar.h		\
 	gedit/gedit-tab.h 		\

Copied: branches/new_plugins/plugin-loaders/python/bindings/gedit.defs (from r6466, /branches/new_plugins/bindings/python/gedit.defs)
==============================================================================
--- /branches/new_plugins/bindings/python/gedit.defs	(original)
+++ branches/new_plugins/plugin-loaders/python/bindings/gedit.defs	Wed Aug 27 17:25:57 2008
@@ -35,13 +35,20 @@
   (gtype-id "GEDIT_TYPE_PANEL")
 )
 
-(define-object Plugin
+(define-object __Plugin
   (in-module "Gedit")
   (parent "GObject")
   (c-name "GeditPlugin")
   (gtype-id "GEDIT_TYPE_PLUGIN")
 )
 
+(define-object Plugin
+  (in-module "Gedit")
+  (parent "GeditPlugin")
+  (c-name "GeditPluginPython")
+  (gtype-id "GEDIT_TYPE_PLUGIN_PYTHON")
+)
+
 (define-object Statusbar
   (in-module "Gedit")
   (parent "GtkStatusbar")
@@ -669,6 +676,19 @@
   (return-type "GtkWidget*")
 )
 
+;; From ../gedit/gedit-plugin-python.h
+
+(define-function gedit_plugin_python_get_type
+  (c-name "gedit_plugin_python_get_type")
+  (return-type "GType")
+)
+
+(define-function gedit_plugin_python_new
+  (c-name "gedit_plugin_python_new")
+  (is-constructor-of "GeditPluginPython")
+  (return-type "GObject*")
+)
+
 ;; From ../../gedit/gedit-status-bar.h
 
 (define-method flash_message
@@ -993,8 +1013,8 @@
   (return-type "GType")
 )
 
-(define-function message_bus_get
-  (c-name "gedit_message_bus_get")
+(define-function message_bus_get_default
+  (c-name "gedit_message_bus_get_default")
   (return-type "GeditMessageBus*")
 )
 

Copied: branches/new_plugins/plugin-loaders/python/bindings/gedit.override (from r6466, /branches/new_plugins/bindings/python/gedit.override)
==============================================================================
--- /branches/new_plugins/bindings/python/gedit.override	(original)
+++ branches/new_plugins/plugin-loaders/python/bindings/gedit.override	Wed Aug 27 17:25:57 2008
@@ -4,15 +4,15 @@
 #include "pygobject.h"
 #include <pygtk/pygtk.h>
 
-#include "gedit-language-manager.h"
-#include "gedit-plugin.h"
-#include "gedit-app.h"
-#include "gedit-encodings.h"
-#include "gedit-enum-types.h"
-#include "gedit-statusbar.h"
-#include "gedit-debug.h"
-#include "gedit-message-bus.h"
-#include "gedit-message.h"
+#include <gedit/gedit-language-manager.h>
+#include <gedit/gedit-plugin.h>
+#include <gedit/gedit-app.h>
+#include <gedit/gedit-encodings.h>
+#include <gedit/gedit-enum-types.h>
+#include <gedit/gedit-statusbar.h>
+#include <gedit/gedit-debug.h>
+
+#include "gedit-plugin-python.h"
 
 void pygedit_register_classes (PyObject *d); 
 void pygedit_add_constants (PyObject *module, const gchar *strip_prefix);
@@ -60,222 +60,10 @@
     }
     return py_list;
 }
-
-static int
-_helper_wrap_message_types(PyObject *args, const gchar ***keys, GType **types, gint *num, gboolean direct)
-{
-    guint len, i, pos;
-    
-    len = PyTuple_Size(args);
-
-    if (len == 1 && PyDict_Check(PyTuple_GetItem(args, 0)))
-    {
-    	/* get key -> gtype from mapping */
-    	PyObject *dict = PyTuple_GetItem(args, 0);
-    	PyObject *key;
-    	PyObject *value;
-
-    	*num = PyDict_Size(dict);
-    	*types = g_new(GType, *num);
-        *keys = g_new(const gchar *, *num);
-        pos = 0;
-        i = 0;
-        
-        while (PyDict_Next(dict, &pos, &key, &value)) {
-            *keys[i] = PyString_AsString(key);
-            
-            if (direct) {
-                *types[i] = pyg_type_from_object(value);
-            } else {
-                PyObject *pytype = PyObject_Type(value);
-                *types[i] = pytype ? pyg_type_from_object(pytype) : 0;
-                Py_DECREF(pytype);
-            }
-            
-            if (*types[i] == 0 || *keys[i] == NULL) {
-                g_free(*types);
-                g_free(*keys);
-                return 0;
-            }
-            
-            i++;
-        }
-    }
-    else
-    {
-        if (len % 2 != 0) {
-            PyErr_SetString(PyExc_TypeError,
-                            "Even number of arguments expected (name/type pairs)");
-            return 0;
-        }
-
-        *num = len / 2;
-        *types = g_new(GType, *num);
-        *keys = g_new(const gchar *, *num);
-
-        for (i = 0; i < *num; i++) {
-            PyObject *key = PyTuple_GetItem(args, i * 2);
-            PyObject *value = PyTuple_GetItem(args, i * 2 + 1);
-    
-            *keys[i] = PyString_AsString(key);
-            
-            if (direct) {
-                *types[i] = pyg_type_from_object(value);
-            } else {
-                PyObject *pytype = PyObject_Type(value);
-                *types[i] = pytype ? pyg_type_from_object(pytype) : 0;
-                Py_DECREF(pytype);
-            }
-
-            if (*types[i] == 0 || *keys[i] == NULL) {
-                g_free(*types);
-                g_free(*keys);
-                return 0;
-            }
-        }
-    }
-    
-    return 1;
-}
-
-static int
-_helper_wrap_message_set_value(GeditMessage *message, PyObject *pykey, PyObject *pyvalue)
-{
-    const gchar *key;
-    GType gtype;
-    GValue value = {0,};
-
-    key = PyString_AsString(pykey);
-    
-    if (key == NULL)
-        return 0;
-
-    gtype = gedit_message_get_key_type(message, key);
-    
-    if (gtype == 0) {
-        PyErr_SetString(PyExc_TypeError, "invalid key");
-        return 0;
-    }
-
-    g_value_init(&value, gtype);
-    
-    if (pyg_value_from_pyobject(&value, pyvalue)) {
-        PyErr_SetString(PyExc_TypeError,
-                        "value is of the wrong type for this key");
-        return 0;
-    }
-
-    gedit_message_set_value(message, key, &value);
-    g_value_unset(&value);
-    
-    return 1;
-}
-
-static int
-_helper_wrap_message_set_values(GeditMessage *message, PyObject *args)
-{
-    guint len, i;
-    
-    len = PyTuple_Size(args);
-
-    if (len == 1 && PyDict_Check(PyTuple_GetItem(args, 0)))
-    {
-    	/* do key -> value from mapping */
-    	PyObject *dict = PyTuple_GetItem(args, 0);
-    	PyObject *pykey, *pyvalue;
-    	
-    	i = 0;
-
-        while (PyDict_Next(dict, &i, &pykey, &pyvalue)) {
-            if (!_helper_wrap_message_set_value(message, pykey, pyvalue))
-                return 0;
-        }
-    } else {
-        if (len % 2 != 0) {
-            PyErr_SetString(PyExc_TypeError,
-                            "Even number of arguments expected (name/type pairs)");
-            return 0;
-        }
-
-        for (i = 0; i < len / 2; i++) {
-            PyObject *pykey = PyTuple_GetItem(args, i * 2);
-            PyObject *pyvalue = PyTuple_GetItem(args, i * 2 + 1);
-            
-            if (!_helper_wrap_message_set_value(message, pykey, pyvalue))
-                return 0;
-        }
-    }
-    
-    return 1;
-}
-
-static GeditMessage *
-_helper_wrap_create_message(PyObject *args)
-{
-    guint len, num;
-    const gchar *domain;
-    const gchar *name;
-    GType *types;
-    const gchar **keys;
-    PyObject *slice;
-    GeditMessage *message;
-
-    len = PyTuple_Size(args);
-
-    if (len < 2) {
-        PyErr_SetString(PyExc_TypeError,
-                        "GeditMessage requires at least two arguments");
-        return NULL;
-    }
-    
-    domain = PyString_AsString(PyTuple_GetItem(args, 0));
-    name = PyString_AsString(PyTuple_GetItem(args, 1));
-    
-    if (!domain || !name) {
-        PyErr_SetString(PyExc_TypeError,
-                        "First two arguments need to be strings");
-        return NULL;
-    }
-    
-    slice = PyTuple_GetSlice (args, 2, len);
-
-    if (!_helper_wrap_message_types (slice, &keys, &types, &num, FALSE)) {
-        Py_DECREF(slice);
-    	return NULL;
-    }
-
-    message = g_object_new(GEDIT_TYPE_MESSAGE, "domain", domain, "name", name, NULL);
-    gedit_message_set_types (message, keys, types, num);
-
-    g_free(types);
-    g_free(keys);
-    
-    _helper_wrap_message_set_values(message, slice);
-    Py_DECREF(slice);
-
-    return message;
-}
-
-typedef struct {
-    PyObject *func;
-    PyObject *data;
-} PyGeditCustomNotify;
-
-static void 
-pygedit_custom_destroy_notify(gpointer user_data)
-{
-    PyGeditCustomNotify *cunote = user_data;
-    PyGILState_STATE state;
-    
-    g_return_if_fail(user_data);
-    state = pyg_gil_state_ensure();
-    Py_XDECREF(cunote->func);
-    Py_XDECREF(cunote->data);
-    pyg_gil_state_release(state);
-    
-    g_free(cunote);
-}
-
+%%
+include
+  geditmessage.override
+  geditplugin.override
 %%
 modulename gedit 
 %%
@@ -295,13 +83,6 @@
   *_get_type
   gedit_document_error_quark
   gedit_panel_add_item_with_stock_icon
-  gedit_message_new_valist
-  gedit_message_get_valist
-  gedit_message_set_valist
-  gedit_message_set_valuesv
-  gedit_message_bus_disconnect_by_func
-  gedit_message_bus_block_by_func
-  gedit_message_bus_unblock_by_func
 %%
 override gedit_app_create_window kwargs
 static PyObject *
@@ -660,220 +441,3 @@
     return Py_None;
 }
 %%
-override gedit_message_new
-static int
-_wrap_gedit_message_new(PyGObject *self, PyObject *args)
-{
-    self->obj = (GObject *)_helper_wrap_create_message(args);
-    
-    if (!self->obj) {
-        PyErr_SetString(PyExc_RuntimeError,
-                        "could not create GeditMessage object");
-        return -1;
-    }
-    pygobject_register_wrapper((PyObject *)self);
-
-    return 0;
-}
-%%
-override gedit_message_set_types args
-static PyObject *
-_wrap_gedit_message_set_types(PyGObject *self, PyObject *args)
-{
-    guint num;
-    GType *types;
-    const gchar **keys;
-
-    if (!_helper_wrap_message_types (args, &keys, &types, &num, TRUE)) {
-    	return NULL;
-    }
- 
-    gedit_message_set_types (GEDIT_MESSAGE(self->obj), keys, types, num);
-
-    g_free(types);
-    g_free(keys);
-
-    Py_INCREF (Py_None);
-    return Py_None;
-}
-%%
-override gedit_message_get args
-static PyObject *
-_wrap_gedit_message_get(PyGObject *self, PyObject *args)
-{
-    guint len, i;
-    PyObject *ret;
-
-    len = PyTuple_Size(args);
-    
-    ret = PyTuple_New(len);
-    
-    for (i = 0; i < len; i++) {
-        GValue value = { 0, };
-        PyObject *py_key = PyTuple_GetItem(args, i);
-        const gchar *key;
-        
-        if (!PyString_Check(py_key)) {
-	    PyErr_SetString(PyExc_TypeError, "keys must be strings");
-	    Py_DECREF(ret);
-	    return NULL;
-	}
-	
-	key = PyString_AsString(py_key);
-	gedit_message_get_value (GEDIT_MESSAGE (self->obj), key, &value);
-	
-	PyTuple_SetItem(ret, i, pyg_value_as_pyobject(&value, TRUE));
-	g_value_unset(&value);
-    }
-    
-    return ret;
-}
-%%
-override gedit_message_get_value kwargs
-static PyObject *
-_wrap_gedit_message_get_value(PyGObject *self, PyObject *args, PyObject *kwargs)
-{
-    static char *kwlist[] = { "key", NULL };
-    const gchar *key;
-    PyObject *ret;
-    GValue value = { 0, };
-    
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s:GeditMessage.get_value", kwlist, &key))
-        return NULL;
-
-    gedit_message_get_value(GEDIT_MESSAGE(self->obj), key, &value);
-    ret = pyg_value_as_pyobject(&value, TRUE);
-    g_value_unset(&value);
-    
-    return ret;
-}
-%%
-override gedit_message_set_value kwargs
-static PyObject *
-_wrap_gedit_message_set_value(PyGObject *self, PyObject *args, PyObject *kwargs)
-{
-    static char *kwlist[] = { "key", "value", NULL };
-    PyObject *ret, *pykey, *pyvalue;
-    GValue value = { 0, };
-    GType gtype;
-    
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO:GeditMessage.set_value", kwlist, &pykey, &pyvalue))
-        return NULL;
-    
-    if (!_helper_wrap_message_set_value(GEDIT_MESSAGE(self->obj), pykey, pyvalue))
-        return NULL;
-    
-    Py_INCREF(Py_None);
-    return Py_None;
-}
-%%
-override gedit_message_set args
-static PyObject *
-_wrap_gedit_message_set (PyGObject *self, PyObject *args) {
-    if (!_helper_wrap_message_set_values(GEDIT_MESSAGE(self->obj), args))
-        return NULL;
-    
-    Py_INCREF(Py_None);
-    return Py_None;
-}
-%%
-override gedit_message_bus_connect kwargs
-static void
-pygedit_message_bus_connect_cb(GeditMessageBus *bus, GeditMessage *message, gpointer data)
-{
-    PyGILState_STATE state;
-    PyGeditCustomNotify *cunote = data;
-    PyObject *pybus, *pymessage, *retobj;
-    gboolean ret = FALSE;
-
-    g_assert(cunote->func);
-
-    state = pyg_gil_state_ensure();
-
-    pybus = pygobject_new((GObject *)bus);
-    pymessage = pygobject_new((GObject *)message);
-
-    if (cunote->data) {
-        retobj = PyEval_CallFunction(cunote->func, "(NNO)", pybus, pymessage, cunote->data);
-    } else {
-        retobj = PyEval_CallFunction(cunote->func, "(NN)", pybus, pymessage);
-    }
-
-    if (PyErr_Occurred()) {
-        PyErr_Print();
-    }
-
-    Py_XDECREF(retobj);
-
-    pyg_gil_state_release(state);
-}
-
-static PyObject *
-_wrap_gedit_message_bus_connect(PyGObject *self, PyObject *args, PyObject *kwargs) 
-{
-    static char *kwlist[] = { "domain", "name", "func", "data", NULL };
-    PyObject *pyfunc, *pyarg = NULL;
-    const gchar *domain;
-    const gchar *name;
-    PyGeditCustomNotify *cunote;
-
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
-				     "ssO|O:GeditMessageBus.connect",
-				     kwlist, &domain, &name, &pyfunc, &pyarg))
-        return NULL;
-
-    if (!PyCallable_Check(pyfunc)) {
-        PyErr_SetString(PyExc_TypeError, "func must be a callable object");
-        return NULL;
-    }
-    cunote = g_new(PyGeditCustomNotify, 1);
-    Py_INCREF(pyfunc);
-    cunote->func = pyfunc;
-    Py_XINCREF(pyarg);
-    cunote->data = pyarg;
-
-    gedit_message_bus_connect(GEDIT_MESSAGE_BUS(self->obj),
-                              domain,
-                              name,
-                              pygedit_message_bus_connect_cb,
-                              (gpointer)cunote,
-                              pygedit_custom_destroy_notify);
-    Py_INCREF(Py_None);
-    return Py_None;
-}
-%%
-override gedit_message_bus_send args
-static PyObject *
-_wrap_gedit_message_bus_send (PyGObject *self, PyObject *args)
-{
-    /* create a new message object */
-    GeditMessage *message;
-    
-    message = _helper_wrap_create_message(args);
-    
-    if (!message)
-        return NULL;
-    
-    gedit_message_bus_send_message(GEDIT_MESSAGE_BUS(self->obj), message);
-    g_object_unref (message);
-    
-    Py_INCREF(Py_None);
-    return Py_None;
-}
-%%
-override gedit_message_bus_send_sync args
-static PyObject *
-_wrap_gedit_message_bus_send_sync (PyGObject *self, PyObject *args)
-{
-    /* create a new message object */
-    GeditMessage *message;
-    
-    message = _helper_wrap_create_message(args);
-    
-    if (!message)
-        return NULL;
-    
-    gedit_message_bus_send_message_sync(GEDIT_MESSAGE_BUS(self->obj), message);
-    return pygobject_new((GObject *)message);
-}
-%%

Added: branches/new_plugins/plugin-loaders/python/bindings/geditmessage.override
==============================================================================
--- (empty file)
+++ branches/new_plugins/plugin-loaders/python/bindings/geditmessage.override	Wed Aug 27 17:25:57 2008
@@ -0,0 +1,448 @@
+%%
+headers
+
+#include <gedit/gedit-message-bus.h>
+#include <gedit/gedit-message.h>
+
+static int
+_helper_wrap_message_types(PyObject *args, const gchar ***keys, GType **types, gint *num, gboolean direct)
+{
+    guint len, i, pos;
+    
+    len = PyTuple_Size(args);
+
+    if (len == 1 && PyDict_Check(PyTuple_GetItem(args, 0)))
+    {
+    	/* get key -> gtype from mapping */
+    	PyObject *dict = PyTuple_GetItem(args, 0);
+    	PyObject *key;
+    	PyObject *value;
+
+    	*num = PyDict_Size(dict);
+    	*types = g_new(GType, *num);
+        *keys = g_new(const gchar *, *num);
+        pos = 0;
+        i = 0;
+        
+        while (PyDict_Next(dict, &pos, &key, &value)) {
+            *keys[i] = PyString_AsString(key);
+            
+            if (direct) {
+                *types[i] = pyg_type_from_object(value);
+            } else {
+                PyObject *pytype = PyObject_Type(value);
+                *types[i] = pytype ? pyg_type_from_object(pytype) : 0;
+                Py_DECREF(pytype);
+            }
+            
+            if (*types[i] == 0 || *keys[i] == NULL) {
+                g_free(*types);
+                g_free(*keys);
+                return 0;
+            }
+            
+            i++;
+        }
+    }
+    else
+    {
+        if (len % 2 != 0) {
+            PyErr_SetString(PyExc_TypeError,
+                            "Even number of arguments expected (name/type pairs)");
+            return 0;
+        }
+
+        *num = len / 2;
+        *types = g_new(GType, *num);
+        *keys = g_new(const gchar *, *num);
+
+        for (i = 0; i < *num; i++) {
+            PyObject *key = PyTuple_GetItem(args, i * 2);
+            PyObject *value = PyTuple_GetItem(args, i * 2 + 1);
+    
+            *keys[i] = PyString_AsString(key);
+            
+            if (direct) {
+                *types[i] = pyg_type_from_object(value);
+            } else {
+                PyObject *pytype = PyObject_Type(value);
+                *types[i] = pytype ? pyg_type_from_object(pytype) : 0;
+                Py_DECREF(pytype);
+            }
+
+            if (*types[i] == 0 || *keys[i] == NULL) {
+                g_free(*types);
+                g_free(*keys);
+                return 0;
+            }
+        }
+    }
+    
+    return 1;
+}
+
+static int
+_helper_wrap_message_set_value(GeditMessage *message, PyObject *pykey, PyObject *pyvalue)
+{
+    const gchar *key;
+    GType gtype;
+    GValue value = {0,};
+
+    key = PyString_AsString(pykey);
+    
+    if (key == NULL)
+        return 0;
+
+    gtype = gedit_message_get_key_type(message, key);
+    
+    if (gtype == 0) {
+        PyErr_SetString(PyExc_TypeError, "invalid key");
+        return 0;
+    }
+
+    g_value_init(&value, gtype);
+    
+    if (pyg_value_from_pyobject(&value, pyvalue)) {
+        PyErr_SetString(PyExc_TypeError,
+                        "value is of the wrong type for this key");
+        return 0;
+    }
+
+    gedit_message_set_value(message, key, &value);
+    g_value_unset(&value);
+    
+    return 1;
+}
+
+static int
+_helper_wrap_message_set_values(GeditMessage *message, PyObject *args)
+{
+    guint len, i;
+    
+    len = PyTuple_Size(args);
+
+    if (len == 1 && PyDict_Check(PyTuple_GetItem(args, 0)))
+    {
+    	/* do key -> value from mapping */
+    	PyObject *dict = PyTuple_GetItem(args, 0);
+    	PyObject *pykey, *pyvalue;
+    	
+    	i = 0;
+
+        while (PyDict_Next(dict, &i, &pykey, &pyvalue)) {
+            if (!_helper_wrap_message_set_value(message, pykey, pyvalue))
+                return 0;
+        }
+    } else {
+        if (len % 2 != 0) {
+            PyErr_SetString(PyExc_TypeError,
+                            "Even number of arguments expected (name/type pairs)");
+            return 0;
+        }
+
+        for (i = 0; i < len / 2; i++) {
+            PyObject *pykey = PyTuple_GetItem(args, i * 2);
+            PyObject *pyvalue = PyTuple_GetItem(args, i * 2 + 1);
+            
+            if (!_helper_wrap_message_set_value(message, pykey, pyvalue))
+                return 0;
+        }
+    }
+    
+    return 1;
+}
+
+static GeditMessage *
+_helper_wrap_create_message(PyObject *args)
+{
+    guint len, num;
+    const gchar *domain;
+    const gchar *name;
+    GType *types;
+    const gchar **keys;
+    PyObject *slice;
+    GeditMessage *message;
+
+    len = PyTuple_Size(args);
+
+    if (len < 2) {
+        PyErr_SetString(PyExc_TypeError,
+                        "GeditMessage requires at least two arguments");
+        return NULL;
+    }
+    
+    domain = PyString_AsString(PyTuple_GetItem(args, 0));
+    name = PyString_AsString(PyTuple_GetItem(args, 1));
+    
+    if (!domain || !name) {
+        PyErr_SetString(PyExc_TypeError,
+                        "First two arguments need to be strings");
+        return NULL;
+    }
+    
+    slice = PyTuple_GetSlice (args, 2, len);
+
+    if (!_helper_wrap_message_types (slice, &keys, &types, &num, FALSE)) {
+        Py_DECREF(slice);
+    	return NULL;
+    }
+
+    message = g_object_new(GEDIT_TYPE_MESSAGE, "domain", domain, "name", name, NULL);
+    gedit_message_set_types (message, keys, types, num);
+
+    g_free(types);
+    g_free(keys);
+    
+    _helper_wrap_message_set_values(message, slice);
+    Py_DECREF(slice);
+
+    return message;
+}
+
+typedef struct {
+    PyObject *func;
+    PyObject *data;
+} PyGeditCustomNotify;
+
+static void 
+pygedit_custom_destroy_notify(gpointer user_data)
+{
+    PyGeditCustomNotify *cunote = user_data;
+    PyGILState_STATE state;
+    
+    g_return_if_fail(user_data);
+    state = pyg_gil_state_ensure();
+    Py_XDECREF(cunote->func);
+    Py_XDECREF(cunote->data);
+    pyg_gil_state_release(state);
+    
+    g_free(cunote);
+}
+%%
+ignore-glob
+  *_get_type
+  gedit_message_new_valist
+  gedit_message_get_valist
+  gedit_message_set_valist
+  gedit_message_set_valuesv
+  gedit_message_bus_disconnect_by_func
+  gedit_message_bus_block_by_func
+  gedit_message_bus_unblock_by_func
+%%
+override gedit_message_new
+static int
+_wrap_gedit_message_new(PyGObject *self, PyObject *args)
+{
+    self->obj = (GObject *)_helper_wrap_create_message(args);
+    
+    if (!self->obj) {
+        PyErr_SetString(PyExc_RuntimeError,
+                        "could not create GeditMessage object");
+        return -1;
+    }
+    pygobject_register_wrapper((PyObject *)self);
+
+    return 0;
+}
+%%
+override gedit_message_set_types args
+static PyObject *
+_wrap_gedit_message_set_types(PyGObject *self, PyObject *args)
+{
+    guint num;
+    GType *types;
+    const gchar **keys;
+
+    if (!_helper_wrap_message_types (args, &keys, &types, &num, TRUE)) {
+    	return NULL;
+    }
+ 
+    gedit_message_set_types (GEDIT_MESSAGE(self->obj), keys, types, num);
+
+    g_free(types);
+    g_free(keys);
+
+    Py_INCREF (Py_None);
+    return Py_None;
+}
+%%
+override gedit_message_get args
+static PyObject *
+_wrap_gedit_message_get(PyGObject *self, PyObject *args)
+{
+    guint len, i;
+    PyObject *ret;
+
+    len = PyTuple_Size(args);
+    
+    ret = PyTuple_New(len);
+    
+    for (i = 0; i < len; i++) {
+        GValue value = { 0, };
+        PyObject *py_key = PyTuple_GetItem(args, i);
+        const gchar *key;
+        
+        if (!PyString_Check(py_key)) {
+	    PyErr_SetString(PyExc_TypeError, "keys must be strings");
+	    Py_DECREF(ret);
+	    return NULL;
+	}
+	
+	key = PyString_AsString(py_key);
+	gedit_message_get_value (GEDIT_MESSAGE (self->obj), key, &value);
+	
+	PyTuple_SetItem(ret, i, pyg_value_as_pyobject(&value, TRUE));
+	g_value_unset(&value);
+    }
+    
+    return ret;
+}
+%%
+override gedit_message_get_value kwargs
+static PyObject *
+_wrap_gedit_message_get_value(PyGObject *self, PyObject *args, PyObject *kwargs)
+{
+    static char *kwlist[] = { "key", NULL };
+    const gchar *key;
+    PyObject *ret;
+    GValue value = { 0, };
+    
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s:GeditMessage.get_value", kwlist, &key))
+        return NULL;
+
+    gedit_message_get_value(GEDIT_MESSAGE(self->obj), key, &value);
+    ret = pyg_value_as_pyobject(&value, TRUE);
+    g_value_unset(&value);
+    
+    return ret;
+}
+%%
+override gedit_message_set_value kwargs
+static PyObject *
+_wrap_gedit_message_set_value(PyGObject *self, PyObject *args, PyObject *kwargs)
+{
+    static char *kwlist[] = { "key", "value", NULL };
+    PyObject *ret, *pykey, *pyvalue;
+    GValue value = { 0, };
+    GType gtype;
+    
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO:GeditMessage.set_value", kwlist, &pykey, &pyvalue))
+        return NULL;
+    
+    if (!_helper_wrap_message_set_value(GEDIT_MESSAGE(self->obj), pykey, pyvalue))
+        return NULL;
+    
+    Py_INCREF(Py_None);
+    return Py_None;
+}
+%%
+override gedit_message_set args
+static PyObject *
+_wrap_gedit_message_set (PyGObject *self, PyObject *args) {
+    if (!_helper_wrap_message_set_values(GEDIT_MESSAGE(self->obj), args))
+        return NULL;
+    
+    Py_INCREF(Py_None);
+    return Py_None;
+}
+%%
+override gedit_message_bus_connect kwargs
+static void
+pygedit_message_bus_connect_cb(GeditMessageBus *bus, GeditMessage *message, gpointer data)
+{
+    PyGILState_STATE state;
+    PyGeditCustomNotify *cunote = data;
+    PyObject *pybus, *pymessage, *retobj;
+    gboolean ret = FALSE;
+
+    g_assert(cunote->func);
+
+    state = pyg_gil_state_ensure();
+
+    pybus = pygobject_new((GObject *)bus);
+    pymessage = pygobject_new((GObject *)message);
+
+    if (cunote->data) {
+        retobj = PyEval_CallFunction(cunote->func, "(NNO)", pybus, pymessage, cunote->data);
+    } else {
+        retobj = PyEval_CallFunction(cunote->func, "(NN)", pybus, pymessage);
+    }
+
+    if (PyErr_Occurred()) {
+        PyErr_Print();
+    }
+
+    Py_XDECREF(retobj);
+
+    pyg_gil_state_release(state);
+}
+
+static PyObject *
+_wrap_gedit_message_bus_connect(PyGObject *self, PyObject *args, PyObject *kwargs) 
+{
+    static char *kwlist[] = { "domain", "name", "func", "data", NULL };
+    PyObject *pyfunc, *pyarg = NULL;
+    const gchar *domain;
+    const gchar *name;
+    PyGeditCustomNotify *cunote;
+
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
+				     "ssO|O:GeditMessageBus.connect",
+				     kwlist, &domain, &name, &pyfunc, &pyarg))
+        return NULL;
+
+    if (!PyCallable_Check(pyfunc)) {
+        PyErr_SetString(PyExc_TypeError, "func must be a callable object");
+        return NULL;
+    }
+    cunote = g_new(PyGeditCustomNotify, 1);
+    Py_INCREF(pyfunc);
+    cunote->func = pyfunc;
+    Py_XINCREF(pyarg);
+    cunote->data = pyarg;
+
+    gedit_message_bus_connect(GEDIT_MESSAGE_BUS(self->obj),
+                              domain,
+                              name,
+                              pygedit_message_bus_connect_cb,
+                              (gpointer)cunote,
+                              pygedit_custom_destroy_notify);
+    Py_INCREF(Py_None);
+    return Py_None;
+}
+%%
+override gedit_message_bus_send args
+static PyObject *
+_wrap_gedit_message_bus_send (PyGObject *self, PyObject *args)
+{
+    /* create a new message object */
+    GeditMessage *message;
+    
+    message = _helper_wrap_create_message(args);
+    
+    if (!message)
+        return NULL;
+    
+    gedit_message_bus_send_message(GEDIT_MESSAGE_BUS(self->obj), message);
+    g_object_unref (message);
+    
+    Py_INCREF(Py_None);
+    return Py_None;
+}
+%%
+override gedit_message_bus_send_sync args
+static PyObject *
+_wrap_gedit_message_bus_send_sync (PyGObject *self, PyObject *args)
+{
+    /* create a new message object */
+    GeditMessage *message;
+    
+    message = _helper_wrap_create_message(args);
+    
+    if (!message)
+        return NULL;
+    
+    gedit_message_bus_send_message_sync(GEDIT_MESSAGE_BUS(self->obj), message);
+    return pygobject_new((GObject *)message);
+}
+%%

Added: branches/new_plugins/plugin-loaders/python/bindings/geditplugin.override
==============================================================================
--- (empty file)
+++ branches/new_plugins/plugin-loaders/python/bindings/geditplugin.override	Wed Aug 27 17:25:57 2008
@@ -0,0 +1,210 @@
+%%
+headers
+#include <gedit/gedit-plugin.h>
+#include <gedit/gedit-window.h>
+%%
+override gedit_plugin_activate kwargs
+static PyObject *
+_wrap_gedit_plugin_activate(PyGObject *self, PyObject *args, PyObject *kwargs)
+{
+	gpointer klass, klass2;
+	static char *kwlist[] = { "window", NULL };
+	PyGObject *window;
+	PyObject *cls = (PyObject *)(((PyObject *)self)->ob_type);
+	
+	if (!PyArg_ParseTupleAndKeywords (args, 
+					  kwargs,
+					  "O!:GeditPlugin.activate", 
+					  kwlist,
+					  &PyGeditWindow_Type, 
+					  &window))
+		return NULL;
+
+	klass = g_type_class_ref (pyg_type_from_object (cls));
+	
+	if (GEDIT_IS_PLUGIN_PYTHON_CLASS (klass))
+	{
+		klass2 = g_type_class_peek_parent (klass);
+		g_type_class_unref (klass);
+		klass = g_type_class_ref (G_TYPE_FROM_CLASS (klass2));
+	}
+
+	if (GEDIT_PLUGIN_CLASS (klass)->activate)
+		GEDIT_PLUGIN_CLASS (klass)->activate (GEDIT_PLUGIN (self->obj), 
+						      GEDIT_WINDOW (window->obj));
+	else {
+		PyErr_SetString (PyExc_NotImplementedError, 
+				 "virtual method GeditPlugin.activate not implemented");
+		g_type_class_unref (klass);
+		return NULL;
+	}
+
+	g_type_class_unref (klass);
+	Py_INCREF(Py_None);
+	return Py_None;
+}
+
+%%
+override gedit_plugin_deactivate kwargs
+static PyObject *
+_wrap_gedit_plugin_deactivate(PyGObject *self, PyObject *args, PyObject *kwargs)
+{
+	gpointer klass, klass2;
+	static char *kwlist[] = {"window", NULL};
+	PyGObject *window;
+	PyObject *cls = (PyObject *)(((PyObject *)self)->ob_type);
+
+	if (!PyArg_ParseTupleAndKeywords (args, 
+					  kwargs,
+					  "O!:GeditPlugin.deactivate", 
+					  kwlist,
+					  &PyGeditWindow_Type, 
+					  &window))
+		return NULL;
+
+	klass = g_type_class_ref (pyg_type_from_object (cls));
+
+	if (GEDIT_IS_PLUGIN_PYTHON_CLASS (klass))
+	{
+		klass2 = g_type_class_peek_parent (klass);
+		g_type_class_unref (klass);
+		klass = g_type_class_ref (G_TYPE_FROM_CLASS (klass2));
+	}
+	
+	if (GEDIT_PLUGIN_CLASS (klass)->deactivate)
+		GEDIT_PLUGIN_CLASS (klass)->deactivate (GEDIT_PLUGIN (self->obj), 
+							GEDIT_WINDOW (window->obj));
+	else {
+		PyErr_SetString (PyExc_NotImplementedError, 
+				 "virtual method GeditPlugin.deactivate not implemented");
+		g_type_class_unref (klass);
+		return NULL;
+	}
+
+	g_type_class_unref (klass);
+	Py_INCREF(Py_None);
+	return Py_None;
+}
+
+%%
+override gedit_plugin_update_ui kwargs
+static PyObject *
+_wrap_gedit_plugin_update_ui (PyGObject *self, PyObject *args, PyObject *kwargs)
+{
+	gpointer klass, klass2;
+	static char *kwlist[] = {"window", NULL};
+	PyGObject *window;
+	PyObject *cls = (PyObject *)(((PyObject *)self)->ob_type);
+
+	if (!PyArg_ParseTupleAndKeywords (args, 
+					  kwargs,
+					  "O!:GeditPlugin.update_ui", 
+					  kwlist,
+					  &PyGeditWindow_Type, 
+					  &window))
+		return NULL;
+
+	klass = g_type_class_ref (pyg_type_from_object (cls));
+
+	if (GEDIT_IS_PLUGIN_PYTHON_CLASS (klass))
+	{
+		klass2 = g_type_class_peek_parent (klass);
+		g_type_class_unref (klass);
+		klass = g_type_class_ref (G_TYPE_FROM_CLASS (klass2));
+	}
+	
+	if (GEDIT_PLUGIN_CLASS (klass)->update_ui)
+		GEDIT_PLUGIN_CLASS (klass)->update_ui (GEDIT_PLUGIN (self->obj), 
+						       GEDIT_WINDOW (window->obj));
+	else {
+		PyErr_SetString (PyExc_NotImplementedError, 
+				 "virtual method GeditPlugin.update_ui not implemented");
+		g_type_class_unref (klass);
+		return NULL;
+	}
+
+	g_type_class_unref (klass);
+	Py_INCREF(Py_None);
+	return Py_None;
+}
+
+%%
+override gedit_plugin_is_configurable
+static PyObject *
+_wrap_gedit_plugin_is_configurable (PyGObject *self)
+{
+	int ret;
+	gpointer klass, klass2;
+	PyObject *cls = (PyObject *)(((PyObject *)self)->ob_type);
+
+	klass = g_type_class_ref (pyg_type_from_object (cls));
+
+	if (GEDIT_IS_PLUGIN_PYTHON_CLASS (klass))
+	{
+		klass2 = g_type_class_peek_parent (klass);
+		g_type_class_unref (klass);
+		klass = g_type_class_ref (G_TYPE_FROM_CLASS (klass2));
+	}
+	
+	if (GEDIT_PLUGIN_CLASS (klass)->is_configurable)
+		ret = GEDIT_PLUGIN_CLASS (klass)->is_configurable (GEDIT_PLUGIN (self->obj));
+	else {
+		PyErr_SetString (PyExc_NotImplementedError, 
+				 "virtual method GeditPlugin.is_configurable not implemented");
+		g_type_class_unref (klass);
+		return NULL;
+	}
+
+	g_type_class_unref (klass);
+	return PyBool_FromLong (ret);
+}
+
+%%
+override gedit_plugin_configure_dialog
+static PyObject *
+_wrap_gedit_plugin_create_configure_dialog (PyGObject *self)
+{
+	GtkWidget *ret;
+	gpointer klass, klass2;
+	PyObject *cls = (PyObject *)(((PyObject *)self)->ob_type);
+
+	klass = g_type_class_ref(pyg_type_from_object (cls));
+
+	if (GEDIT_IS_PLUGIN_PYTHON_CLASS (klass))
+	{
+		klass2 = g_type_class_peek_parent (klass);
+		g_type_class_unref (klass);
+		klass = g_type_class_ref (G_TYPE_FROM_CLASS (klass2));
+	}
+	
+	if (GEDIT_PLUGIN_CLASS (klass)->create_configure_dialog)
+		ret = GEDIT_PLUGIN_CLASS (klass)->create_configure_dialog (GEDIT_PLUGIN (self->obj));
+	else {
+		PyErr_SetString (PyExc_NotImplementedError, 
+				 "virtual method GeditPlugin.create_configure_dialog not implemented");
+		g_type_class_unref (klass);
+		return NULL;
+	}
+
+	g_type_class_unref (klass);
+
+	/* pygobject_new handles NULL checking */
+	return pygobject_new ((GObject *)ret);
+}
+%%
+override gedit_plugin_python_new
+static int
+_wrap_gedit_plugin_python_new(PyGObject *self)
+{
+        pygobject_construct (self, NULL);
+
+        if (!self->obj) {
+                PyErr_SetString (PyExc_RuntimeError, "could not create gedit.Plugin object");
+                return -1;
+        }
+        
+        _gedit_plugin_python_set_instance (GEDIT_PLUGIN_PYTHON (self->obj), (PyObject *)self);
+        return 0;
+}
+%%
+new-constructor GEDIT_TYPE_PLUGIN_PYTHON

Added: branches/new_plugins/plugin-loaders/python/gedit-plugin-loader-python.c
==============================================================================
--- (empty file)
+++ branches/new_plugins/plugin-loaders/python/gedit-plugin-loader-python.c	Wed Aug 27 17:25:57 2008
@@ -0,0 +1,602 @@
+#include "gedit-plugin-loader-python.h"
+#include "gedit-plugin-python.h"
+#include <gedit/gedit-object-module.h>
+
+#include <Python.h>
+#include <pygobject.h>
+#include <pygtk/pygtk.h>
+#include <signal.h>
+#include "config.h"
+
+#if PY_VERSION_HEX < 0x02050000
+typedef int Py_ssize_t;
+#define PY_SSIZE_T_MAX INT_MAX
+#define PY_SSIZE_T_MIN INT_MIN
+#endif
+
+#define GEDIT_PLUGIN_LOADER_PYTHON_GET_PRIVATE(object)(G_TYPE_INSTANCE_GET_PRIVATE((object), GEDIT_TYPE_PLUGIN_LOADER_PYTHON, GeditPluginLoaderPythonPrivate))
+
+struct _GeditPluginLoaderPythonPrivate
+{
+	GHashTable *loaded_plugins;
+	guint idle_gc;
+	gboolean init_failed;
+};
+
+typedef struct
+{
+	PyObject *type;
+	gchar    *path;
+} PythonInfo;
+
+static void gedit_plugin_loader_iface_init (gpointer g_iface, gpointer iface_data);
+
+/* Exported by pygedit module */
+void pygedit_register_classes (PyObject *d);
+void pygedit_add_constants (PyObject *module, const gchar *strip_prefix);
+extern PyMethodDef pygedit_functions[];
+
+/* Exported by pygeditutils module */
+void pygeditutils_register_classes (PyObject *d);
+extern PyMethodDef pygeditutils_functions[];
+
+/* Exported by pygeditcommands module */
+void pygeditcommands_register_classes (PyObject *d);
+extern PyMethodDef pygeditcommands_functions[];
+
+/* We retreive this to check for correct class hierarchy */
+static PyTypeObject *PyGeditPlugin_Type;
+
+GEDIT_PLUGIN_LOADER_REGISTER_TYPE (GeditPluginLoaderPython, gedit_plugin_loader_python);
+
+static void
+destroy_pyobject (gpointer           data, 
+                  GeditPluginPython *plugin, 
+                  gboolean           is_last_ref)
+{
+        if (is_last_ref)
+                _gedit_plugin_python_destroy (plugin);
+}
+
+static GeditPlugin *
+new_plugin_from_info (GeditPluginLoaderPython *loader,
+		      GeditPluginInfo         *info)
+{
+	PythonInfo *pyinfo;
+	GObject *object;
+	
+	pyinfo = (PythonInfo *)g_hash_table_lookup (loader->priv->loaded_plugins, info);
+	
+	if (pyinfo == NULL)
+		return NULL;
+	
+	PyObject *instance = PyObject_CallObject (pyinfo->type, NULL);
+	
+	/* CHECKME: not sure if we want to decrease the reference here, but
+           should be OK since GeditPythonPlugin adds a reference */
+        Py_XDECREF (instance);
+        
+        // FIXME: what does this do, and why?
+        object = pygobject_get (instance);
+        g_object_add_toggle_ref (object, (GToggleNotify)destroy_pyobject, NULL);
+
+	return GEDIT_PLUGIN (pygobject_get (instance));
+}
+
+static GeditPlugin *
+add_python_info (GeditPluginLoaderPython *loader,
+		 GeditPluginInfo         *info,
+		 const gchar             *path,
+		 PyObject                *type)
+{
+	PythonInfo *pyinfo;
+	
+	pyinfo = g_new (PythonInfo, 1);
+	pyinfo->path = g_strdup (path);
+	pyinfo->type = type;
+	
+	Py_INCREF (pyinfo->type);
+	
+	g_hash_table_insert (loader->priv->loaded_plugins, info, pyinfo);
+	
+	return new_plugin_from_info (loader, info);
+}
+
+static GeditPlugin *
+gedit_plugin_loader_iface_load (GeditPluginLoader *loader,
+				GeditPluginInfo   *info,
+				const gchar       *path)
+{
+	GeditPluginLoaderPython *pyloader = GEDIT_PLUGIN_LOADER_PYTHON (loader);
+	PyObject *main_module, *main_locals, *locals, *key, *value;
+	PyObject *pymodule, *fromlist;
+	gchar *module_name;
+	Py_ssize_t pos = 0;
+	GeditPlugin *result;
+	
+	if (pyloader->priv->init_failed)
+	{
+		g_warning ("Cannot load python plugin Python '%s' since gedit was"
+		           "not able to initialize the Python interpreter.",
+		           gedit_plugin_info_get_name (info));
+		return NULL;
+	}
+	
+	/* see if py definition for the plugin is already loaded */
+	result = new_plugin_from_info (pyloader, info);
+	
+	if (result != NULL)
+		return result;
+	
+	main_module = PyImport_AddModule ("__main__");
+	if (main_module == NULL)
+	{
+		g_warning ("Could not get __main__.");
+		return NULL;
+	}
+	
+	/* If we have a special path, we register it */
+	if (path != NULL)
+	{
+		PyObject *sys_path = PySys_GetObject ("path");
+		PyObject *pypath = PyString_FromString (path);
+
+		if (PySequence_Contains (sys_path, pypath) == 0)
+			PyList_Insert (sys_path, 0, pypath);
+
+		Py_DECREF (pypath);
+	}
+	
+	main_locals = PyModule_GetDict (main_module);
+	
+	/* we need a fromlist to be able to import modules with a '.' in the
+	   name. */
+	fromlist = PyTuple_New(0);
+	module_name = g_strdup (gedit_plugin_info_get_module_name (info));
+	pymodule = PyImport_ImportModuleEx (module_name, 
+					    main_locals, 
+					    main_locals, 
+					    fromlist);
+	g_free (module_name);
+	Py_DECREF(fromlist);
+
+	if (!pymodule)
+	{
+		PyErr_Print ();
+		return NULL;
+	}
+
+	locals = PyModule_GetDict (pymodule);
+	
+	while (PyDict_Next (locals, &pos, &key, &value))
+	{
+		if (!PyType_Check(value))
+			continue;
+
+		if (PyObject_IsSubclass (value, (PyObject*) PyGeditPlugin_Type))
+			return add_python_info (pyloader, info, path, value);
+	}
+	
+	g_warning ("No GeditPlugin derivative found in Python plugin '%s'",
+		   gedit_plugin_info_get_name (info));
+
+	return NULL;
+}
+
+static void
+gedit_plugin_loader_iface_unload (GeditPluginLoader *loader,
+				  GeditPluginInfo   *info)
+{
+	//GeditPluginLoaderPython *pyloader = GEDIT_PLUGIN_LOADER_PYTHON (loader);
+	
+	/* this is a no-op, since the type module will be properly unused as
+	   the last reference to the plugin dies. When the plugin is activated
+	   again, the library will be reloaded */
+}
+
+static gboolean
+run_gc (GeditPluginLoaderPython *loader)
+{
+	while (PyGC_Collect ())
+		;
+
+	loader->priv->idle_gc = 0;
+	return FALSE;
+}
+
+static void
+gedit_plugin_loader_iface_garbage_collect (GeditPluginLoader *loader)
+{
+	GeditPluginLoaderPython *pyloader;
+	
+	if (!Py_IsInitialized())
+		return;
+
+	pyloader = GEDIT_PLUGIN_LOADER_PYTHON (loader);
+
+	/*
+	 * We both run the GC right now and we schedule
+	 * a further collection in the main loop.
+	 */
+
+	while (PyGC_Collect ())
+		;
+
+	if (pyloader->priv->idle_gc == 0)
+		pyloader->priv->idle_gc = g_idle_add ((GSourceFunc)run_gc, pyloader);
+}
+
+static void
+gedit_plugin_loader_iface_init (gpointer g_iface, 
+				gpointer iface_data)
+{
+	GeditPluginLoaderInterface *iface = (GeditPluginLoaderInterface *)g_iface;
+	
+	iface->load = gedit_plugin_loader_iface_load;
+	iface->unload = gedit_plugin_loader_iface_unload;
+	iface->garbage_collect = gedit_plugin_loader_iface_garbage_collect;
+}
+
+static void
+gedit_python_shutdown (GeditPluginLoaderPython *loader)
+{
+	if (!Py_IsInitialized ())
+		return;
+
+	if (loader->priv->idle_gc != 0)
+	{
+		g_source_remove (loader->priv->idle_gc);
+		loader->priv->idle_gc = 0;
+	}
+
+	while (PyGC_Collect ())
+		;	
+
+	Py_Finalize ();
+}
+
+
+/* C equivalent of
+ *    import pygtk
+ *    pygtk.require ("2.0")
+ */
+static gboolean
+gedit_check_pygtk2 (void)
+{
+	PyObject *pygtk, *mdict, *require;
+
+	/* pygtk.require("2.0") */
+	pygtk = PyImport_ImportModule ("pygtk");
+	if (pygtk == NULL)
+	{
+		g_warning ("Error initializing Python interpreter: could not import pygtk.");
+		return FALSE;
+	}
+
+	mdict = PyModule_GetDict (pygtk);
+	require = PyDict_GetItemString (mdict, "require");
+	PyObject_CallObject (require,
+			     Py_BuildValue ("(S)", PyString_FromString ("2.0")));
+	if (PyErr_Occurred())
+	{
+		g_warning ("Error initializing Python interpreter: pygtk 2 is required.");
+		return FALSE;
+	}
+
+	return TRUE;
+}
+
+/* Note: the following two functions are needed because
+ * init_pyobject and init_pygtk which are *macros* which in case
+ * case of error set the PyErr and then make the calling
+ * function return behind our back.
+ * It's up to the caller to check the result with PyErr_Occurred()
+ */
+static void
+gedit_init_pygobject (void)
+{
+	init_pygobject_check (2, 11, 5); /* FIXME: get from config */
+}
+
+static void
+gedit_init_pygtk (void)
+{
+	PyObject *gtk, *mdict, *version, *required_version;
+
+	init_pygtk ();
+
+	/* there isn't init_pygtk_check(), do the version
+	 * check ourselves */
+	gtk = PyImport_ImportModule("gtk");
+	mdict = PyModule_GetDict(gtk);
+	version = PyDict_GetItemString (mdict, "pygtk_version");
+	if (!version)
+	{
+		PyErr_SetString (PyExc_ImportError,
+				 "PyGObject version too old");
+		return;
+	}
+
+	required_version = Py_BuildValue ("(iii)", 2, 4, 0); /* FIXME */
+
+	if (PyObject_Compare (version, required_version) == -1)
+	{
+		PyErr_SetString (PyExc_ImportError,
+				 "PyGObject version too old");
+		Py_DECREF (required_version);
+		return;
+	}
+
+	Py_DECREF (required_version);
+}
+
+static void
+old_gtksourceview_init (void)
+{
+	PyErr_SetString(PyExc_ImportError,
+			"gtksourceview module not allowed, use gtksourceview2");
+}
+
+static void
+gedit_init_pygtksourceview (void)
+{
+	PyObject *gtksourceview, *mdict, *version, *required_version;
+
+	gtksourceview = PyImport_ImportModule("gtksourceview2");
+	if (gtksourceview == NULL)
+	{
+		PyErr_SetString (PyExc_ImportError,
+				 "could not import gtksourceview");
+		return;
+	}
+
+	mdict = PyModule_GetDict (gtksourceview);
+	version = PyDict_GetItemString (mdict, "pygtksourceview2_version");
+	if (!version)
+	{
+		PyErr_SetString (PyExc_ImportError,
+				 "PyGtkSourceView version too old");
+		return;
+	}
+
+	required_version = Py_BuildValue ("(iii)", 0, 8, 0); /* FIXME */
+
+	if (PyObject_Compare (version, required_version) == -1)
+	{
+		PyErr_SetString (PyExc_ImportError,
+				 "PyGtkSourceView version too old");
+		Py_DECREF (required_version);
+		return;
+	}
+
+	Py_DECREF (required_version);
+
+	/* Create a dummy 'gtksourceview' module to prevent
+	 * loading of the old 'gtksourceview' modules that
+	 * has conflicting symbols with the gtksourceview2 module.
+	 * Raise an exception when trying to import it.
+	 */
+	PyImport_AppendInittab ("gtksourceview", old_gtksourceview_init);
+}
+
+static gboolean
+gedit_python_init (GeditPluginLoaderPython *loader)
+{
+	PyObject *mdict, *tuple;
+	PyObject *gedit, *geditutils, *geditcommands;
+	PyObject *gettext, *install, *gettext_args;
+	struct sigaction old_sigint;
+	gint res;
+	char *argv[] = { "gedit", NULL };
+
+	if (loader->priv->init_failed)
+	{
+		/* We already failed to initialized Python, don't need to
+		 * retry again */
+		return FALSE;
+	}
+	
+	if (Py_IsInitialized ())
+	{
+		/* Python has already been successfully initialized */
+		return TRUE;
+	}
+
+	/* We are trying to initialize Python for the first time,
+	   set init_failed to FALSE only if the entire initialization process
+	   ends with success */
+	loader->priv->init_failed = TRUE;
+
+	/* Hack to make python not overwrite SIGINT: this is needed to avoid
+	 * the crash reported on bug #326191 */
+
+	/* CHECK: can't we use Py_InitializeEx instead of Py_Initialize in order
+          to avoid to manage signal handlers ? - Paolo (Dec. 31, 2006) */
+
+	/* Save old handler */
+	res = sigaction (SIGINT, NULL, &old_sigint);  
+	if (res != 0)
+	{
+		g_warning ("Error initializing Python interpreter: cannot get "
+		           "handler to SIGINT signal (%s)",
+		           strerror (errno));
+
+		return FALSE;
+	}
+
+	/* Python initialization */
+	Py_Initialize ();
+
+	/* Restore old handler */
+	res = sigaction (SIGINT, &old_sigint, NULL);
+	if (res != 0)
+	{
+		g_warning ("Error initializing Python interpreter: cannot restore "
+		           "handler to SIGINT signal (%s).",
+		           strerror (errno));
+
+		goto python_init_error;
+	}
+
+	PySys_SetArgv (1, argv);
+
+	if (!gedit_check_pygtk2 ())
+	{
+		/* Warning message already printed in check_pygtk2 */
+		goto python_init_error;
+	}
+
+	/* import gobject */	
+	gedit_init_pygobject ();
+	if (PyErr_Occurred ())
+	{
+		g_warning ("Error initializing Python interpreter: could not import pygobject.");
+
+		goto python_init_error;		
+	}
+
+	/* import gtk */
+	gedit_init_pygtk ();
+	if (PyErr_Occurred ())
+	{
+		g_warning ("Error initializing Python interpreter: could not import pygtk.");
+
+		goto python_init_error;
+	}
+	
+	/* import gtksourceview */
+	gedit_init_pygtksourceview ();
+	if (PyErr_Occurred ())
+	{
+		PyErr_Print ();
+
+		g_warning ("Error initializing Python interpreter: could not import pygtksourceview.");
+
+		goto python_init_error;
+	}	
+	
+	/* import gedit */
+	gedit = Py_InitModule ("gedit", pygedit_functions);
+	mdict = PyModule_GetDict (gedit);
+
+	pygedit_register_classes (mdict);
+	pygedit_add_constants (gedit, "GEDIT_");
+
+	/* gedit version */
+	tuple = Py_BuildValue("(iii)", 
+			      GEDIT_MAJOR_VERSION,
+			      GEDIT_MINOR_VERSION,
+			      GEDIT_MICRO_VERSION);
+	PyDict_SetItemString(mdict, "version", tuple);
+	Py_DECREF(tuple);
+	
+	/* Retrieve the Python type for gedit.Plugin */
+	PyGeditPlugin_Type = (PyTypeObject *) PyDict_GetItemString (mdict, "Plugin"); 
+	if (PyGeditPlugin_Type == NULL)
+	{
+		PyErr_Print ();
+
+		goto python_init_error;
+	}
+
+	/* import gedit.utils */
+	geditutils = Py_InitModule ("gedit.utils", pygeditutils_functions);
+	PyDict_SetItemString (mdict, "utils", geditutils);
+
+	/* import gedit.commands */
+	geditcommands = Py_InitModule ("gedit.commands", pygeditcommands_functions);
+	PyDict_SetItemString (mdict, "commands", geditcommands);
+
+	mdict = PyModule_GetDict (geditutils);
+	pygeditutils_register_classes (mdict);
+	
+	mdict = PyModule_GetDict (geditcommands);
+	pygeditcommands_register_classes (mdict);
+
+	/* i18n support */
+	gettext = PyImport_ImportModule ("gettext");
+	if (gettext == NULL)
+	{
+		g_warning ("Error initializing Python interpreter: could not import gettext.");
+
+		goto python_init_error;
+	}
+
+	mdict = PyModule_GetDict (gettext);
+	install = PyDict_GetItemString (mdict, "install");
+	gettext_args = Py_BuildValue ("ss", GETTEXT_PACKAGE, GEDIT_LOCALEDIR);
+	PyObject_CallObject (install, gettext_args);
+	Py_DECREF (gettext_args);
+	
+	/* Python has been successfully initialized */
+	loader->priv->init_failed = FALSE;
+	
+	return TRUE;
+	
+python_init_error:
+
+	g_warning ("Please check the installation of all the Python related packages required "
+	           "by gedit and try again.");
+
+	PyErr_Clear ();
+
+	gedit_python_shutdown (loader);
+
+	return FALSE;
+}
+
+static void
+gedit_plugin_loader_python_finalize (GObject *object)
+{
+	GeditPluginLoaderPython *pyloader = GEDIT_PLUGIN_LOADER_PYTHON (object);
+	
+	g_hash_table_destroy (pyloader->priv->loaded_plugins);
+	gedit_python_shutdown (pyloader);
+
+	G_OBJECT_CLASS (gedit_plugin_loader_python_parent_class)->finalize (object);
+}
+
+static void
+gedit_plugin_loader_python_class_init (GeditPluginLoaderPythonClass *klass)
+{
+	GObjectClass *object_class = G_OBJECT_CLASS (klass);
+	
+	object_class->finalize = gedit_plugin_loader_python_finalize;
+
+	g_type_class_add_private (object_class, sizeof (GeditPluginLoaderPythonPrivate));
+}
+
+static void
+destroy_python_info (PythonInfo *info)
+{
+	PyGILState_STATE state = pyg_gil_state_ensure ();
+	Py_DECREF (info->type);	
+	pyg_gil_state_release (state);
+	
+	g_free (info->path);
+	g_free (info);
+}
+
+static void
+gedit_plugin_loader_python_init (GeditPluginLoaderPython *self)
+{
+	self->priv = GEDIT_PLUGIN_LOADER_PYTHON_GET_PRIVATE (self);
+	
+	/* initialize python interpreter */
+	gedit_python_init (self);
+
+	/* loaded_plugins maps GeditPluginInfo to a PythonInfo */
+	self->priv->loaded_plugins = g_hash_table_new_full (g_direct_hash,
+						            g_direct_equal,
+						            NULL,
+						            (GDestroyNotify)destroy_python_info);
+}
+
+GeditPluginLoaderPython *
+gedit_plugin_loader_python_new ()
+{
+	GObject *loader = g_object_new (GEDIT_TYPE_PLUGIN_LOADER_PYTHON, NULL);
+
+	return GEDIT_PLUGIN_LOADER_PYTHON (loader);
+}
+

Added: branches/new_plugins/plugin-loaders/python/gedit-plugin-loader-python.h
==============================================================================
--- (empty file)
+++ branches/new_plugins/plugin-loaders/python/gedit-plugin-loader-python.h	Wed Aug 27 17:25:57 2008
@@ -0,0 +1,39 @@
+#ifndef __GEDIT_PLUGIN_LOADER_PYTHON_H__
+#define __GEDIT_PLUGIN_LOADER_PYTHON_H__
+
+#include <gedit/gedit-plugin-loader.h>
+
+G_BEGIN_DECLS
+
+#define GEDIT_TYPE_PLUGIN_LOADER_PYTHON		(gedit_plugin_loader_python_get_type ())
+#define GEDIT_PLUGIN_LOADER_PYTHON(obj)		(G_TYPE_CHECK_INSTANCE_CAST ((obj), GEDIT_TYPE_PLUGIN_LOADER_PYTHON, GeditPluginLoaderPython))
+#define GEDIT_PLUGIN_LOADER_PYTHON_CONST(obj)	(G_TYPE_CHECK_INSTANCE_CAST ((obj), GEDIT_TYPE_PLUGIN_LOADER_PYTHON, GeditPluginLoaderPython const))
+#define GEDIT_PLUGIN_LOADER_PYTHON_CLASS(klass)	(G_TYPE_CHECK_CLASS_CAST ((klass), GEDIT_TYPE_PLUGIN_LOADER_PYTHON, GeditPluginLoaderPythonClass))
+#define GEDIT_IS_PLUGIN_LOADER_PYTHON(obj)		(G_TYPE_CHECK_INSTANCE_TYPE ((obj), GEDIT_TYPE_PLUGIN_LOADER_PYTHON))
+#define GEDIT_IS_PLUGIN_LOADER_PYTHON_CLASS(klass)	(G_TYPE_CHECK_CLASS_TYPE ((klass), GEDIT_TYPE_PLUGIN_LOADER_PYTHON))
+#define GEDIT_PLUGIN_LOADER_PYTHON_GET_CLASS(obj)	(G_TYPE_INSTANCE_GET_CLASS ((obj), GEDIT_TYPE_PLUGIN_LOADER_PYTHON, GeditPluginLoaderPythonClass))
+
+typedef struct _GeditPluginLoaderPython		GeditPluginLoaderPython;
+typedef struct _GeditPluginLoaderPythonClass		GeditPluginLoaderPythonClass;
+typedef struct _GeditPluginLoaderPythonPrivate	GeditPluginLoaderPythonPrivate;
+
+struct _GeditPluginLoaderPython {
+	GObject parent;
+	
+	GeditPluginLoaderPythonPrivate *priv;
+};
+
+struct _GeditPluginLoaderPythonClass {
+	GObjectClass parent_class;
+};
+
+GType gedit_plugin_loader_python_get_type (void) G_GNUC_CONST;
+GeditPluginLoaderPython *gedit_plugin_loader_python_new(void);
+
+/* All the loaders must implement this function */
+G_MODULE_EXPORT GType register_gedit_plugin_loader (GTypeModule * module);
+
+G_END_DECLS
+
+#endif /* __GEDIT_PLUGIN_LOADER_PYTHON_H__ */
+

Added: branches/new_plugins/plugin-loaders/python/gedit-plugin-python.c
==============================================================================
--- (empty file)
+++ branches/new_plugins/plugin-loaders/python/gedit-plugin-python.c	Wed Aug 27 17:25:57 2008
@@ -0,0 +1,304 @@
+/*
+ * gedit-plugin-python.c
+ * This file is part of gedit
+ *
+ * Copyright (C) 2005 Raphael Slinckx
+ * Copyright (C) 2008 Jesse van den Kieboom
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program 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 General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, 
+ * Boston, MA 02111-1307, USA. 
+ */
+
+#include <config.h>
+
+#include "gedit-plugin-python.h"
+
+#include <gedit/gedit-plugin.h>
+#include <gedit/gedit-debug.h>
+#include <pygobject.h>
+#include <string.h>
+
+#define GEDIT_PLUGIN_PYTHON_GET_PRIVATE(object)(G_TYPE_INSTANCE_GET_PRIVATE ((object), GEDIT_TYPE_PLUGIN_PYTHON, GeditPluginPythonPrivate))
+
+static GObjectClass *parent_class;
+
+struct _GeditPluginPythonPrivate 
+{
+	PyObject *instance;
+};
+
+static void	 gedit_plugin_python_class_init		(GeditPluginPythonClass *klass);
+static void	 gedit_plugin_python_init 		(GeditPluginPython      *plugin);
+
+G_DEFINE_TYPE (GeditPluginPython, gedit_plugin_python, GEDIT_TYPE_PLUGIN)
+
+static PyObject *
+call_python_method (GeditPluginPythonPrivate *priv,
+		    GeditWindow		     *window,
+		    gchar		     *method)
+{
+	PyObject *py_ret = NULL;
+
+	g_return_val_if_fail (PyObject_HasAttrString (priv->instance, method), NULL);
+
+	if (window == NULL)
+	{
+		py_ret = PyObject_CallMethod (priv->instance,
+					      method,
+					      NULL);
+	}
+	else
+	{
+		py_ret = PyObject_CallMethod (priv->instance,
+					      method,
+					      "(N)",
+					      pygobject_new (G_OBJECT (window)));
+	}
+	
+	if (!py_ret)
+		PyErr_Print ();
+
+	return py_ret;
+}
+
+static gboolean
+check_py_object_is_gtk_widget (PyObject *py_obj)
+{
+	static PyTypeObject *_PyGtkWidget_Type = NULL;
+
+	if (_PyGtkWidget_Type == NULL)
+	{
+		PyObject *module;
+
+	    	if ((module = PyImport_ImportModule ("gtk")))
+	    	{
+			PyObject *moddict = PyModule_GetDict (module);
+			_PyGtkWidget_Type = (PyTypeObject *) PyDict_GetItemString (moddict, "Widget");
+	    	}
+
+		if (_PyGtkWidget_Type == NULL)
+		{
+			PyErr_SetString(PyExc_TypeError, "could not find Python gtk widget type");
+			PyErr_Print();
+
+			return FALSE;
+		}
+	}
+
+	return PyObject_TypeCheck (py_obj, _PyGtkWidget_Type) ? TRUE : FALSE;
+}
+
+static void
+impl_update_ui (GeditPlugin *plugin,
+		GeditWindow *window)
+{
+	PyGILState_STATE state = pyg_gil_state_ensure ();
+	GeditPluginPythonPrivate *priv = GEDIT_PLUGIN_PYTHON(plugin)->priv;
+	
+	if (PyObject_HasAttrString (priv->instance, "update_ui"))
+	{		
+		PyObject *py_ret = call_python_method (priv, window, "update_ui");
+		
+		if (py_ret)
+		{
+			Py_XDECREF (py_ret);
+		}
+	}
+	else
+		GEDIT_PLUGIN_CLASS (parent_class)->update_ui (plugin, window);
+
+	pyg_gil_state_release (state);
+}
+
+static void
+impl_deactivate (GeditPlugin *plugin,
+		 GeditWindow *window)
+{
+	PyGILState_STATE state = pyg_gil_state_ensure ();
+	GeditPluginPythonPrivate *priv = GEDIT_PLUGIN_PYTHON(plugin)->priv;
+	
+	if (PyObject_HasAttrString (priv->instance, "deactivate"))
+	{		
+		PyObject *py_ret = call_python_method (priv, window, "deactivate");
+		
+		if (py_ret)
+		{
+			Py_XDECREF (py_ret);
+		}
+	}
+	else
+		GEDIT_PLUGIN_CLASS (parent_class)->deactivate (plugin, window);
+
+	pyg_gil_state_release (state);
+}
+
+static void
+impl_activate (GeditPlugin *plugin,
+	       GeditWindow *window)
+{
+	PyGILState_STATE state = pyg_gil_state_ensure ();
+	GeditPluginPythonPrivate *priv = GEDIT_PLUGIN_PYTHON(plugin)->priv;
+		
+	if (PyObject_HasAttrString (priv->instance, "activate"))
+	{
+		PyObject *py_ret = call_python_method (priv, window, "activate");
+
+		if (py_ret)
+		{
+			Py_XDECREF (py_ret);
+		}
+	}
+	else
+		GEDIT_PLUGIN_CLASS (parent_class)->activate (plugin, window);
+	
+	pyg_gil_state_release (state);
+}
+
+static GtkWidget *
+impl_create_configure_dialog (GeditPlugin *plugin)
+{
+	PyGILState_STATE state = pyg_gil_state_ensure ();
+	GeditPluginPythonPrivate *priv = GEDIT_PLUGIN_PYTHON(plugin)->priv;
+	GtkWidget *ret = NULL;
+	
+	if (PyObject_HasAttrString (priv->instance, "create_configure_dialog"))
+	{
+		PyObject *py_ret = call_python_method (priv, NULL, "create_configure_dialog");
+	
+		if (py_ret)
+		{
+			if (check_py_object_is_gtk_widget (py_ret))
+			{
+				ret = GTK_WIDGET (pygobject_get (py_ret));
+				g_object_ref (ret);
+			}
+			else
+			{
+				PyErr_SetString(PyExc_TypeError, "return value for create_configure_dialog is not a GtkWidget");
+				PyErr_Print();
+			}
+			
+			Py_DECREF (py_ret);
+		}
+	}
+	else
+		ret = GEDIT_PLUGIN_CLASS (parent_class)->create_configure_dialog (plugin);
+ 
+	pyg_gil_state_release (state);
+	
+	return ret;
+}
+
+static gboolean
+impl_is_configurable (GeditPlugin *plugin)
+{
+	PyGILState_STATE state = pyg_gil_state_ensure ();
+	GeditPluginPythonPrivate *priv = GEDIT_PLUGIN_PYTHON(plugin)->priv;
+	PyObject *dict = priv->instance->ob_type->tp_dict;	
+	gboolean result;
+	
+	if (dict == NULL)
+		result = FALSE;
+	else if (!PyDict_Check(dict))
+		result = FALSE;
+	else 
+		result = PyDict_GetItemString(dict, "create_configure_dialog") != NULL;
+
+	pyg_gil_state_release (state);
+	
+	return result;
+}
+
+void
+_gedit_plugin_python_set_instance (GeditPluginPython *plugin, 
+				  PyObject 	    *instance)
+{
+	PyGILState_STATE state = pyg_gil_state_ensure ();
+	
+	Py_XDECREF (plugin->priv->instance);
+	
+	/* CHECK: is the increment actually needed? */
+	Py_INCREF (instance);
+	plugin->priv->instance = instance;
+	pyg_gil_state_release (state);
+}
+
+PyObject *
+_gedit_plugin_python_get_instance (GeditPluginPython *plugin)
+{
+	return plugin->priv->instance;
+}
+
+void
+_gedit_plugin_python_destroy (GeditPluginPython *plugin)
+{
+	PyGILState_STATE state;
+	PyObject *instance;
+	
+	if (plugin->priv->instance)
+	{
+		state = pyg_gil_state_ensure ();
+		
+		instance = plugin->priv->instance;
+		plugin->priv->instance = 0;
+
+		Py_XDECREF (instance);
+		pyg_gil_state_release (state);
+	}
+	else
+		g_object_unref (plugin);
+}
+
+
+static void
+gedit_plugin_python_init (GeditPluginPython *plugin)
+{
+	plugin->priv = GEDIT_PLUGIN_PYTHON_GET_PRIVATE(plugin);
+
+	gedit_debug_message (DEBUG_PLUGINS, "Creating Python plugin instance");
+	plugin->priv->instance = 0;
+}
+
+static void
+gedit_plugin_python_finalize (GObject *object)
+{
+	PyGILState_STATE state;
+	
+	gedit_debug_message (DEBUG_PLUGINS, "Finalizing Python plugin instance");
+
+	state = pyg_gil_state_ensure ();
+	Py_XDECREF (GEDIT_PLUGIN_PYTHON(object)->priv->instance);
+	pyg_gil_state_release (state);
+	
+	G_OBJECT_CLASS (parent_class)->finalize (object);
+}
+
+static void
+gedit_plugin_python_class_init (GeditPluginPythonClass *klass)
+{
+	GeditPluginClass *plugin_class = GEDIT_PLUGIN_CLASS (klass);
+
+	parent_class = g_type_class_peek_parent (klass);
+
+	g_type_class_add_private (klass, sizeof (GeditPluginPythonPrivate));
+	G_OBJECT_CLASS (klass)->finalize = gedit_plugin_python_finalize;
+
+	plugin_class->activate = impl_activate;
+	plugin_class->deactivate = impl_deactivate;
+	plugin_class->update_ui = impl_update_ui;
+	plugin_class->create_configure_dialog = impl_create_configure_dialog;
+	plugin_class->is_configurable = impl_is_configurable;
+}
+

Added: branches/new_plugins/plugin-loaders/python/gedit-plugin-python.h
==============================================================================
--- (empty file)
+++ branches/new_plugins/plugin-loaders/python/gedit-plugin-python.h	Wed Aug 27 17:25:57 2008
@@ -0,0 +1,87 @@
+/*
+ * gedit-plugin-python.h
+ * This file is part of gedit
+ *
+ * Copyright (C) 2005 - Raphael Slinckx
+ * Copyright (C) 2008 - Jesse van den Kieboom
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program 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 General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, 
+ * Boston, MA 02111-1307, USA. 
+ */
+
+#ifndef __GEDIT_PLUGIN_PYTHON_H__
+#define __GEDIT_PLUGIN_PYTHON_H__
+
+#include <glib-object.h>
+#include <pygobject.h>
+
+#include <gedit/gedit-plugin.h>
+
+G_BEGIN_DECLS
+
+/*
+ * Type checking and casting macros
+ */
+#define GEDIT_TYPE_PLUGIN_PYTHON		(gedit_plugin_python_get_type())
+#define GEDIT_PLUGIN_PYTHON(obj)		(G_TYPE_CHECK_INSTANCE_CAST((obj), GEDIT_TYPE_PLUGIN_PYTHON, GeditPluginPython))
+#define GEDIT_PLUGIN_PYTHON_CLASS(klass)	(G_TYPE_CHECK_CLASS_CAST((klass), GEDIT_TYPE_PLUGIN_PYTHON, GeditPluginPythonClass))
+#define GEDIT_IS_PLUGIN_PYTHON(obj)		(G_TYPE_CHECK_INSTANCE_TYPE((obj), GEDIT_TYPE_PLUGIN_PYTHON))
+#define GEDIT_IS_PLUGIN_PYTHON_CLASS(klass)	(G_TYPE_CHECK_CLASS_TYPE ((klass), GEDIT_TYPE_PLUGIN_PYTHON))
+#define GEDIT_PLUGIN_PYTHON_GET_CLASS(obj)	(G_TYPE_INSTANCE_GET_CLASS((obj), GEDIT_TYPE_PLUGIN_PYTHON, GeditPluginPythonClass))
+
+/* Private structure type */
+typedef struct _GeditPluginPythonPrivate GeditPluginPythonPrivate;
+
+/*
+ * Main object structure
+ */
+typedef struct _GeditPluginPython GeditPluginPython;
+
+struct _GeditPluginPython 
+{
+	GeditPlugin parent;
+	
+	/*< private > */
+	GeditPluginPythonPrivate *priv;
+};
+
+/*
+ * Class definition
+ */
+typedef struct _GeditPluginPythonClass GeditPluginPythonClass;
+
+struct _GeditPluginPythonClass 
+{
+	GeditPluginClass parent_class;
+};
+
+/*
+ * Public methods
+ */
+GType	 gedit_plugin_python_get_type 		(void) G_GNUC_CONST;
+
+
+/* 
+ * Private methods
+ */
+void	  _gedit_plugin_python_set_instance	(GeditPluginPython *plugin, 
+						 PyObject 	   *instance);
+PyObject *_gedit_plugin_python_get_instance	(GeditPluginPython *plugin);
+void 	  _gedit_plugin_python_destroy		(GeditPluginPython *plugin);
+
+G_END_DECLS
+
+#endif  /* __GEDIT_PLUGIN_PYTHON_H__ */
+

Added: branches/new_plugins/plugin-loaders/python/pythonloader.gedit-plugin-loader.desktop.in
==============================================================================
--- (empty file)
+++ branches/new_plugins/plugin-loaders/python/pythonloader.gedit-plugin-loader.desktop.in	Wed Aug 27 17:25:57 2008
@@ -0,0 +1,4 @@
+[Gedit Plugin Loader]
+Loader=Python
+Module=pythonloader
+Copyright=Copyright  2008 Jesse van den Kieboom



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]