Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Plugins and Signal/Slot mechanism
Forum Updated to NodeBB v4.3 + New Features

Plugins and Signal/Slot mechanism

Scheduled Pinned Locked Moved General and Desktop
11 Posts 3 Posters 15.5k Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • G Offline
    G Offline
    goetz
    wrote on last edited by
    #2

    I can't see why that's not a good solution?

    If you provide us with your implementation for getToolbar() and getObject() we probably can help further. Do both functions return the same object?

    Also: It is definitely NOT possible to declare signals and slots in an interface, as the inheritance from QObjet is forbidden there.

    If you declare your interfaces with the proper macros you can use qobject_cast and test if a plugin implements a certain interface.

    See the Docs on "qobject_cast":http://doc.qt.nokia.com/4.7/qobject.html#qobject_cast and the "Plug & Paint Example":http://doc.qt.nokia.com/4.7/tools-plugandpaint.html for this.

    http://www.catb.org/~esr/faqs/smart-questions.html

    1 Reply Last reply
    0
    • F Offline
      F Offline
      Franzk
      wrote on last edited by
      #3

      When inheriting from QObject in plugin interfaces, you should have all that in a separate shared lib, so the meta object is properly accessed. Qt Creator is one example of this.

      "Horse sense is the thing a horse has which keeps it from betting on people." -- W.C. Fields

      http://www.catb.org/~esr/faqs/smart-questions.html

      1 Reply Last reply
      0
      • F Offline
        F Offline
        Franzk
        wrote on last edited by
        #4

        Besides that, the plugin will always be seen as or even has to be a QObject, so you can connect to those signals anyway. The only downside is that the signal and slot names aren't clear from the interface...

        "Horse sense is the thing a horse has which keeps it from betting on people." -- W.C. Fields

        http://www.catb.org/~esr/faqs/smart-questions.html

        1 Reply Last reply
        0
        • J Offline
          J Offline
          julu
          wrote on last edited by
          #5

          [quote author="Volker" date="1288282846"]
          If you provide us with your implementation for getToolbar() and getObject() we probably can help further. Do both functions return the same object?
          [/quote]
          No, one returns a member, the other the whole class.
          @
          QWidget* plugin_Toolbar::getToolbar()
          {
          return(m_toolbar);
          }

          QObject* plugin_Toolbar::getObject()
          {
          return(this);
          }
          @

          [quote author="Volker" date="1288282846"]
          Also: It is definitely NOT possible to declare signals and slots in an interface, as the inheritance from QObjet is forbidden there.
          [/quote]
          Allright, I've tried to do this for quite a while, because I thought of having the signals/slots in the interface would be a nice thing. Knowing this prevents me from further failure.
          W/o, the interface isn't fat, so good thing.

          [quote author="Franzk" date="1288329878"]Besides that, the plugin will always be seen as or even has to be a QObject, so you can connect to those signals anyway. The only downside is that the signal and slot names aren't clear from the interface...[/quote]
          Okay, I can live with that.

          Thank you for your help!

          1 Reply Last reply
          0
          • G Offline
            G Offline
            goetz
            wrote on last edited by
            #6

            You can shorten your connect a bit:

            @
            connect(toolbar_plugin, SIGNAL(buttonClicked()),
            mainWindow, SLOT(close()));
            @

            Calling getObject() on plugin_Toolbar is redundant, as both pointers are identical.

            Unfortunately it's not reliable in the client code, that uses the plugin, because the connected signal is not guaranteed to exist in the plugin. You will notice this only at runtime (watch console output for QObjects warnings about failed connections). Alternatively you can use "QMetaObject":http://doc.qt.nokia.com/4.7/qmetaobject.html to look if the object has the wanted signal.

            You can get around this limitation like this:

            Create an abstract base class (like MyAbstractToolbarPlugin), that inherits from OQbject (and probably from non-QObject IBasePlugin), and declare the signal there.

            In your concrete plugin, inherit from MyAbstractToolbarPlugin, then you definitely do have the signal.

            Of course, this solution has another, different downside: You can only implement one QObject base class per plugin.

            http://www.catb.org/~esr/faqs/smart-questions.html

            1 Reply Last reply
            0
            • J Offline
              J Offline
              julu
              wrote on last edited by
              #7

              Allright, I think I've already tried this by doing the following:

              Interface class:
              @
              class IBasePlugin
              {
              public:
              virtual ~IBasePlugin(){}

              virtual QString name() = 0;
              virtual QString version() = 0;
              

              };

              class IToolbar : public IModule, public QObject
              {
              Q_OBJECT
              public:
              virtual ~IToolbar(){}
              virtual QWidget* getToolbar() = 0;
              virtual QObject* getObject() = 0;
              signals:
              void exitClicked();
              };
              @

              And changing the implementation to:
              @
              class plugin_Toolbar : /public QObject,/ public IToolbar
              {
              Q_OBJECT
              Q_INTERFACES(IToolbar IBasePlugin)

              public:
              plugin_Toolbar();

              QString name()    { return "abc"; }
              QString version() { return "1"; }
              
              QWidget* getToolbar();
              QObject* getObject();
              

              signals:
              void buttonClicked();
              @

              But with this I'm getting errors:

              in function ~IToolbar
              undefined reference to vtable for IToolbar

              1 Reply Last reply
              0
              • G Offline
                G Offline
                goetz
                wrote on last edited by
                #8

                In your plugin, did you link against the lib/object file of IToolbar?

                http://www.catb.org/~esr/faqs/smart-questions.html

                1 Reply Last reply
                0
                • G Offline
                  G Offline
                  goetz
                  wrote on last edited by
                  #9

                  Ah, and I forgot to mention: You can/should omit IToolbar from the Q_INTERFACES macro, as you directly inherit from it.

                  http://www.catb.org/~esr/faqs/smart-questions.html

                  1 Reply Last reply
                  0
                  • J Offline
                    J Offline
                    julu
                    wrote on last edited by
                    #10

                    [quote author="Volker" date="1288343476"]Ah, and I forgot to mention: You can/should omit IToolbar from the Q_INTERFACES macro, as you directly inherit from it.[/quote]
                    Okay, the reason I'm doing this is is to be able to do a qobject_cast to IToolbar. If I use only this macro
                    @
                    Q_INTERFACES(IBasePlugin)
                    @
                    the cast to IToolbar fails.

                    Now I finally got it working, in my Plugins .pro I had to add the header file of the interface(s)
                    @
                    ...
                    HEADERS +=
                    plugin_toolbarright.h
                    ../../interfaces.h #!!! important
                    ...
                    @
                    So thanks @ all, the cryptic undefined references to vtable were quite confusing...

                    Hints for plugin writers:
                    Signals can't be declared virtual, but slots can.

                    1 Reply Last reply
                    0
                    • G Offline
                      G Offline
                      goetz
                      wrote on last edited by
                      #11

                      The qobject_cast to IToolbar should work without listing it in the macro. It's the same as if you inherited from QLabel.

                      But why would you object_cast to IToolbar anyway? That's only needed if you downcast from a QObject pointer to an IToolbar pointer. You can always safely assign a plugin_Toolbar pointer to an IToolbar pointer thanks to inheritance.

                      http://www.catb.org/~esr/faqs/smart-questions.html

                      1 Reply Last reply
                      0

                      • Login

                      • Login or register to search.
                      • First post
                        Last post
                      0
                      • Categories
                      • Recent
                      • Tags
                      • Popular
                      • Users
                      • Groups
                      • Search
                      • Get Qt Extensions
                      • Unsolved