Qt Forum

    • Login
    • Search
    • Categories
    • Recent
    • Tags
    • Popular
    • Users
    • Groups
    • Search
    • Unsolved

    Call for Presentations - Qt World Summit

    Solved Using std::function as parameter for slot and signal

    General and Desktop
    4
    9
    5470
    Loading More Posts
    • 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.
    • CrazySiberianScientist
      CrazySiberianScientist last edited by CrazySiberianScientist

      Hi!
      How to set object of std::function as parameter for signal and slot?

      Example:

      signals:
          void sendSetProcFunc(const std::function<void (const QImage &,
                                                     QList<QPolygon> &,
                                                     QList<QImage> &)>
                           &procFunc);
      
      ...................................
      public slots:
          void onSetProcFunc(const std::function<void (const QImage &,
                                                     QList<QPolygon> &,
                                                     QList<QImage> &)>
                           &procFunc);
      

      Building in Qt 5.7 with MinGW_32bit gives next errors:


      debug\moc_QtCVGUI.cpp: In static member function 'static void QtCVGUI::qt_static_metacall(QObject*, QMetaObject::Call, int, void**)':
      debug\moc_QtCVGUI.cpp:131:128: warning: type qualifiers ignored on function return type [-Wignored-qualifiers]
      case 2: _t->sendSetProcFunc((reinterpret_cast< const std::function<const void( QImage&,QList<QPolygon>&,QList<QImage>&)>()>(_a[1]))); break;
      ^
      debug\moc_QtCVGUI.cpp:131:142: error: no matching function for call to 'QtCVGUI::sendSetProcFunc(const std::function<const void(QImage&, QList<QPolygon>&, QList<QImage>&)>&)'
      case 2: _t->sendSetProcFunc((reinterpret_cast< const std::function<const void( QImage&,QList<QPolygon>&,QList<QImage>&)>()>(_a[1]))); break;
      ^
      In file included from debug\moc_QtCVGUI.cpp:9:0:
      ****/QtCVGUI.h:49:10: note: candidate: void QtCVGUI::sendSetProcFunc(const std::function<void(const QImage&, QList<QPolygon>&, QList<QImage>&)>&)
      void sendSetProcFunc(const std::function<void (const QImage &,
      ^
      ****/QtCVGUI.h:49:10: note: no known conversion for argument 1 from 'const std::function<const void(QImage&, QList<QPolygon>&, QList<QImage>&)>' to 'const std::function<void(const QImage&, QList<QPolygon>&, QList<QImage>&)>&'


      Removing of all const and setting of std::function as usual variable (NOT reference) solve this problem (i.e. make succesful build).
      Why are there such restrictions and how to bypass them?

      void sendSetProcFunc(std::function<void (QImage &,
                                                     QList<QPolygon> &,
                                                     QList<QImage> &)>
                           procFunc);
      
      jsulm 1 Reply Last reply Reply Quote 0
      • jsulm
        jsulm Lifetime Qt Champion @CrazySiberianScientist last edited by

        @CrazySiberianScientist said in Using std::function as parameter for slot and signal:

        reinterpret_cast< const std::function<const void( QImage&,QList<QPolygon>&,QList<QImage>&)>

        Shouldn't your cast (why do you use reinterpret_cast actually? What type is _a?) be

        reinterpret_cast< std::function<void(const QImage&,QList<QPolygon>&,QList<QImage>&)>
        

        So, no const in front of std::function, no const in front of void and const for the first parameter.

        https://forum.qt.io/topic/113070/qt-code-of-conduct

        1 Reply Last reply Reply Quote 0
        • VRonin
          VRonin last edited by VRonin

          the problem is here QtCVGUI.h:49:10: note: no known conversion for argument 1 from 'const std::function<const void(QImage&, QList<QPolygon>&, QList<QImage>&)>' to 'const std::function<void(const QImage&, QList<QPolygon>&, QList<QImage>&)>&'

          notice std::function<const void vs std::function<void

          Difficult to tell you exactly what went wrong without seeing your emit call but my guess is you are trying to pass a function that has a signature like this: void MyClass::MyFunction(const QImage&, QList<QPolygon>&, QList<QImage>&) const and the final const screws you

          "La mort n'est rien, mais vivre vaincu et sans gloire, c'est mourir tous les jours"
          ~Napoleon Bonaparte

          On a crusade to banish setIndexWidget() from the holy land of Qt

          CrazySiberianScientist 1 Reply Last reply Reply Quote 0
          • CrazySiberianScientist
            CrazySiberianScientist @VRonin last edited by

            @VRonin
            In my code there isn't any emit with sendSetProcFunc .


            @jsulm said in Using std::function as parameter for slot and signal:

            Shouldn't your cast (why do you use reinterpret_cast actually? What type is _a?) be

            This isn't my cast, this cast of MOC.


            On bugtracker I created issue : https://bugreports.qt.io/browse/QTBUG-60539

            kshegunov 1 Reply Last reply Reply Quote 0
            • kshegunov
              kshegunov Moderators @CrazySiberianScientist last edited by kshegunov

              Probably a deficiency in moc's parsing abilities (no wonder with all the introduced additional complexity in c++11, I might add). Try to typedef and use the alias instead.
              E.g:

              typedef std::function<void (const QImage &, QList<QPolygon> &, QList<QImage> &)> UnnecessaryWrapper;
              
              signals:
                  void sendSetProcFunc(const UnnecessaryWrapper & procFunc);
              
              public slots:
                  void onSetProcFunc(const UnnecessaryWrapper & procFunc);
              

              Edit:
              I see that Thiago already triaged it as a moc issue. Okay, for the sake of argument try to typedef your argument type.

              Read and abide by the Qt Code of Conduct

              CrazySiberianScientist 1 Reply Last reply Reply Quote 3
              • CrazySiberianScientist
                CrazySiberianScientist @kshegunov last edited by CrazySiberianScientist

                @kshegunov

                I didn't properly check all combinations.
                This builds successfull even without typedef:

                void sendSetProcFunc(const std::function<void (/*const*/ QImage &,
                                                               QList<QPolygon> &,
                                                               QList<QImage> &)>
                                     &procFunc);
                
                
                void onSetProcFunc(const std::function<void (/*const*/ QImage &,
                                                               QList<QPolygon> &,
                                                               QList<QImage> &)>
                                     &procFunc);
                
                kshegunov 1 Reply Last reply Reply Quote 0
                • kshegunov
                  kshegunov Moderators @CrazySiberianScientist last edited by kshegunov

                  @CrazySiberianScientist said in Using std::function as parameter for slot and signal:

                  This builds successfull even without typedef

                  Because the moc won't have a const to place at the inappropriate place. My suggestion holds as a possible workaround nonetheless, as const QImage & is profoundly different from QImage &.

                  Read and abide by the Qt Code of Conduct

                  CrazySiberianScientist 1 Reply Last reply Reply Quote 2
                  • CrazySiberianScientist
                    CrazySiberianScientist @kshegunov last edited by CrazySiberianScientist

                    @kshegunov

                    Thank you. Your solution works.
                    But don't forget about (may be this is obvious for someone, but I will put this for others):

                    int main(){
                    ...
                       // May be this isn't good place for it
                       qRegisterMetaType<UnnecessaryWrapper>("UnnecessaryWrapper");
                    ...
                    }
                    
                    
                    
                    kshegunov 1 Reply Last reply Reply Quote 2
                    • kshegunov
                      kshegunov Moderators @CrazySiberianScientist last edited by

                      @CrazySiberianScientist said in Using std::function as parameter for slot and signal:

                         // May be this isn't good place for it
                         qRegisterMetaType<UnnecessaryWrapper>("UnnecessaryWrapper");
                      

                      This is exactly correct and also an appropriate place, but it is unneeded unless you're going to pass that callback across threads.
                      Anyway, I'm glad it worked.

                      Read and abide by the Qt Code of Conduct

                      1 Reply Last reply Reply Quote 0
                      • First post
                        Last post