It appears I've been thinking about doing proxying the hard way - there's a much simpler way (really more a wrapper than a proxy):
proxyqwidget.h =========== class ProxyQWidget : public QWidget { public: ProxyQWidget (QWsiget *parent, const char *name, const char *cls); virtual const char *className () const { return clsName; } virtual QMetaObject *metaObject () const; private: char *clsName; }; proxyqwidget.cpp ============= ProxyQWidget::ProxyQWisget (QWidget *parent, const char *name, const char* cls) : QWidget (parent, name) { clsName = new char [strlen (cls) + 1]; strcpy (clsName, cls); } QMetaObject *ProxyQWisget::metaObject { <manipulate the meta object here> // You'll probably need another method to pull the meta data out // of Python and the actual widget - I haven't done that } pyqwidgetplugin.cpp =============== QWidget* PyQWidgetPlugin::create(const QString &key, QWidget* parent, const char* name) { if (debug) printf ("create %s\n", key.latin1 ()); PyObject* widgetModule = init(key); // get the py factory function PyObject *widgetFactory = pyize->getNewObjectRef (widgetModule, "createWidget"); if (!widgetFactory) return pyqw_error ("***failed to find widget factory\n"); //************************ //!!!!! create the proxy with the parent, name and key passed in ProxyQWidget *pw = new ProxyQWidget(parent, name, key.latin1 ()); // set up the args for the python factory function call //************************ //!!!!! The proxy is passed as the parent of the Python widget PyObject *pyParent = sipMapCppToSelf (pw, sipClass_QWidget); PyObject *args = Py_BuildValue ("Ns", pyParent, name); PyObject *pluginWidget = NULL; if (pyParent && args) { // run the factory function pluginWidget = pyize->runFunction (widgetFactory, args); if (!pluginWidget) pyqw_error ("*** runFunction failure\n;"); } else if (debug) pyqw_error ("***failed to create args\n"); // cleanup pyize->decref (pyParent); pyize->decref (args); pyize->decref (widgetFactory); QWidget *widget; // convert the PyObject to a C++ PyQWidget * int isErr = 0; widget = sipForceConvertTo_QWidget (pluginWidget, &isErr); if (isErr) return pyqw_error ("***failed sip conversion to C++ pointer\n"); pyize->releaseLock (); //************************ //!!!! Now just return the proxy as the parent of the Python // widget return pw; } This lets you set the class name, control the QMetaObject, and fixes one other BIG problem I think the other approach ignored. With the other approach (just embedding the Python widget and doing all of the virtual method stuff), the proxy widget had no children (I think that's why it always segfaulted for me). There is NO general way to transfer the children to the proxy because, as in the case of FileChooser, some of the children are QObjects but not QWidgets (any QLayout descendents) and can't be reparented - the approach above handles that (and is considerably simpler besides). Leaving ProxyQWidget parentless was probably causing a lot of the earlier problems too. I also made a few changes to pyqwidgetplugin.cpp - mostly some refactoring (all the calls to the Pythonize ctor were driving me nuts - you can replace them in 'init' with pyize->acquireLock()). I haven't played around with this much yet, but it seems to work just fine. The one thing that needs to be done is that the Python widget needs to provide size hints so that the proxy widget can size itself properly - the "FileChooser" widget isn't very pretty in QtDesigner without those, but it seems to work. I feel a little silly not having thought of this earlier. The other question is what this does to code generation. Haven't looked at that either - that's likely to be a problem. It should be possible to remove the extra widget layer from the generated code ('cause I would think it's going to show up there). Jim _______________________________________________ PyKDE mailing list [EMAIL PROTECTED] http://mats.imk.fraunhofer.de/mailman/listinfo/pykde