Qt Forum

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

    Update: Forum Guidelines & Code of Conduct

    How to get the sender() in a C++ lambda signal slot handler?

    General and Desktop
    7
    12
    9620
    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.
    • P
      philk last edited by VRonin

      When I call signal() from within a lambda function its always null.

      connect(senderObject, &Sender::signal, this, [=]() {
        QObject* sender = sender(); // always null?
      });
      
      1 Reply Last reply Reply Quote 0
      • sierdzio
        sierdzio Moderators last edited by VRonin

        Try with:

        connect(senderObject, &Sender::signal, this, [&]() {
          QObject* sender = sender();
        });
        

        (Z(:^

        1 Reply Last reply Reply Quote 2
        • P
          philk last edited by

          This does not work, sender returns nullptr.

          1 Reply Last reply Reply Quote 0
          • D
            dvolosnykh last edited by

            I have experienced the same problem several times.

            1 Reply Last reply Reply Quote 0
            • A
              AndreasF last edited by

              I know, it's an old thread, but for information:

              		QLineEdit* senderObject = new QLineEdit(this);
              		connect(senderObject, &QLineEdit::returnPressed, [senderObject, this]() 
              		{ 
              			if (senderObject && !senderObject->text().simplified().isEmpty())
              			{ 
              				QString txt = senderObject->text().simplified();
              				Icons()[txt];
              				senderObject->close();
              				iconListModel_->clearModelData(true);
              				iconListModel_->setModelData();
              			}
              		});
              
              1 Reply Last reply Reply Quote 2
              • aha_1980
                aha_1980 Lifetime Qt Champion last edited by

                Hi all,

                I just encountered the same problem and the correct solution is this: https://stackoverflow.com/questions/19719397/qt-slots-and-c11-lambda

                In short: don't use sender() within the lambda, capture senderObject instead:

                connect(senderObject, &Sender::signal, [senderObject, this]() {
                  // use senderObject here
                });
                

                Works like a charm.

                Qt has to stay free or it will die.

                mrjj 1 Reply Last reply Reply Quote 6
                • mrjj
                  mrjj Lifetime Qt Champion @aha_1980 last edited by

                  @aha_1980
                  But what do you do when hook up multiple objects to same lambda slot ?
                  Capture them all ?

                  aha_1980 VRonin 2 Replies Last reply Reply Quote 0
                  • aha_1980
                    aha_1980 Lifetime Qt Champion @mrjj last edited by

                    @mrjj

                    From my recent (and limited) experience, I'd say you better use the classical "member function" slot here, otherwise your code will get ugly.

                    Qt has to stay free or it will die.

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

                      @mrjj said in How to get the sender() in a C++ lambda signal slot handler?:

                      But what do you do when hook up multiple objects to same lambda slot ?

                      if they are all pointers just use [=]. The compiler will take care to capture all and nothing more than what you need.

                      "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

                      aha_1980 1 Reply Last reply Reply Quote 0
                      • aha_1980
                        aha_1980 Lifetime Qt Champion @VRonin last edited by

                        @VRonin said in How to get the sender() in a C++ lambda signal slot handler?:

                        if they are all pointers just use [=]. The compiler will take care to capture all and nothing more than what you need

                        Yeah, but you still need to find out which one emitted the signal inside the lambda...

                        Qt has to stay free or it will die.

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

                          Alternatively use std::bind

                          const auto myLambda = [](QObject* sender, bool pressed)->void{
                          QPushButton* const senderButton= qobject_cast<QPushButton*>(sender);
                          Q_ASSERT(senderButton);
                          qDebug() << senderButton->text() << pressed;
                          };
                          QObject::connect(button1,&QPushButton::clicked,std::bind(myLambda,button1,std::placeholders::_1));
                          QObject::connect(button2,&QPushButton::clicked,std::bind(myLambda,button2,std::placeholders::_1));
                          

                          "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

                          aha_1980 1 Reply Last reply Reply Quote 8
                          • aha_1980
                            aha_1980 Lifetime Qt Champion @VRonin last edited by

                            @VRonin Cool! Will need to try this but looks promising.

                            Qt has to stay free or it will die.

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