1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141
|
/* -*- Mode: C; c-basic-offset: 4 -*- */
%%
headers
#include <Python.h>
#define NO_IMPORT_PYGOBJECT
#include "pygobject.h"
#include <keybinder.h>
typedef struct _Handler_and_Args {
PyObject *handler;
PyObject *args;
char *keystring;
} Handler_and_Args;
static GSList *HA_List = NULL;
void handler_c_func (const char *keystring, gpointer user_data)
{
PyGILState_STATE gstate;
Handler_and_Args *ha = (Handler_and_Args *) user_data;
gstate = PyGILState_Ensure();
PyObject *result = PyEval_CallObject(ha->handler, ha->args);
if (result == NULL) {
if (PyErr_Occurred()) {
PyErr_Print();
}
} else {
Py_DECREF(result);
}
PyGILState_Release(gstate);
}
%%
modulename _keybinder
%%
%%
ignore-glob
keybinder_init
*_get_type
%%
override keybinder_bind kwargs
static PyObject*
_wrap_keybinder_bind (PyGObject *self, PyObject *args, PyObject *kwargs)
{
guint len;
PyObject *first;
char *keystring = NULL;
PyObject *handler;
PyObject *extra_args;
GSList *iter;
Handler_and_Args *ha;
gboolean success;
len = PyTuple_Size(args);
if (len < 2) {
PyErr_SetString(PyExc_TypeError, "bind requires at least 2 arguments");
return NULL;
}
first = PySequence_GetSlice(args, 0, 2);
if (!PyArg_ParseTuple(first, "sO:keybinder_bind", &keystring, &handler)) {
Py_XDECREF(first);
return NULL;
}
Py_XDECREF(first);
if (!PyCallable_Check(handler)) {
PyErr_SetString(PyExc_TypeError, "bind: 2nd argument must be callable");
return NULL;
}
for (iter = HA_List; iter != NULL; iter = iter->next) {
Handler_and_Args *ha = (Handler_and_Args *) iter->data;
if (strcmp(keystring, ha->keystring) == 0) {
PyErr_SetString(PyExc_KeyError, "bind: keystring is already bound");
return NULL;
}
}
extra_args = PySequence_GetSlice(args, 2, len);
if (extra_args == NULL) {
return NULL;
}
ha = g_new(Handler_and_Args, 1);
ha->handler = handler;
ha->args = extra_args;
ha->keystring = g_strdup(keystring);
Py_XINCREF(handler);
Py_XINCREF(extra_args);
success = keybinder_bind(keystring, &handler_c_func, ha);
if (success) {
HA_List = g_slist_prepend(HA_List, ha);
Py_RETURN_TRUE;
} else {
Py_RETURN_FALSE;
}
}
%%
override keybinder_unbind kwargs
static PyObject*
_wrap_keybinder_unbind (PyGObject *self, PyObject *args, PyObject *kwargs)
{
guint len;
char *keystring = NULL;
GSList *iter;
len = PyTuple_Size(args);
if (len != 1) {
PyErr_SetString(PyExc_TypeError, "unbind requires exactly 1 argument");
return NULL;
}
if (!PyArg_ParseTuple(args, "s:keybinder_unbind", &keystring)) {
return NULL;
}
for (iter = HA_List; iter != NULL; iter = iter->next) {
Handler_and_Args *ha = (Handler_and_Args *) iter->data;
if (strcmp(keystring, ha->keystring) == 0) {
keybinder_unbind(keystring, &handler_c_func);
HA_List = g_slist_remove(HA_List, ha);
Py_XDECREF(ha->handler);
Py_XDECREF(ha->args);
g_free(ha->keystring);
g_free(ha);
Py_INCREF(Py_None);
return Py_None;
}
}
PyErr_SetString(PyExc_KeyError, "bind: keystring is not bound");
return NULL;
}
|