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. Lambda that uses signal argument to connect to a slot

Lambda that uses signal argument to connect to a slot

Scheduled Pinned Locked Moved Solved General and Desktop
18 Posts 5 Posters 18.8k Views
  • 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.
  • O Offline
    O Offline
    ofmrew
    wrote on 31 Oct 2018, 19:02 last edited by
    #1

    I have a signal that has a string as an argument that I want to connect to the StatusBar show message. The following works, but it requires me to declare a variable, mouseLocString. Is the a way to capture the argument being passed?

    connect(ui->canvas, &MyCanvas::mouseLoc,
                [this](){this->ui->statusBar->showMessage(this->ui->canvas->mouseLocString, 0);});
    

    I know that I can, and probably should, change the signal to have both a string and an int. But I would like to know how to capture a signal argument in a lambda. Lambdas are really nice.

    S 1 Reply Last reply 31 Oct 2018, 20:12
    0
    • O ofmrew
      31 Oct 2018, 19:02

      I have a signal that has a string as an argument that I want to connect to the StatusBar show message. The following works, but it requires me to declare a variable, mouseLocString. Is the a way to capture the argument being passed?

      connect(ui->canvas, &MyCanvas::mouseLoc,
                  [this](){this->ui->statusBar->showMessage(this->ui->canvas->mouseLocString, 0);});
      

      I know that I can, and probably should, change the signal to have both a string and an int. But I would like to know how to capture a signal argument in a lambda. Lambdas are really nice.

      S Offline
      S Offline
      sierdzio
      Moderators
      wrote on 31 Oct 2018, 20:12 last edited by
      #2

      @ofmrew said in Lambda that uses signal argument to connect to a slot:

      [this]( ){
             ^
             |
           here
      

      This is where you put arguments in a lambda. For example:

      [this](int someInt) { qDebug() << someInt; }
      

      (Z(:^

      O 1 Reply Last reply 31 Oct 2018, 20:24
      4
      • S sierdzio
        31 Oct 2018, 20:12

        @ofmrew said in Lambda that uses signal argument to connect to a slot:

        [this]( ){
               ^
               |
             here
        

        This is where you put arguments in a lambda. For example:

        [this](int someInt) { qDebug() << someInt; }
        
        O Offline
        O Offline
        ofmrew
        wrote on 31 Oct 2018, 20:24 last edited by
        #3

        @sierdzio What if the someInt in your response is created on the fly and only exists as an argument in the signal. I has no name; that is why in my example code I had to declare a variable in which to store a value and be able to address it by name.

        S 1 Reply Last reply 31 Oct 2018, 20:27
        0
        • S Offline
          S Offline
          SGaist
          Lifetime Qt Champion
          wrote on 31 Oct 2018, 20:27 last edited by
          #4

          From what you wrote, the signature of mouseLoc isMyCanvas::mouseLoc(int someInt) so that's exactly the use case of someInt.

          Interested in AI ? www.idiap.ch
          Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

          O 1 Reply Last reply 31 Oct 2018, 21:45
          2
          • O ofmrew
            31 Oct 2018, 20:24

            @sierdzio What if the someInt in your response is created on the fly and only exists as an argument in the signal. I has no name; that is why in my example code I had to declare a variable in which to store a value and be able to address it by name.

            S Offline
            S Offline
            sierdzio
            Moderators
            wrote on 31 Oct 2018, 20:27 last edited by
            #5

            @ofmrew said in Lambda that uses signal argument to connect to a slot:

            @sierdzio What if the someInt in your response is created on the fly and only exists as an argument in the signal. I has no name; that is why in my example code I had to declare a variable in which to store a value and be able to address it by name.

            Does not matter if it has a name or not. Compiler cares for number of arguments and their types, not how they are called.

            (Z(:^

            1 Reply Last reply
            4
            • S SGaist
              31 Oct 2018, 20:27

              From what you wrote, the signature of mouseLoc isMyCanvas::mouseLoc(int someInt) so that's exactly the use case of someInt.

              O Offline
              O Offline
              ofmrew
              wrote on 31 Oct 2018, 21:45 last edited by
              #6

              @SGaist This is what I was looking for. I know bad grammar. I will try it tomorrow. Thanks.

              O 1 Reply Last reply 1 Nov 2018, 18:37
              0
              • O ofmrew
                31 Oct 2018, 21:45

                @SGaist This is what I was looking for. I know bad grammar. I will try it tomorrow. Thanks.

                O Offline
                O Offline
                ofmrew
                wrote on 1 Nov 2018, 18:37 last edited by
                #7

                @ofmrew Did not work. I tried

                    connect(ui->canvas, &MyCanvas::mouseLoc,
                               [this](){this->ui->statusBar->showMessage(MyCanvas::mouseLoc(QString st), 0);});
                

                I know it does not look correct, but what should it be?

                J 1 Reply Last reply 1 Nov 2018, 19:11
                0
                • O ofmrew
                  1 Nov 2018, 18:37

                  @ofmrew Did not work. I tried

                      connect(ui->canvas, &MyCanvas::mouseLoc,
                                 [this](){this->ui->statusBar->showMessage(MyCanvas::mouseLoc(QString st), 0);});
                  

                  I know it does not look correct, but what should it be?

                  J Offline
                  J Offline
                  JonB
                  wrote on 1 Nov 2018, 19:11 last edited by JonB 11 Jan 2018, 19:29
                  #8

                  @ofmrew
                  With the warning that I don't do C++ now and when I did I didn't use lambdas... but I can't help sticking my neck out :)

                  A lambda is essentially a call to an anonymous function, with nasty syntax. If you wrote your slot as a function, you would pass a parameter for the string (received from the signal) to it, wouldn't you? Like:

                  void slot(const QString& st)
                  {
                      this->ui->statusBar->showMessage(st, 0);
                  }
                  

                  So when you want to do that in lambda, @sierdzio is telling you that the formal parameter belongs inside the (). Sooo... I believe you want:

                      connect(ui->canvas, &MyCanvas::mouseLoc,
                                 [this](const QString& st){this->ui->statusBar->showMessage(st, 0);});
                  

                  We could lay it out so we can see what it is going on:

                      connect(ui->canvas, &MyCanvas::mouseLoc,
                                 [this](const QString& st)
                                 {
                                     this->ui->statusBar->showMessage(st, 0);
                                 }
                             );
                  

                  See how it's really the same syntax as when you do it with an explicit function?

                  O 1 Reply Last reply 1 Nov 2018, 19:39
                  5
                  • J JonB
                    1 Nov 2018, 19:11

                    @ofmrew
                    With the warning that I don't do C++ now and when I did I didn't use lambdas... but I can't help sticking my neck out :)

                    A lambda is essentially a call to an anonymous function, with nasty syntax. If you wrote your slot as a function, you would pass a parameter for the string (received from the signal) to it, wouldn't you? Like:

                    void slot(const QString& st)
                    {
                        this->ui->statusBar->showMessage(st, 0);
                    }
                    

                    So when you want to do that in lambda, @sierdzio is telling you that the formal parameter belongs inside the (). Sooo... I believe you want:

                        connect(ui->canvas, &MyCanvas::mouseLoc,
                                   [this](const QString& st){this->ui->statusBar->showMessage(st, 0);});
                    

                    We could lay it out so we can see what it is going on:

                        connect(ui->canvas, &MyCanvas::mouseLoc,
                                   [this](const QString& st)
                                   {
                                       this->ui->statusBar->showMessage(st, 0);
                                   }
                               );
                    

                    See how it's really the same syntax as when you do it with an explicit function?

                    O Offline
                    O Offline
                    ofmrew
                    wrote on 1 Nov 2018, 19:39 last edited by
                    #9

                    @JonB Still no dice. I tried:

                    connect(ui->canvas, &MyCanvas::mouseLoc, [=](MyCanvas::mouseLoc(QString st)){ui->statusBar->showMessage(st, 0)};));
                    

                    No type named mouseLoc.

                    S 1 Reply Last reply 2 Nov 2018, 05:37
                    0
                    • S Offline
                      S Offline
                      SGaist
                      Lifetime Qt Champion
                      wrote on 1 Nov 2018, 19:52 last edited by
                      #10

                      Where is mouseLoc used ?

                      Interested in AI ? www.idiap.ch
                      Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

                      O 1 Reply Last reply 1 Nov 2018, 20:34
                      0
                      • S SGaist
                        1 Nov 2018, 19:52

                        Where is mouseLoc used ?

                        O Offline
                        O Offline
                        ofmrew
                        wrote on 1 Nov 2018, 20:34 last edited by
                        #11

                        @SGaist ```
                        /void MyCanvas::mouseMoveEvent(QMouseEvent *e)
                        {
                        qDebug() << e << this->rect();
                        QPoint mouseLocation = e->pos();
                        qDebug() << mouseLocation;
                        QPoint worldPosition = currentMatrix.inverted().map(mouseLocation);
                        QString x = QString::number(worldPosition.rx());
                        QString y = QString::number(worldPosition.ry());
                        QString pt = x.append(":");
                        mouseLocString = pt.append(y);
                        emit mouseLoc(mouseLocString);
                        if (currentAction == 2){
                        corner2Ptw = e->pos();
                        this->update();
                        }
                        }

                        This is the code workaround that declares mouseLocString.  I would like to eliminate that step. I am, however, beginning to believe that it is a futile effort. Like I said above, I should just declare the signal with both parameters and connect it to the StatusBar slot. But I wanted to see how far I can push the boundaries of lambda. I find them very useful. Sorry if I have wasted your time.
                        1 Reply Last reply
                        0
                        • S Offline
                          S Offline
                          SGaist
                          Lifetime Qt Champion
                          wrote on 1 Nov 2018, 21:57 last edited by
                          #12

                          Eliminate what step ?

                          Interested in AI ? www.idiap.ch
                          Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

                          1 Reply Last reply
                          0
                          • M Offline
                            M Offline
                            mpergand
                            wrote on 1 Nov 2018, 22:11 last edited by
                            #13

                            @ofmrew said in Lambda that uses signal argument to connect to a slot:

                            connect(ui->canvas, &MyCanvas::mouseLoc, [=](MyCanvas::mouseLoc(QString st)){ui->statusBar->showMessage(st, 0)};));

                            connect(ui->canvas, &MyCanvas::mouseLoc, [](QPoint p)
                            {
                            ui->statusBar->showMessage(QString("%1:%2").arg(p.x()).arg(p.y()));
                            });

                            1 Reply Last reply
                            0
                            • S Offline
                              S Offline
                              SGaist
                              Lifetime Qt Champion
                              wrote on 1 Nov 2018, 22:17 last edited by
                              #14

                              You can't avoid the connection step. Otherwise, how would Qt know what to call ?

                              Interested in AI ? www.idiap.ch
                              Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

                              1 Reply Last reply
                              0
                              • O ofmrew
                                1 Nov 2018, 19:39

                                @JonB Still no dice. I tried:

                                connect(ui->canvas, &MyCanvas::mouseLoc, [=](MyCanvas::mouseLoc(QString st)){ui->statusBar->showMessage(st, 0)};));
                                

                                No type named mouseLoc.

                                S Offline
                                S Offline
                                sierdzio
                                Moderators
                                wrote on 2 Nov 2018, 05:37 last edited by
                                #15

                                @ofmrew said in Lambda that uses signal argument to connect to a slot:

                                @JonB Still no dice. I tried:

                                connect(ui->canvas, &MyCanvas::mouseLoc, [=](MyCanvas::mouseLoc(QString st)){ui->statusBar->showMessage(st, 0)};));
                                

                                No type named mouseLoc.

                                But @JonB wrote you exactly what code to use and you tried something else. Try what he proposed.

                                (Z(:^

                                O 1 Reply Last reply 2 Nov 2018, 15:13
                                3
                                • S sierdzio
                                  2 Nov 2018, 05:37

                                  @ofmrew said in Lambda that uses signal argument to connect to a slot:

                                  @JonB Still no dice. I tried:

                                  connect(ui->canvas, &MyCanvas::mouseLoc, [=](MyCanvas::mouseLoc(QString st)){ui->statusBar->showMessage(st, 0)};));
                                  

                                  No type named mouseLoc.

                                  But @JonB wrote you exactly what code to use and you tried something else. Try what he proposed.

                                  O Offline
                                  O Offline
                                  ofmrew
                                  wrote on 2 Nov 2018, 15:13 last edited by
                                  #16

                                  @sierdzio I tried:

                                      connect(ui->canvas, &MyCanvas::mouseLoc,
                                          [this](const QString& st)
                                          {this->ui->statusBar->showMessage(st, 0);});
                                  

                                  And it worked. Thanks everyone, I learned something.

                                  S 1 Reply Last reply 2 Nov 2018, 19:30
                                  0
                                  • O ofmrew
                                    2 Nov 2018, 15:13

                                    @sierdzio I tried:

                                        connect(ui->canvas, &MyCanvas::mouseLoc,
                                            [this](const QString& st)
                                            {this->ui->statusBar->showMessage(st, 0);});
                                    

                                    And it worked. Thanks everyone, I learned something.

                                    S Offline
                                    S Offline
                                    sierdzio
                                    Moderators
                                    wrote on 2 Nov 2018, 19:30 last edited by
                                    #17

                                    @ofmrew said in Lambda that uses signal argument to connect to a slot:

                                    @sierdzio I tried:

                                        connect(ui->canvas, &MyCanvas::mouseLoc,
                                            [this](const QString& st)
                                            {this->ui->statusBar->showMessage(st, 0);});
                                    

                                    And it worked. Thanks everyone, I learned something.

                                    Cheers :-)

                                    For the future, one more recommendation:

                                    connect(ui->canvas, &MyCanvas::mouseLoc,
                                             this, // <- control object
                                             [this](const QString& st)
                                             {this->ui->statusBar->showMessage(st, 0);});
                                    

                                    Adding a control object allows Qt to disconnect the connection automatically when that object is deleted. It does not matter in this case (your canvas is part of UI which is part of this), but in other situations it is a good thing to remember about (and costs nothing).

                                    (Z(:^

                                    O 1 Reply Last reply 2 Nov 2018, 21:45
                                    4
                                    • S sierdzio
                                      2 Nov 2018, 19:30

                                      @ofmrew said in Lambda that uses signal argument to connect to a slot:

                                      @sierdzio I tried:

                                          connect(ui->canvas, &MyCanvas::mouseLoc,
                                              [this](const QString& st)
                                              {this->ui->statusBar->showMessage(st, 0);});
                                      

                                      And it worked. Thanks everyone, I learned something.

                                      Cheers :-)

                                      For the future, one more recommendation:

                                      connect(ui->canvas, &MyCanvas::mouseLoc,
                                               this, // <- control object
                                               [this](const QString& st)
                                               {this->ui->statusBar->showMessage(st, 0);});
                                      

                                      Adding a control object allows Qt to disconnect the connection automatically when that object is deleted. It does not matter in this case (your canvas is part of UI which is part of this), but in other situations it is a good thing to remember about (and costs nothing).

                                      O Offline
                                      O Offline
                                      ofmrew
                                      wrote on 2 Nov 2018, 21:45 last edited by
                                      #18

                                      @sierdzio Thanks, I am learning even more. I made that change. Any other wise tips, the would be gratefully accepted.

                                      1 Reply Last reply
                                      0

                                      1/18

                                      31 Oct 2018, 19:02

                                      • Login

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