📄 pluginintro.html
字号:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN"><!-- /home/edba/dist/qtopia/main-Sunday/qtopia/doc/pluginintro.doc:1 --><html><head><meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1"><title>Qtopia Plugins</title><style type="text/css"><!--h3.fn,span.fn { margin-left: 1cm; text-indent: -1cm; }a:link { color: #004faf; text-decoration: none }a:visited { color: #672967; text-decoration: none }body { background: #ffffff; color: black; }--></style></head><body><table border="0" cellpadding="0" cellspacing="0" width="100%"><tr><td width="200" align="left" valign="top"><a href="index.html"><img height="27" width="472" src="dochead.png" border="0"></a><br><font face="Arial,Helvetica,Geneva,Swiss,SunSans-Regular" align="center" size=32>Qtopia</font> <a href="index.html">Home</a> - <a href="qtopiaclasses.html">Classes</a> - <a href="qtopiaannotated.html">Annotated</a> - <a href="qtopiafunctions.html">Functions</a> - <a href="qtindex.html">Qt Embedded</a></td><td align="right" valign="top"> <table border="0" cellpadding="0" cellspacing="0" width="137"> <tr> <td><a href="http://www.trolltech.com/company/about/trolls.html"><img height="100" width="100" src="face.png" border="0"></a></td> <td><img height="100" width="100" src="qtlogo.png" align="top" border="0"></td> </tr> </table></td></tr></table><h1 align=center>Qtopia Plugins</h1><p> <p> Contents<!-- toc --><ul><li><a href="#1"> Introduction</a><li><a href="#2"> Writing the functionality</a><li><a href="#3"> Subclassing the interface</a><li><a href="#4"> Implementing the interface</a><li><a href="#5"> Creating an instance</a><li><a href="#6"> Loading Plugins</a></ul><!-- endtoc --><p> <h2> Introduction</h2><a name="1"></a><p> Plugins are implemented in Qtopia via a COM-like layer. The basic stepsto writing any Qtopia plugin are:<ul><li> Write the functionality that the plugin will provide.<li> Subclass the interface for the plugin you wish to write.<li> Provide implemetations for the interface methods.<li> Create an instance of the plugin.</ul><p> There are also some basic rules to follow when writing a plugin:<ul><li> Due to the implementation details of moc, it is important that any QObjectsubclasses in your plugin have unique names to prevent clashes betweentwo plugins. As a rule, use a unique prefix for all classes includinginternal classes. For example, if a plugin "foo" has an internal helperclass that is a QObject subclass, it should be named FooHelperrather than Helper.<li> Plugins should not leak memory. Since a plugin may be unloaded at anytime it is important to cleanup all used memory when your plugin interfaceis destructed.</ul><p> <h2> Writing the functionality</h2><a name="2"></a><p> Consider the following fictious plugin interface:<p> <pre>// {05E0A4AB-DDC5-4449-85A9-828100DE00A9} #ifndef IID_WidgetPlugin#define IID_WidgetPlugin QUuid( 0x05e0a4ab, 0xddc5, 0x4449, 0x85, 0xa9, 0x82, 0x81, 0x00, 0xde, 0x00, 0xa9)#endifstruct WidgetPluginInterface : public QUnknownInterface{ virtual QWidget *widget( QWidget *parent ) = 0; virtual QString name() const = 0;};</pre> <p> This is a simple interface that provides a plugin name and a widget thatis created with the supplied parent.<p> IID_WidgetPlugin defines a unique ID for this interface.<p> The plugin that we are writing provides a widget that draws an ellipse inits center. The code below implements the functionality that this pluginprovides.<p> <pre>class EllipseWidget : public QWidget{ Q_OBJECTpublic: EllipseWidget( QWidget *parent=0 ) : QWidget( parent, "Ellipse" ) { }protected: void paintEvent( QPaintEvent * ) { QPainter p( this ); p.drawEllipse( rect() ); }};</pre> <p> <h2> Subclassing the interface</h2><a name="3"></a><p> Now you can subclass the WidgetPluginInterface:<p> <pre>struct CirclePlugin : public WidgetPluginInterface{public: virtual QWidget *widget( QWidget *parent ); virtual QString name() const; QRESULT queryInterface( const <a href="quuid.html">QUuid</a>&, QUnknownInterface** ); Q_REFCOUNTprotected: CircleWidget *w; ulong ref;};</pre> <p> There are two things to note in the CirclePlugin struct:<ul><li> the queryInterface() function allows the plugin loader to querywhat interfaces the plugin implements.<li> Q_REFCOUNT is a macro to simplify the reference counting.This macro expects the ulog ref variable to be present.</ul><p> <h2> Implementing the interface</h2><a name="4"></a><p> The constructor an destructor are straight-forward. The most importantpoint is that ref must be initialised with 0.<pre>CirclePlugin::CirclePlugin() : w(0), ref(0){}CirclePlugin::~CirclePlugin(){ delete w;}</pre> <p> The queryInterface() function can be implemented using thefollowing boilerplate code:<p> <pre>QRESULT CirclePlugin::queryInterface( const <a href="quuid.html">QUuid</a> &uuid, QUnknownInterface **iface ){ *iface = 0; if ( uuid == IID_QUnknown ) *iface = this; else if ( uuid == IID_WidgetPlugin ) *iface = this; else return QS_FALSE; (*iface)->addRef(); return QS_OK;}</pre> <p> A plugin can provide several interfaces. At the very least QUnknownInterfaceis provided by all plugins.<p> The widget() function returns the widget.<p> <pre>QWidget *CirclePlugin::widget( QWidget *parent ){ if ( !w ) w = new CircleWidget( parent ); return w;}</pre> <p> The name() function returns the name of the plugin.<p> <pre>QString CirclePlugin::name(){ return qApp->translate( "WidgetPlugin", "Circle" );}</pre> <p> <h2> Creating an instance</h2><a name="5"></a><p> You must also create an instance of the widget plugin using thefollowing boilerplate code:<p> <pre>Q_EXPORT_INTERFACE(){ Q_CREATE_INSTANCE( CirclePlugin )}</pre> <p> <h2> Loading Plugins</h2><a name="6"></a><p> The recommended method for loading plugins is to use the <a href="pluginloader.html">PluginLoader</a> class.The PluginLoader class provides simplified enumeration and loading ofplugins and provides safety in cases where the system has been booted inSafe Mode.<p> <pre>PluginLoader loader( "Widgets" );QStringList list = pluginLoader.list();QStringList::Iterator it;QValueList<WidgetPluginInterface*> widgetsList;for ( it = list.begin(); it != list.end(); ++it ) { WidgetPluginInterface *iface = 0; if ( pluginLoader.queryInterface( *it, IID_WidgetPlugin, (QUnknownInterface**)&iface ) == QS_OK && iface ) { widgetsList.append( iface ); }}</pre> <p> The PluginLoader class expects the plugins to be installed in the$QPEDIR/plugins/<i>type</i> directory.<p> <!-- eof --><p><address><hr><div align="center"><table width="100%" cellspacing="0" border="0"><tr><td>Copyright © 2001-2004 Trolltech<td><a href="http://www.trolltech.com/trademarks.html">Trademarks</a><td align="right"><div align="right">Qtopia version 2.0.0</div></table></div></address></body></html>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -