fix logic
[personal-kdelibs.git] / kdecore / util / kgenericfactory.h
blob4d52394c4f6722d21b7f703125c000281855150a
1 /* This file is part of the KDE project
2 * Copyright (C) 2001 Simon Hausmann <hausmann@kde.org>
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
14 * You should have received a copy of the GNU Library General Public License
15 * along with this library; see the file COPYING.LIB. If not, write to
16 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 * Boston, MA 02110-1301, USA.
19 #ifndef kgenericfactory_h
20 #define kgenericfactory_h
22 #include <klibloader.h>
23 #include <kpluginfactory.h>
24 #include <kpluginloader.h>
25 #include <ktypelist.h>
26 #include <kcomponentdata.h>
27 #include <kgenericfactory.tcc>
28 #include <kglobal.h>
29 #include <klocale.h>
30 #include <kdebug.h>
32 /* @internal */
33 template <class T>
34 class KGenericFactoryBase : public KPluginFactory
36 public:
37 explicit KGenericFactoryBase(const char *componentName, const char *catalogName)
38 : KPluginFactory(componentName, catalogName)
40 s_self = this;
41 s_createComponentDataCalled = false;
44 explicit KGenericFactoryBase( const KAboutData *data )
45 : KPluginFactory(data)
47 s_self = this;
48 s_createComponentDataCalled = false;
51 virtual ~KGenericFactoryBase()
53 s_self = 0;
56 static KComponentData componentData()
58 Q_ASSERT(s_self);
59 if (!s_createComponentDataCalled) {
60 s_createComponentDataCalled = true;
62 KComponentData *kcd = s_self->createComponentData();
63 Q_ASSERT(kcd);
64 s_self->setComponentData(*kcd);
65 delete kcd;
67 return static_cast<KPluginFactory *>(s_self)->componentData();
70 protected:
71 virtual KComponentData *createComponentData()
73 return new KComponentData(componentData());
76 private:
77 static bool s_createComponentDataCalled;
78 static KGenericFactoryBase<T> *s_self;
81 /* @internal */
82 template <class T>
83 KGenericFactoryBase<T> *KGenericFactoryBase<T>::s_self = 0;
85 /* @internal */
86 template <class T>
87 bool KGenericFactoryBase<T>::s_createComponentDataCalled = false;
89 /**
90 * This template provides a generic implementation of a KLibFactory ,
91 * for use with shared library components. It implements the pure virtual
92 * createObject method of KLibFactory and instantiates objects of the
93 * specified class (template argument) when the class name argument of
94 * createObject matches a class name in the given hierarchy.
96 * In case you are developing a KParts component, skip this file and
97 * go directly to KParts::GenericFactory .
99 * Note that the class specified as template argument needs to provide
100 * a certain constructor:
101 * <ul>
102 * <li>If the class is derived from QObject then it needs to have
103 * a constructor like:
104 * <code>MyClass( QObject *parent,
105 * const QStringList &args );</code>
106 * <li>If the class is derived from QWidget then it needs to have
107 * a constructor like:
108 * <code>MyWidget( QWidget *parent,
109 * const QStringList &args);</code>
110 * <li>If the class is derived from KParts::Part then it needs to have
111 * a constructor like:
112 * <code>MyPart( QWidget *parentWidget,
113 * QObject *parent,
114 * const QStringList &args );</code>
115 * </ul>
116 * The args QStringList passed to the constructor is the args string list
117 * that the caller passed to KLibFactory's create method.
119 * In addition upon instantiation this template provides a central
120 * KComponentData object for your component, accessible through the
121 * static componentData() method. The componentName and catalogName arguments
122 * of the KGenericFactory constructor are passed to the KComponentData object.
124 * The creation of the KComponentData object can be customized by inheriting
125 * from this template class and re-implementing the virtual createComponentData
126 * method. For example it could look like this:
127 * \code
128 * KComponentData *MyFactory::createComponentData()
130 * return new KComponentData( myAboutData );
132 * \endcode
134 * Example of usage of the whole template:
135 * \code
136 * class MyPlugin : public KParts::Plugin
138 * Q_ OBJECT
139 * public:
140 * MyPlugin( QObject *parent, const QStringList &args );
141 * ...
142 * };
144 * K_EXPORT_COMPONENT_FACTORY( libmyplugin, KGenericFactory<MyPlugin> )
145 * \endcode
147 template <class Product, class ParentType = QObject>
148 class KDE_DEPRECATED KGenericFactory : public KGenericFactoryBase<Product>
150 public:
151 explicit KGenericFactory( const char *componentName = 0, const char *catalogName = 0 )
152 : KGenericFactoryBase<Product>(componentName, catalogName)
155 explicit KGenericFactory( const KAboutData *data )
156 : KGenericFactoryBase<Product>(data)
159 protected:
160 virtual QObject *createObject( QObject *parent,
161 const char *className, const QStringList &args )
163 return KDEPrivate::ConcreteFactory<Product, ParentType>
164 ::create( 0, parent, className, args );
169 * \class KGenericFactory kgenericfactory.h <KGenericFactory>
171 * This template provides a generic implementation of a KLibFactory ,
172 * for use with shared library components. It implements the pure virtual
173 * createObject method of KLibFactory and instantiates objects of the
174 * specified classes in the given typelist template argument when the class
175 * name argument of createObject matches a class names in the given hierarchy
176 * of classes.
178 * Note that each class in the specified in the typelist template argument
179 * needs to provide a certain constructor:
180 * <ul>
181 * <li>If the class is derived from QObject then it needs to have
182 * a constructor like:
183 * <code>MyClass( QObject *parent,
184 * const QStringList &args );</code>
185 * <li>If the class is derived from QWidget then it needs to have
186 * a constructor like:
187 * <code>MyWidget( QWidget *parent,
188 * const QStringList &args);</code>
189 * <li>If the class is derived from KParts::Part then it needs to have
190 * a constructor like:
191 * <code>MyPart( QWidget *parentWidget,
192 * QObject *parent,
193 * const QStringList &args );</code>
194 * </ul>
195 * The args QStringList passed to the constructor is the args string list
196 * that the caller passed to KLibFactory's create method.
198 * In addition upon instantiation this template provides a central
199 * KComponentData object for your component, accessible through the
200 * static componentData() method. The componentName and catalogName arguments
201 * of the KGenericFactory constructor are passed to the KComponentData object.
203 * The creation of the KComponentData object can be customized by inheriting
204 * from this template class and re-implementing the virtual createComponentData
205 * method. For example it could look like this:
206 * \code
207 * KComponentData *MyFactory::createComponentData()
209 * return new KComponentData( myAboutData );
211 * \endcode
213 * Example of usage of the whole template:
214 * \code
215 * class MyPlugin : public KParts::Plugin
217 * Q_ OBJECT
218 * public:
219 * MyPlugin( QObject *parent,
220 * const QStringList &args );
221 * ...
222 * };
224 * class MyDialogComponent : public KDialog
226 * Q_ OBJECT
227 * public:
228 * MyDialogComponent( QWidget *parentWidget,
229 * const QStringList &args );
230 * ...
231 * };
233 * typedef K_TYPELIST_2( MyPlugin, MyDialogComponent ) Products;
234 * K_EXPORT_COMPONENT_FACTORY( libmyplugin, KGenericFactory<Products> )
235 * \endcode
237 template <class Product, class ProductListTail>
238 class KGenericFactory< KTypeList<Product, ProductListTail>, QObject >
239 : public KGenericFactoryBase<KTypeList<Product, ProductListTail> >
241 public:
242 explicit KGenericFactory( const char *componentName = 0, const char *catalogName = 0 )
243 : KGenericFactoryBase<KTypeList<Product, ProductListTail> >(componentName, catalogName)
246 explicit KGenericFactory( const KAboutData *data )
247 : KGenericFactoryBase<KTypeList<Product, ProductListTail> >(data)
251 protected:
252 virtual QObject *createObject( QObject *parent,
253 const char *className, const QStringList &args )
255 return KDEPrivate::MultiFactory< KTypeList< Product, ProductListTail > >
256 ::create( 0, parent, className, args );
261 * \class KGenericFactory kgenericfactory.h <KGenericFactory>
263 * This template provides a generic implementation of a KLibFactory ,
264 * for use with shared library components. It implements the pure virtual
265 * createObject method of KLibFactory and instantiates objects of the
266 * specified classes in the given typelist template argument when the class
267 * name argument of createObject matches a class names in the given hierarchy
268 * of classes.
270 * Note that each class in the specified in the typelist template argument
271 * needs to provide a certain constructor:
272 * <ul>
273 * <li>If the class is derived from QObject then it needs to have
274 * a constructor like:
275 * <code>MyClass( QObject *parent,
276 * const QStringList &args );</code>
277 * <li>If the class is derived from QWidget then it needs to have
278 * a constructor like:
279 * <code>MyWidget( QWidget *parent,
280 * const QStringList &args);</code>
281 * <li>If the class is derived from KParts::Part then it needs to have
282 * a constructor like:
283 * <code>MyPart( QWidget *parentWidget,
284 * QObject *parent,
285 * const QStringList &args );</code>
286 * </ul>
287 * The args QStringList passed to the constructor is the args string list
288 * that the caller passed to KLibFactory's create method.
290 * In addition upon instantiation this template provides a central
291 * KComponentData object for your component, accessible through the
292 * static componentData() method. The componentName and catalogNames arguments
293 * of the KGenericFactory constructor are passed to the KComponentData object.
295 * The creation of the KComponentData object can be customized by inheriting
296 * from this template class and re-implementing the virtual createComponentData
297 * method. For example it could look like this:
298 * \code
299 * KComponentData *MyFactory::createComponentData()
301 * return new KComponentData( myAboutData );
303 * \endcode
305 * Example of usage of the whole template:
306 * \code
307 * class MyPlugin : public KParts::Plugin
309 * Q_ OBJECT
310 * public:
311 * MyPlugin( QObject *parent,
312 * const QStringList &args );
313 * ...
314 * };
316 * class MyDialogComponent : public KDialog
318 * Q_ OBJECT
319 * public:
320 * MyDialogComponent( QWidget *parentWidget,
321 * const QStringList &args );
322 * ...
323 * };
325 * typedef K_TYPELIST_2( MyPlugin, MyDialogComponent ) Products;
326 * K_EXPORT_COMPONENT_FACTORY( libmyplugin, KGenericFactory<Products> )
327 * \endcode
329 template <class Product, class ProductListTail,
330 class ParentType, class ParentTypeListTail>
331 class KGenericFactory< KTypeList<Product, ProductListTail>,
332 KTypeList<ParentType, ParentTypeListTail> >
333 : public KGenericFactoryBase<KTypeList<Product, ProductListTail> >
335 public:
336 explicit KGenericFactory( const char *componentName = 0, const char *catalogName = 0 )
337 : KGenericFactoryBase<KTypeList<Product, ProductListTail> >(componentName, catalogName)
339 explicit KGenericFactory( const KAboutData *data )
340 : KGenericFactoryBase<KTypeList<Product, ProductListTail> >(data)
344 protected:
345 virtual QObject *createObject( QObject *parent,
346 const char *className, const QStringList &args )
348 return KDEPrivate::MultiFactory< KTypeList< Product, ProductListTail >,
349 KTypeList< ParentType, ParentTypeListTail > >
350 ::create( 0, 0, parent,
351 className, args );
356 * vim: et sw=4
359 #endif