Browse Source

Templated ctkPluginTracker for type safety.

Sascha Zelzer 14 years ago
parent
commit
7bda06907d

+ 1 - 8
Libs/PluginFramework/CMakeLists.txt

@@ -27,8 +27,6 @@ SET(KIT_SRCS
   ctkPluginFrameworkUtil.cpp
   ctkPluginManifest.cpp
   ctkPluginPrivate.cpp
-  #ctkPluginTracker.cpp
-  #ctkPluginTrackerPrivate.cpp
   ctkPlugins.cpp
   ctkRequirePlugin.cpp
   ctkServiceEvent.cpp
@@ -38,13 +36,8 @@ SET(KIT_SRCS
   ctkServiceReferencePrivate.cpp
   ctkServiceRegistration.cpp
   ctkServiceRegistrationPrivate.cpp
-  #ctkServiceTracker.cpp
-  #ctkServiceTrackerCustomizer.h
-  #ctkServiceTrackerPrivate.cpp
   ctkServices.cpp
   ctkServiceSlotEntry.cpp
-  #ctkTrackedPlugin.cpp
-  #ctkTrackedService.cpp
   ctkPluginStorage.cpp
   ctkVersion.cpp
   ctkVersionRange.cpp
@@ -60,7 +53,7 @@ SET(KIT_SRCS
 SET(KIT_MOC_SRCS
   ctkPluginFrameworkListeners_p.h
   ctkServiceFactory.h
-  #ctkTrackedPlugin_p.h
+  ctkTrackedPluginListener_p.h
   ctkTrackedServiceListener_p.h
 )
 

+ 53 - 36
Libs/PluginFramework/ctkPluginTracker.cpp

@@ -20,30 +20,31 @@
 =============================================================================*/
 
 
-#include "ctkPluginTracker.h"
-
 #include "ctkPluginContext.h"
 #include "ctkPluginTrackerPrivate.h"
 #include "ctkTrackedPlugin_p.h"
 
 #include <QDebug>
 
-ctkPluginTracker::~ctkPluginTracker()
+template<class T>
+ctkPluginTracker<T>::~ctkPluginTracker()
 {
 
 }
 
-ctkPluginTracker::ctkPluginTracker(ctkPluginContext* context, ctkPlugin::States stateMask,
-                 ctkPluginTrackerCustomizer* customizer)
-  : d_ptr(new ctkPluginTrackerPrivate(this, context, stateMask, customizer))
+template<class T>
+ctkPluginTracker<T>::ctkPluginTracker(ctkPluginContext* context, ctkPlugin::States stateMask,
+                                      PluginTrackerCustomizer* customizer)
+  : d_ptr(new PluginTrackerPrivate(this, context, stateMask, customizer))
 {
 
 }
 
-void ctkPluginTracker::open()
+template<class T>
+void ctkPluginTracker<T>::open()
 {
-  Q_D(ctkPluginTracker);
-  QSharedPointer<ctkTrackedPlugin> t;
+  Q_D(PluginTracker);
+  QSharedPointer<TrackedPlugin> t;
   {
     QMutexLocker lock(&d->mutex);
     if (d->trackedPlugin)
@@ -53,10 +54,10 @@ void ctkPluginTracker::open()
 
     if (d->DEBUG)
     {
-      qDebug() << "ctkPluginTracker::open";
+      qDebug() << "ctkPluginTracker<T>::open";
     }
 
-    t = QSharedPointer<ctkTrackedPlugin>(new ctkTrackedPlugin(this, d->customizer));
+    t = QSharedPointer<TrackedPlugin>(new TrackedPlugin(this, d->customizer));
     {
       QMutexLocker lockT(t.data());
       d->context->connectPluginListener(t.data(), SLOT(pluginChanged(ctkPluginEvent)), Qt::DirectConnection);
@@ -81,11 +82,12 @@ void ctkPluginTracker::open()
   t->trackInitial(); /* process the initial references */
 }
 
-void ctkPluginTracker::close()
+template<class T>
+void ctkPluginTracker<T>::close()
 {
-  Q_D(ctkPluginTracker);
+  Q_D(PluginTracker);
   QList<QSharedPointer<ctkPlugin> > plugins;
-  QSharedPointer<ctkTrackedPlugin> outgoing;
+  QSharedPointer<TrackedPlugin> outgoing;
   {
     QMutexLocker lock(&d->mutex);
     outgoing = d->trackedPlugin;
@@ -96,7 +98,7 @@ void ctkPluginTracker::close()
 
     if (d->DEBUG)
     {
-      qDebug() << "ctkPluginTracker::close";
+      qDebug() << "ctkPluginTracker<T>::close";
     }
 
     outgoing->close();
@@ -112,10 +114,11 @@ void ctkPluginTracker::close()
   }
 }
 
-QList<QSharedPointer<ctkPlugin> > ctkPluginTracker::getPlugins() const
+template<class T>
+QList<QSharedPointer<ctkPlugin> > ctkPluginTracker<T>::getPlugins() const
 {
-  Q_D(const ctkPluginTracker);
-  QSharedPointer<ctkTrackedPlugin> t = d->tracked();
+  Q_D(const PluginTracker);
+  QSharedPointer<TrackedPlugin> t = d->tracked();
   if (t.isNull())
   { /* if ctkPluginTracker is not open */
     return QList<QSharedPointer<ctkPlugin> >();
@@ -127,10 +130,11 @@ QList<QSharedPointer<ctkPlugin> > ctkPluginTracker::getPlugins() const
   }
 }
 
-QVariant ctkPluginTracker::getObject(QSharedPointer<ctkPlugin> plugin) const
+template<class T>
+T ctkPluginTracker<T>::getObject(QSharedPointer<ctkPlugin> plugin) const
 {
-  Q_D(const ctkPluginTracker);
-  QSharedPointer<ctkTrackedPlugin> t = d->tracked();
+  Q_D(const PluginTracker);
+  QSharedPointer<TrackedPlugin> t = d->tracked();
   if (t.isNull())
   {
     return QVariant();
@@ -142,10 +146,11 @@ QVariant ctkPluginTracker::getObject(QSharedPointer<ctkPlugin> plugin) const
   }
 }
 
-void ctkPluginTracker::remove(QSharedPointer<ctkPlugin> plugin)
+template<class T>
+void ctkPluginTracker<T>::remove(QSharedPointer<ctkPlugin> plugin)
 {
-  Q_D(ctkPluginTracker);
-  QSharedPointer<ctkTrackedPlugin> t = d->tracked();
+  Q_D(PluginTracker);
+  QSharedPointer<TrackedPlugin> t = d->tracked();
   if (t.isNull())
   {
     return;
@@ -153,10 +158,11 @@ void ctkPluginTracker::remove(QSharedPointer<ctkPlugin> plugin)
   t->untrack(plugin, ctkPluginEvent());
 }
 
-int ctkPluginTracker::size() const
+template<class T>
+int ctkPluginTracker<T>::size() const
 {
-  Q_D(const ctkPluginTracker);
-  QSharedPointer<ctkTrackedPlugin> t = d->tracked();
+  Q_D(const PluginTracker);
+  QSharedPointer<TrackedPlugin> t = d->tracked();
   if (t.isNull())
   {
     return 0;
@@ -168,10 +174,11 @@ int ctkPluginTracker::size() const
   }
 }
 
-int ctkPluginTracker::getTrackingCount() const
+template<class T>
+int ctkPluginTracker<T>::getTrackingCount() const
 {
-  Q_D(const ctkPluginTracker);
-  QSharedPointer<ctkTrackedPlugin> t = d->tracked();
+  Q_D(const PluginTracker);
+  QSharedPointer<TrackedPlugin> t = d->tracked();
   if (t.isNull())
   {
     return -1;
@@ -183,16 +190,25 @@ int ctkPluginTracker::getTrackingCount() const
   }
 }
 
-QVariant ctkPluginTracker::addingPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event)
+template<>
+inline QSharedPointer<ctkPlugin> ctkPluginTracker<QSharedPointer<ctkPlugin> >::addingPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event)
 {
   Q_UNUSED(event)
 
-  QVariant var;
-  var.setValue(plugin);
-  return var;
+  return plugin;
+}
+
+template<class T>
+T ctkPluginTracker<T>::addingPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event)
+{
+  Q_UNUSED(plugin)
+  Q_UNUSED(event)
+
+  return 0;
 }
 
-void ctkPluginTracker::modifiedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event, QVariant object)
+template<class T>
+void ctkPluginTracker<T>::modifiedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event, T object)
 {
   Q_UNUSED(plugin)
   Q_UNUSED(event)
@@ -200,7 +216,8 @@ void ctkPluginTracker::modifiedPlugin(QSharedPointer<ctkPlugin> plugin, const ct
   /* do nothing */
 }
 
-void ctkPluginTracker::removedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event, QVariant object)
+template<class T>
+void ctkPluginTracker<T>::removedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event, T object)
 {
   Q_UNUSED(plugin)
   Q_UNUSED(event)

+ 33 - 11
Libs/PluginFramework/ctkPluginTracker.h

@@ -30,7 +30,8 @@
 #include "ctkPlugin.h"
 #include "ctkPluginTrackerCustomizer.h"
 
-class ctkPluginTrackerPrivate;
+template<class T> class ctkTrackedPlugin;
+template<class T> class ctkPluginTrackerPrivate;
 
 /**
  * The <code>ctkPluginTracker</code> class simplifies tracking plugins much like
@@ -53,9 +54,13 @@ class ctkPluginTrackerPrivate;
  * <code>ctkPluginTrackerCustomizer</code> implementations must also be
  * thread-safe.
  *
- * @ThreadSafe
+ * \tparam T The type of the tracked object. The type must be an assignable
+ *         datatype, provide a boolean conversion function, and provide
+ *         a constructor and an assignment operator which can handle 0 as an argument.
+ * \threadsafe
  */
-class CTK_PLUGINFW_EXPORT ctkPluginTracker : protected ctkPluginTrackerCustomizer
+template<class T = QSharedPointer<ctkPlugin> >
+class ctkPluginTracker : protected ctkPluginTrackerCustomizer<T>
 {
 public:
 
@@ -85,7 +90,7 @@ public:
    * @see ctkPlugin#getState()
    */
   ctkPluginTracker(ctkPluginContext* context, ctkPlugin::States stateMask,
-                   ctkPluginTrackerCustomizer* customizer = 0);
+                   ctkPluginTrackerCustomizer<T>* customizer = 0);
 
   /**
    * Open this <code>ctkPluginTracker</code> and begin tracking plugins.
@@ -131,7 +136,7 @@ public:
    *         <code>null</code> if the specified <code>ctkPlugin</code> is not
    *         being tracked.
    */
-  QVariant getObject(QSharedPointer<ctkPlugin> plugin) const;
+  T getObject(QSharedPointer<ctkPlugin> plugin) const;
 
   /**
    * Remove a plugin from this <code>ctkPluginTracker</code>.
@@ -200,7 +205,7 @@ protected:
    * @return The specified plugin.
    * @see ctkPluginTrackerCustomizer::addingPlugin(ctkPlugin*, const ctkPluginEvent&)
    */
-  QVariant addingPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event);
+  T addingPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event);
 
   /**
    * Default implementation of the
@@ -220,7 +225,7 @@ protected:
    * @param object The customized object for the specified ctkPlugin.
    * @see ctkPluginTrackerCustomizer::modifiedPlugin(ctkPlugin*, const ctkPluginEvent&, QVariant)
    */
-  void modifiedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event, QVariant object);
+  void modifiedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event, T object);
 
   /**
    * Default implementation of the
@@ -240,15 +245,32 @@ protected:
    * @param object The customized object for the specified plugin.
    * @see ctkPluginTrackerCustomizer::removedPlugin(ctkPlugin*, const ctkPluginEvent&, QVariant)
    */
-  void removedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event, QVariant object);
+  void removedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event, T object);
 
 private:
 
-  friend class ctkTrackedPlugin;
+  typedef ctkPluginTracker<T> PluginTracker;
+  typedef ctkTrackedPlugin<T> TrackedPlugin;
+  typedef ctkPluginTrackerPrivate<T> PluginTrackerPrivate;
+  typedef ctkPluginTrackerCustomizer<T> PluginTrackerCustomizer;
 
-  Q_DECLARE_PRIVATE(ctkPluginTracker)
+  friend class ctkTrackedPlugin<T>;
+  friend class ctkPluginTrackerPrivate<T>;
 
-  const QScopedPointer<ctkPluginTrackerPrivate> d_ptr;
+  inline PluginTrackerPrivate* d_func()
+  {
+    return reinterpret_cast<PluginTrackerPrivate*>(qGetPtrHelper(d_ptr));
+  }
+
+  inline const PluginTrackerPrivate* d_func() const
+  {
+    return reinterpret_cast<const PluginTrackerPrivate*>(qGetPtrHelper(d_ptr));
+  }
+
+  const QScopedPointer<PluginTrackerPrivate> d_ptr;
 };
 
+
+#include "ctkPluginTracker.cpp"
+
 #endif // CTKPLUGINTRACKER_H

+ 7 - 5
Libs/PluginFramework/ctkPluginTrackerCustomizer.h

@@ -32,7 +32,7 @@ class ctkPlugin;
 
 /**
  * The <code>ctkPluginTrackerCustomizer</code> interface allows a
- * <code>ctkPluginTracker</code> to customize the <code>Plugin</code>s that are
+ * <code>ctkPluginTracker</code> to customize the <code>ctkPlugin</code>s that are
  * tracked. A <code>ctkPluginTrackerCustomizer</code> is called when a plugin is
  * being added to a <code>ctkPluginTracker</code>. The
  * <code>ctkPluginTrackerCustomizer</code> can then return an object for the
@@ -54,8 +54,10 @@ class ctkPlugin;
  * <code>ctkPluginTrackerCustomizer</code> implementations must also be
  * thread-safe.
  *
- * @ThreadSafe
+ * \tparam T The type of the tracked object.
+ * \threadsafe
  */
+template<class T>
 struct ctkPluginTrackerCustomizer {
 
   virtual ~ctkPluginTrackerCustomizer() {}
@@ -81,7 +83,7 @@ struct ctkPluginTrackerCustomizer {
    *         object or <code>null</code> if the specified <code>ctkPlugin</code>
    *         object should not be tracked.
    */
-  virtual QVariant addingPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event) = 0;
+  virtual T addingPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event) = 0;
 
   /**
    * A plugin tracked by the <code>ctkPluginTracker</code> has been modified.
@@ -98,7 +100,7 @@ struct ctkPluginTrackerCustomizer {
    * @param object The tracked object for the specified plugin.
    */
   virtual void modifiedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event,
-      QVariant object) = 0;
+      T object) = 0;
 
   /**
    * A plugin tracked by the <code>ctkPluginTracker</code> has been removed.
@@ -115,7 +117,7 @@ struct ctkPluginTrackerCustomizer {
    * @param object The tracked object for the specified plugin.
    */
   virtual void removedPlugin(QSharedPointer<ctkPlugin> plugin, const ctkPluginEvent& event,
-      QVariant object) = 0;
+      T object) = 0;
 };
 
 #endif // CTKPLUGINTRACKERCUSTOMIZER_H

+ 10 - 9
Libs/PluginFramework/ctkPluginTrackerPrivate.cpp

@@ -20,22 +20,22 @@
 =============================================================================*/
 
 
-#include "ctkPluginTrackerPrivate.h"
-
 #include "ctkTrackedPlugin_p.h"
-#include "ctkPluginTracker.h"
 
-const bool ctkPluginTrackerPrivate::DEBUG = true;
+template<class T>
+const bool ctkPluginTrackerPrivate<T>::DEBUG = true;
 
-ctkPluginTrackerPrivate::ctkPluginTrackerPrivate(
-    ctkPluginTracker* pt, ctkPluginContext* context,
-    ctkPlugin::States stateMask, ctkPluginTrackerCustomizer* customizer)
+template<class T>
+ctkPluginTrackerPrivate<T>::ctkPluginTrackerPrivate(
+    ctkPluginTracker<T>* pt, ctkPluginContext* context,
+    ctkPlugin::States stateMask, ctkPluginTrackerCustomizer<T>* customizer)
   : context(context), customizer(customizer), mask(stateMask), q_ptr(pt)
 {
   this->customizer = customizer ? customizer : q_func();
 }
 
-ctkPluginTrackerPrivate::~ctkPluginTrackerPrivate()
+template<class T>
+ctkPluginTrackerPrivate<T>::~ctkPluginTrackerPrivate()
 {
   if (customizer != q_func())
   {
@@ -43,7 +43,8 @@ ctkPluginTrackerPrivate::~ctkPluginTrackerPrivate()
   }
 }
 
-QSharedPointer<ctkTrackedPlugin> ctkPluginTrackerPrivate::tracked() const
+template<class T>
+QSharedPointer<ctkTrackedPlugin<T> > ctkPluginTrackerPrivate<T>::tracked() const
 {
   return trackedPlugin;
 }

+ 20 - 11
Libs/PluginFramework/ctkPluginTrackerPrivate.h

@@ -28,17 +28,14 @@
 #include <QSharedPointer>
 #include <QMutex>
 
-class ctkPluginTracker;
-class ctkPluginContext;
-class ctkTrackedPlugin;
-struct ctkPluginTrackerCustomizer;
 
+template<class T>
 class ctkPluginTrackerPrivate
 {
 public:
-  ctkPluginTrackerPrivate(ctkPluginTracker* pt,
+  ctkPluginTrackerPrivate(ctkPluginTracker<T>* pt,
                           ctkPluginContext* context, ctkPlugin::States stateMask,
-                          ctkPluginTrackerCustomizer* customizer);
+                          ctkPluginTrackerCustomizer<T>* customizer);
 
   ~ctkPluginTrackerPrivate();
 
@@ -49,7 +46,7 @@ public:
    *
    * @return The current ctkTrackedPlugin object.
    */
-  QSharedPointer<ctkTrackedPlugin> tracked() const;
+  QSharedPointer<ctkTrackedPlugin<T> > tracked() const;
 
   /* set this to true to compile in debug messages */
   static const bool DEBUG; //	= false;
@@ -62,13 +59,13 @@ public:
   /**
    * The <code>ctkPluginTrackerCustomizer</code> object for this tracker.
    */
-  ctkPluginTrackerCustomizer* customizer;
+  ctkPluginTrackerCustomizer<T>* customizer;
 
   /**
    * Tracked plugins: <code>ctkPlugin</code> object -> customized Object and
    * plugin listener slot.
    */
-  QSharedPointer<ctkTrackedPlugin> trackedPlugin;
+  QSharedPointer<ctkTrackedPlugin<T> > trackedPlugin;
 
   /**
    * State mask for plugins being tracked. This field contains the ORed values
@@ -80,9 +77,21 @@ public:
 
 private:
 
-  Q_DECLARE_PUBLIC(ctkPluginTracker)
+  inline ctkPluginTracker<T>* q_func()
+  {
+    return static_cast<ctkPluginTracker<T> *>(q_ptr);
+  }
 
-  ctkPluginTracker * const q_ptr;
+  inline const ctkPluginTracker<T>* q_func() const
+  {
+    return static_cast<const ctkPluginTracker<T> *>(q_ptr);
+  }
+
+  friend class ctkPluginTracker<T>;
+
+  ctkPluginTracker<T> * const q_ptr;
 };
 
+#include "ctkPluginTrackerPrivate.cpp"
+
 #endif // CTKPLUGINTRACKERPRIVATE_H

+ 20 - 18
Libs/PluginFramework/ctkTrackedPlugin.cpp

@@ -20,25 +20,22 @@
 =============================================================================*/
 
 
-#include "ctkTrackedPlugin_p.h"
-
-#include "ctkPluginTracker.h"
-#include "ctkPluginTrackerPrivate.h"
-
-ctkTrackedPlugin::ctkTrackedPlugin(ctkPluginTracker* pluginTracker,
-                 ctkPluginTrackerCustomizer* customizer)
+template<class T>
+ctkTrackedPlugin<T>::ctkTrackedPlugin(ctkPluginTracker<T>* pluginTracker,
+                 ctkPluginTrackerCustomizer<T>* customizer)
   : pluginTracker(pluginTracker), customizer(customizer)
 {
 
 }
 
-void ctkTrackedPlugin::pluginChanged(const ctkPluginEvent& event)
+template<class T>
+void ctkTrackedPlugin<T>::pluginChanged(const ctkPluginEvent& event)
 {
   /*
    * Check if we had a delayed call (which could happen when we
    * close).
    */
-  if (closed)
+  if (this->closed)
   {
     return;
   }
@@ -47,12 +44,12 @@ void ctkTrackedPlugin::pluginChanged(const ctkPluginEvent& event)
   ctkPlugin::State state = plugin->getState();
   if (pluginTracker->d_func()->DEBUG)
   {
-    qDebug() << "ctkTrackedPlugin::pluginChanged[" << state << "]: " << *plugin;
+    qDebug() << "ctkTrackedPlugin<T>::pluginChanged[" << state << "]: " << *plugin;
   }
 
   if (pluginTracker->d_func()->mask & state)
   {
-    track(plugin, event);
+    this->track(plugin, event);
     /*
      * If the customizer throws an exception, it is safe
      * to let it propagate
@@ -60,7 +57,7 @@ void ctkTrackedPlugin::pluginChanged(const ctkPluginEvent& event)
   }
   else
   {
-    untrack(plugin, event);
+    this->untrack(plugin, event);
     /*
      * If the customizer throws an exception, it is safe
      * to let it propagate
@@ -68,20 +65,25 @@ void ctkTrackedPlugin::pluginChanged(const ctkPluginEvent& event)
   }
 }
 
-QVariant ctkTrackedPlugin::customizerAdding(QSharedPointer<ctkPlugin> item,
-    ctkPluginEvent related)
+template<class T>
+T ctkTrackedPlugin<T>::customizerAdding(QSharedPointer<ctkPlugin> item,
+                                     const ctkPluginEvent& related)
 {
   return customizer->addingPlugin(item, related);
 }
 
-void ctkTrackedPlugin::customizerModified(QSharedPointer<ctkPlugin> item,
-    ctkPluginEvent related, QVariant object)
+template<class T>
+void ctkTrackedPlugin<T>::customizerModified(QSharedPointer<ctkPlugin> item,
+                                          const ctkPluginEvent& related,
+                                          T object)
 {
   customizer->modifiedPlugin(item, related, object);
 }
 
-void ctkTrackedPlugin::customizerRemoved(QSharedPointer<ctkPlugin> item,
-    ctkPluginEvent related, QVariant object)
+template<class T>
+void ctkTrackedPlugin<T>::customizerRemoved(QSharedPointer<ctkPlugin> item,
+                                         const ctkPluginEvent& related,
+                                         T object)
 {
   customizer->removedPlugin(item, related, object);
 }

+ 52 - 0
Libs/PluginFramework/ctkTrackedPluginListener_p.h

@@ -0,0 +1,52 @@
+/*=============================================================================
+
+  Library: CTK
+
+  Copyright (c) German Cancer Research Center,
+    Division of Medical and Biological Informatics
+
+  Licensed under the Apache License, Version 2.0 (the "License");
+  you may not use this file except in compliance with the License.
+  You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+  Unless required by applicable law or agreed to in writing, software
+  distributed under the License is distributed on an "AS IS" BASIS,
+  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+  See the License for the specific language governing permissions and
+  limitations under the License.
+
+=============================================================================*/
+
+
+#ifndef CTKTRACKEDPLUGINLISTENER_P_H
+#define CTKTRACKEDPLUGINLISTENER_P_H
+
+#include <QObject>
+
+#include "ctkPluginEvent.h"
+
+class CTK_PLUGINFW_EXPORT ctkTrackedPluginListener : public QObject
+{
+  Q_OBJECT
+
+public:
+  ctkTrackedPluginListener(QObject *parent = 0)
+    : QObject(parent)
+  {}
+
+public slots:
+
+  /**
+   * Slot for the <code>ctkPluginTracker</code>
+   * class. This method must NOT be synchronized to avoid deadlock
+   * potential.
+   *
+   * @param event <code>ctkPluginEvent</code> object from the framework.
+   */
+  virtual void pluginChanged(const ctkPluginEvent& event) = 0;
+
+};
+
+#endif // CTKTRACKEDPLUGINLISTENER_P_H

+ 15 - 15
Libs/PluginFramework/ctkTrackedPlugin_p.h

@@ -25,23 +25,21 @@
 
 #include <QSharedPointer>
 
+#include "ctkTrackedPluginListener_p.h"
 #include "ctkPluginAbstractTracked_p.h"
 #include "ctkPluginEvent.h"
 #include "ctkPlugin.h"
 
-class ctkPluginTracker;
-struct ctkPluginTrackerCustomizer;
 
-class ctkTrackedPlugin : public QObject,
-    public ctkPluginAbstractTracked<QSharedPointer<ctkPlugin>, ctkPluginEvent>
+template<class T>
+class ctkTrackedPlugin : public ctkTrackedPluginListener,
+    public ctkPluginAbstractTracked<QSharedPointer<ctkPlugin>, T, ctkPluginEvent>
 {
-  Q_OBJECT
 
 public:
-  ctkTrackedPlugin(ctkPluginTracker* pluginTracker,
-                   ctkPluginTrackerCustomizer* customizer);
+  ctkTrackedPlugin(ctkPluginTracker<T>* pluginTracker,
+                   ctkPluginTrackerCustomizer<T>* customizer);
 
-private slots:
 
   /**
    * Slot for the <code>ctkPluginTracker</code>
@@ -54,10 +52,10 @@ private slots:
 
 private:
 
-  typedef ctkPluginAbstractTracked<QSharedPointer<ctkPlugin>, ctkPluginEvent> Superclass;
+  typedef ctkPluginAbstractTracked<QSharedPointer<ctkPlugin>, T, ctkPluginEvent> Superclass;
 
-  ctkPluginTracker* pluginTracker;
-  ctkPluginTrackerCustomizer* customizer;
+  ctkPluginTracker<T>* pluginTracker;
+  ctkPluginTrackerCustomizer<T>* customizer;
 
   /**
    * Call the specific customizer adding method. This method must not be
@@ -68,8 +66,8 @@ private:
    * @return Customized object for the tracked item or <code>null</code>
    *         if the item is not to be tracked.
    */
-  QVariant customizerAdding(QSharedPointer<ctkPlugin> item,
-                            ctkPluginEvent related);
+  T customizerAdding(QSharedPointer<ctkPlugin> item,
+                     const ctkPluginEvent& related);
 
   /**
    * Call the specific customizer modified method. This method must not be
@@ -80,7 +78,7 @@ private:
    * @param object Customized object for the tracked item.
    */
   void customizerModified(QSharedPointer<ctkPlugin> item,
-                          ctkPluginEvent related, QVariant object);
+                          const ctkPluginEvent& related, T object);
 
   /**
    * Call the specific customizer removed method. This method must not be
@@ -91,7 +89,9 @@ private:
    * @param object Customized object for the tracked item.
    */
   void customizerRemoved(QSharedPointer<ctkPlugin> item,
-                         ctkPluginEvent related, QVariant object);
+                         const ctkPluginEvent& related, T object);
 };
 
+#include "ctkTrackedPlugin.cpp"
+
 #endif // CTKTRACKEDPLUGIN_P_H