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. Please help with lambda sytax
Forum Updated to NodeBB v4.3 + New Features

Please help with lambda sytax

Scheduled Pinned Locked Moved Unsolved General and Desktop
26 Posts 8 Posters 3.6k Views 3 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.
  • A Anonymous_Banned275

    I am looking at this
    link text

    
        QObject::connect(ui->list,        //object
        &QListWidget::itemClicked,      //signal
        this,                              //object
        [this]( QListWidgetItem * pItem ) { this->ui->list_2->addItem( pItem ); };
    

    And still getting an error

    /media/f/QT/Qt/QT/qtconnectivity/examples/bluetooth/CAT_BT_18112020/device.cpp:181: error: expected ')' before ';' token
         [this]( QListWidgetItem * pItem ) { this->ui->list_2->addItem( pItem ); };                                                                          ^
    

    the error "^" symbol points to the last ";" - it won't copy the "^" symbol at the correct place.

    Please help me.

    Pl45m4P Offline
    Pl45m4P Offline
    Pl45m4
    wrote on last edited by Pl45m4
    #6

    @AnneRanch

    I think, you dont need lambdas for this.
    You can just do this:

    // connection is correct, but wont work as expected or even crash
    QObject::connect(ui->list, &QListWidget::itemClicked, ui->list2, &QListWidget::addItem);
    

    Note:

    Warning: A QListWidgetItem can only be added to a QListWidget once. Adding the same QListWidgetItem multiple times to a QListWidget will result in undefined behavior.

    (https://doc.qt.io/qt-5/qlistwidget.html#addItem-1)

    If you want to use a lambda connection anyway, try without using this before ui.

    might be interesting
    https://artandlogic.com/2013/09/qt-5-and-c11-lambdas-are-your-friend/


    If debugging is the process of removing software bugs, then programming must be the process of putting them in.

    ~E. W. Dijkstra

    JonBJ 1 Reply Last reply
    0
    • Pl45m4P Pl45m4

      @AnneRanch

      I think, you dont need lambdas for this.
      You can just do this:

      // connection is correct, but wont work as expected or even crash
      QObject::connect(ui->list, &QListWidget::itemClicked, ui->list2, &QListWidget::addItem);
      

      Note:

      Warning: A QListWidgetItem can only be added to a QListWidget once. Adding the same QListWidgetItem multiple times to a QListWidget will result in undefined behavior.

      (https://doc.qt.io/qt-5/qlistwidget.html#addItem-1)

      If you want to use a lambda connection anyway, try without using this before ui.

      might be interesting
      https://artandlogic.com/2013/09/qt-5-and-c11-lambdas-are-your-friend/

      JonBJ Offline
      JonBJ Offline
      JonB
      wrote on last edited by JonB
      #7

      @Pl45m4
      Untested by me, but, lambda or not, this (and the OP's original code) attempts to (re-)add an existing QListWidgetItem which is in ui->list as an item in another list, ui->list2. Doesn't runtime forbid this, doesn't a given QListWidgetItem have to belong to just one QListWidget (as returned by QListWidget *QListWidgetItem::listWidget() const)? Don't you have to either remove it first or copy it? That's how it works in C#/.NET! (Or, does it move it across from the existing QListWidget to the other one??)

      I will strike this out if you say it does work....

      Pl45m4P 1 Reply Last reply
      1
      • JonBJ JonB

        @Pl45m4
        Untested by me, but, lambda or not, this (and the OP's original code) attempts to (re-)add an existing QListWidgetItem which is in ui->list as an item in another list, ui->list2. Doesn't runtime forbid this, doesn't a given QListWidgetItem have to belong to just one QListWidget (as returned by QListWidget *QListWidgetItem::listWidget() const)? Don't you have to either remove it first or copy it? That's how it works in C#/.NET! (Or, does it move it across from the existing QListWidget to the other one??)

        I will strike this out if you say it does work....

        Pl45m4P Offline
        Pl45m4P Offline
        Pl45m4
        wrote on last edited by Pl45m4
        #8

        @JonB said in Please help with lambda sytax:

        Doesn't runtime forbid this, doesn't a given QListWidgetItem have to belong to just one QListWidget (as returned by QListWidget *QListWidgetItem::listWidget() const)? (Or, does it move it across from the existing QListWidget to the other one??)

        Haven't checked it either... Well, now that you mention it, it makes sense :)

        But wouldn't it cause a runtime crash or error?! The connection as such, which is a problem apparently, shouldn't be the problem here.

        So to transfer one item from one QListWidget to another, @AnneRanch needs to take it from the first one or create a new one with same properties -> Lambda :-)

        Edit:

        This

        Don't you have to either remove it first or copy it?


        If debugging is the process of removing software bugs, then programming must be the process of putting them in.

        ~E. W. Dijkstra

        JonBJ 1 Reply Last reply
        0
        • Pl45m4P Pl45m4

          @JonB said in Please help with lambda sytax:

          Doesn't runtime forbid this, doesn't a given QListWidgetItem have to belong to just one QListWidget (as returned by QListWidget *QListWidgetItem::listWidget() const)? (Or, does it move it across from the existing QListWidget to the other one??)

          Haven't checked it either... Well, now that you mention it, it makes sense :)

          But wouldn't it cause a runtime crash or error?! The connection as such, which is a problem apparently, shouldn't be the problem here.

          So to transfer one item from one QListWidget to another, @AnneRanch needs to take it from the first one or create a new one with same properties -> Lambda :-)

          Edit:

          This

          Don't you have to either remove it first or copy it?

          JonBJ Offline
          JonBJ Offline
          JonB
          wrote on last edited by JonB
          #9

          @Pl45m4
          Indeed, the connect() itself would be fine, both at compile & runtime. The question is what the QListWidget::addItem will do when the item is clicked on and the slot is called.... Which the OP will get to once her compilation goes through and she tries out the behaviour, I'm trying to anticipate....

          1 Reply Last reply
          0
          • Christian EhrlicherC Offline
            Christian EhrlicherC Offline
            Christian Ehrlicher
            Lifetime Qt Champion
            wrote on last edited by
            #10

            Why do you discuss instead looking at the source?

            void QListWidget::insertItem(int row, QListWidgetItem *item)
            {
                Q_D(QListWidget);
                if (item && !item->view)
                    d->listModel()->insert(row, item);
            }
            

            Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
            Visit the Qt Academy at https://academy.qt.io/catalog

            JonBJ 1 Reply Last reply
            0
            • Christian EhrlicherC Christian Ehrlicher

              Why do you discuss instead looking at the source?

              void QListWidget::insertItem(int row, QListWidgetItem *item)
              {
                  Q_D(QListWidget);
                  if (item && !item->view)
                      d->listModel()->insert(row, item);
              }
              
              JonBJ Offline
              JonBJ Offline
              JonB
              wrote on last edited by JonB
              #11

              @Christian-Ehrlicher
              Because I like reasoning/guessing it through? I still don't know the effect because I don't know what sets item->view, so I'd have to follow that, and/or what that insert() does/does not do. It's not germane to the OP's query about how to write the syntax, it's just it may not produce the behaviour she might be expecting to see at runtime, so it was just a potential caveat from me.

              1 Reply Last reply
              0
              • jsulmJ jsulm

                @AnneRanch What is list_2?
                Also, can you show the whole error?

                A Offline
                A Offline
                Anonymous_Banned275
                wrote on last edited by
                #12

                @jsulm said in Please help with lambda sytax:

                @AnneRanch What is list_2?
                Also, can you show the whole error?

                The original , wrong ";" , whole error was already posted.
                The ";" error was found and corrected.

                Now the error is

                /media/f/QT/Qt/QT/qtconnectivity/examples/bluetooth/CAT_BT_18112020/device.cpp:181: error: no matching function for call to 'DeviceDiscoveryDialog::connect(QListWidget*&, void (/media/f/QT/Qt/QT/qtconnectivity/examples/bluetooth/CAT_BT_18112020/device.cpp:181: error: no matching function for call to 'DeviceDiscoveryDialog::connect(QListWidget*&, void (QListWidget::*)(QListWidgetItem*), DeviceDiscoveryDialog*, DeviceDiscoveryDialog::DeviceDiscoveryDialog(QWidget*)::<lambda(QListWidgetItem*)>)'
                     [this]( QListWidgetItem * pItem ) { this->ui->list_2->addItem ( pItem ); }) ;
                                                                                               ^::*)(QListWidgetItem*), DeviceDiscoveryDialog*, DeviceDiscoveryDialog::DeviceDiscoveryDialog(QWidget*)::<lambda(QListWidgetItem*)>)'
                     [this]( QListWidgetItem * pItem ) { this->ui->list_2->addItem ( pItem ); }) ;
                                                                                               ^
                

                Both list's are QListWidget

                This whole exercise is my desire to learn how to code "connect". I am trying to duplicate QtDesigner WORKING "connect". See attached screen shot. I went too far and started with copying "item" from one dialog to "main dialog". That when things got convoluted with QOverload ( handling "item" as a string ) and lambda.

                793b5e8b-8d6e-4285-bab2-731312ab49e7-image.png

                So far I have learn that Intelisense and lambda do not mix - I cab "addItem" using Intelisense ( legal) but it there but compiler complains there is not "addItem ".
                "click" and "itemchanged" are not the same - no surprise here.

                I am still looking into lambda doc and my head is spinning.
                ( I am not sure why lambda "mixes " QListWidget and QListWidgetItem)

                This is still a learning exercise and I like to go back and copy the QtDesigner WORKING XML to plain C++ code and make it work in ONE dialog.
                Then tackle same and make it work between dialog and main dialog - using "new " connect style. ( It would be nice if QtDesigner did "new connect style " too. )
                Using lambda is last on my TODO list, but I am open to suggestions.

                Thanks

                Pl45m4P 1 Reply Last reply
                0
                • A Anonymous_Banned275

                  @jsulm said in Please help with lambda sytax:

                  @AnneRanch What is list_2?
                  Also, can you show the whole error?

                  The original , wrong ";" , whole error was already posted.
                  The ";" error was found and corrected.

                  Now the error is

                  /media/f/QT/Qt/QT/qtconnectivity/examples/bluetooth/CAT_BT_18112020/device.cpp:181: error: no matching function for call to 'DeviceDiscoveryDialog::connect(QListWidget*&, void (/media/f/QT/Qt/QT/qtconnectivity/examples/bluetooth/CAT_BT_18112020/device.cpp:181: error: no matching function for call to 'DeviceDiscoveryDialog::connect(QListWidget*&, void (QListWidget::*)(QListWidgetItem*), DeviceDiscoveryDialog*, DeviceDiscoveryDialog::DeviceDiscoveryDialog(QWidget*)::<lambda(QListWidgetItem*)>)'
                       [this]( QListWidgetItem * pItem ) { this->ui->list_2->addItem ( pItem ); }) ;
                                                                                                 ^::*)(QListWidgetItem*), DeviceDiscoveryDialog*, DeviceDiscoveryDialog::DeviceDiscoveryDialog(QWidget*)::<lambda(QListWidgetItem*)>)'
                       [this]( QListWidgetItem * pItem ) { this->ui->list_2->addItem ( pItem ); }) ;
                                                                                                 ^
                  

                  Both list's are QListWidget

                  This whole exercise is my desire to learn how to code "connect". I am trying to duplicate QtDesigner WORKING "connect". See attached screen shot. I went too far and started with copying "item" from one dialog to "main dialog". That when things got convoluted with QOverload ( handling "item" as a string ) and lambda.

                  793b5e8b-8d6e-4285-bab2-731312ab49e7-image.png

                  So far I have learn that Intelisense and lambda do not mix - I cab "addItem" using Intelisense ( legal) but it there but compiler complains there is not "addItem ".
                  "click" and "itemchanged" are not the same - no surprise here.

                  I am still looking into lambda doc and my head is spinning.
                  ( I am not sure why lambda "mixes " QListWidget and QListWidgetItem)

                  This is still a learning exercise and I like to go back and copy the QtDesigner WORKING XML to plain C++ code and make it work in ONE dialog.
                  Then tackle same and make it work between dialog and main dialog - using "new " connect style. ( It would be nice if QtDesigner did "new connect style " too. )
                  Using lambda is last on my TODO list, but I am open to suggestions.

                  Thanks

                  Pl45m4P Offline
                  Pl45m4P Offline
                  Pl45m4
                  wrote on last edited by Pl45m4
                  #13

                  @AnneRanch

                  Can you please clarify what your final goal is? It seems that some of your recent topics (incl. this one) are going in the wrong direction...

                  You started here with an error in your connect statement, but we obviously can not know whether your connection makes sense in your case or not.

                  If you want to transfer (i.e. "copy") items, you've clicked in one listWidget to the second listWidget, do what @JonB suggested here.

                  addItem only works, if you have a "free" QListWidgetItem. So even if we correct your mistake, it wont help you or work at all.
                  The item, that the clicked function returns, belongs already to one QListWidget, so you cant just add it to a second one.

                  Changing your code inside lambda to this might work (not tested)

                  // creates a copy of the clicked item, instead of trying to move it
                  QListWidgetItem * newItem = new QListWidgetItem(pItem);
                  ui->list_2->addItem( newItem );
                  

                  The connection as seen in your picture equals somewhat like this (lambda style):

                  connect(ui->list, &QListWidget::currentTextChanged, [=](QString s){
                  
                  ui->plainTextEdit2->appendPlainText(s);
                  });
                  

                  If debugging is the process of removing software bugs, then programming must be the process of putting them in.

                  ~E. W. Dijkstra

                  A 1 Reply Last reply
                  0
                  • Pl45m4P Pl45m4

                    @AnneRanch

                    Can you please clarify what your final goal is? It seems that some of your recent topics (incl. this one) are going in the wrong direction...

                    You started here with an error in your connect statement, but we obviously can not know whether your connection makes sense in your case or not.

                    If you want to transfer (i.e. "copy") items, you've clicked in one listWidget to the second listWidget, do what @JonB suggested here.

                    addItem only works, if you have a "free" QListWidgetItem. So even if we correct your mistake, it wont help you or work at all.
                    The item, that the clicked function returns, belongs already to one QListWidget, so you cant just add it to a second one.

                    Changing your code inside lambda to this might work (not tested)

                    // creates a copy of the clicked item, instead of trying to move it
                    QListWidgetItem * newItem = new QListWidgetItem(pItem);
                    ui->list_2->addItem( newItem );
                    

                    The connection as seen in your picture equals somewhat like this (lambda style):

                    connect(ui->list, &QListWidget::currentTextChanged, [=](QString s){
                    
                    ui->plainTextEdit2->appendPlainText(s);
                    });
                    
                    A Offline
                    A Offline
                    Anonymous_Banned275
                    wrote on last edited by
                    #14

                    @Pl45m4 said in Please help with lambda sytax:

                    @AnneRanch

                    Can you please clarify what your final goal is? It seems that some of your recent topics (incl. this one) are going in the wrong direction...

                    You started here with an error in your connect statement, but we obviously can not know whether your connection makes sense in your case or not.

                    If you want to transfer (i.e. "copy") items, you've clicked in one listWidget to the second listWidget, do what @JonB suggested here.

                    addItem only works, if you have a "free" QListWidgetItem. So even if we correct your mistake, it wont help you or work at all.
                    The item, that the clicked function returns, belongs already to one QListWidget, so you cant just add it to a second one.

                    Changing your code inside lambda to this might work (not tested)

                    // creates a copy of the clicked item, instead of trying to move it
                    QListWidgetItem * newItem = new QListWidgetItem(pItem);
                    ui->list_2->addItem( newItem );
                    

                    The connection as seen in your picture equals somewhat like this (lambda style):

                    connect(ui->list, &QListWidget::currentTextChanged, [=](QString s){
                    
                    ui->plainTextEdit2->appendPlainText(s);
                    });
                    

                    In general terms - The objective is to copy an item from one widget to another.
                    It is actually QString, not a generic "item" I want to copy.

                    The QtDesigner does that with the screen shot of SIGNAL/SLOT I have posted. No problem.

                    Yes, I do not know how to convert QtDesigner XML GUI to plain C code, but if QtDesigner apparently works without creating new "item" why is it necessary to create new item in code? But that is not main issue.

                    To avoid further r misunderstanding - help me to duplicate XML in C code first . Then do the lambda and then copy between dialogs. Baby steps.

                    I can just temporary delete the QtDesigner XML to test the plain C code.

                    Perhaps screen shot what I have now?

                    Eventually "automatically" copy each line of text from Bluetooth scanner dialog "nearby BT devices" to main window Tab2 "nearby BT devices".

                    The unnamed text under "Connect" button , done by QtDesigner, is what I want to duplicate in code.

                    6b8df14a-1471-4c70-9d2c-af9f17683f8d-image.png

                    1 Reply Last reply
                    0
                    • A Offline
                      A Offline
                      Anonymous_Banned275
                      wrote on last edited by
                      #15

                      Please note - I am posting this to illustrate the problem, please please please - NO comments on my programming style!

                      My primary goal is to duplicate XML "connect" using code.
                      The attached code and its variations generally compiles - that is one goal done.

                      HOWEVER - it crashes during run time and I SUSPECT the problem is
                      after
                      clicking button 11 my code builds new instance of scanner dialog and it has build-in timers . The "list" is , in theory, filed AFTER each item individual timer expire.
                      BUT
                      my test connect is executed immediately after the first timer expires and the "item" is changed .

                      I am asking - is it possible I have a timing problem?

                      Here is my current - under construction connect to copy the "list" lines.
                      All it does - just compiles and cannot be tested , in existing code , due to this issue.

                      #ifdef BYPASS
                          // interacts with pushing buitto 11
                          // keeps crashing
                          
                          connect(
                                      this->ui->list,
                                      //          SIGNAL(ui->list->currentTextChanged()),
                                      SIGNAL(ui->list->itemDoubleClicked(*pItem)),
                                      //           SIGNAL(DDD->ui->list->itemChanged(TEST_LABEL)),
                                      //           SIGNAL(itemClicked(QListWidgetItem *)),
                                      //              SIGNAL(itemChanged(TEST_LABEL)),
                                      this->ui->plainTextEdit,
                                      //           SLOT(DDD->ui->plainTextEdit->appendPlainText(TEST_LABEL))
                                      //             SLOT(appendPlainText(TEST_LABEL))
                                      SLOT(ui->plainTextEdit->appendPlainText(*pItem)));
                          //           );
                          
                      #endif
                          
                          
                      

                      This is how it tracks when working - without the code above

                      QDEBUG TRACE 
                      QDEBUG TRACE TASK 
                      		 END imoplement Device DiscoiveryDialog  
                      
                      QDEBUG TRACE TASK 
                      		 find nearby BT devices 
                      
                      file      /media/f/QT/QT_PROJECT/TEST_PROJECT_14/mainwindow_cat_tab.cpp
                      function  on_pushButton_11_clicked
                      @line     236
                      TEMPORARY EXIT 
                      /home/f/build-TEST_PROJECT-Desktop-Debug/TEST_PROJECT exited with code 0
                      

                      And this is failing track

                      QDEBUG TRACE 
                      QDEBUG TRACE TASK 
                      		 START imoplement Device DiscoveryDialog  
                      
                      QDEBUG TRACE TASK 
                      		 find nearby BT devices 
                      
                      file      /media/f/QT/QT_PROJECT/TEST_PROJECT_14/mainwindow_cat_tab.cpp
                      function  on_pushButton_11_clicked
                      @line     206
                      TEMPORARY EXIT 
                      TRACE SCAN FLOW 
                      			 START TOK TRACE SCAN FLOW CONSTRUCTOR 
                      			DeviceDiscoveryDialog::DeviceDiscoveryDialog(QWidget *parent)
                      
                      
                      TEMPORARY exit  @line 
                      133
                      The program has unexpectedly finished.
                      /home/f/build-TEST_PROJECT-Desktop-Debug/TEST_PROJECT crashed
                      

                      Again - all I am asking - is it possible I have a timing problem?

                      jsulmJ JonBJ 3 Replies Last reply
                      0
                      • A Anonymous_Banned275

                        Please note - I am posting this to illustrate the problem, please please please - NO comments on my programming style!

                        My primary goal is to duplicate XML "connect" using code.
                        The attached code and its variations generally compiles - that is one goal done.

                        HOWEVER - it crashes during run time and I SUSPECT the problem is
                        after
                        clicking button 11 my code builds new instance of scanner dialog and it has build-in timers . The "list" is , in theory, filed AFTER each item individual timer expire.
                        BUT
                        my test connect is executed immediately after the first timer expires and the "item" is changed .

                        I am asking - is it possible I have a timing problem?

                        Here is my current - under construction connect to copy the "list" lines.
                        All it does - just compiles and cannot be tested , in existing code , due to this issue.

                        #ifdef BYPASS
                            // interacts with pushing buitto 11
                            // keeps crashing
                            
                            connect(
                                        this->ui->list,
                                        //          SIGNAL(ui->list->currentTextChanged()),
                                        SIGNAL(ui->list->itemDoubleClicked(*pItem)),
                                        //           SIGNAL(DDD->ui->list->itemChanged(TEST_LABEL)),
                                        //           SIGNAL(itemClicked(QListWidgetItem *)),
                                        //              SIGNAL(itemChanged(TEST_LABEL)),
                                        this->ui->plainTextEdit,
                                        //           SLOT(DDD->ui->plainTextEdit->appendPlainText(TEST_LABEL))
                                        //             SLOT(appendPlainText(TEST_LABEL))
                                        SLOT(ui->plainTextEdit->appendPlainText(*pItem)));
                            //           );
                            
                        #endif
                            
                            
                        

                        This is how it tracks when working - without the code above

                        QDEBUG TRACE 
                        QDEBUG TRACE TASK 
                        		 END imoplement Device DiscoiveryDialog  
                        
                        QDEBUG TRACE TASK 
                        		 find nearby BT devices 
                        
                        file      /media/f/QT/QT_PROJECT/TEST_PROJECT_14/mainwindow_cat_tab.cpp
                        function  on_pushButton_11_clicked
                        @line     236
                        TEMPORARY EXIT 
                        /home/f/build-TEST_PROJECT-Desktop-Debug/TEST_PROJECT exited with code 0
                        

                        And this is failing track

                        QDEBUG TRACE 
                        QDEBUG TRACE TASK 
                        		 START imoplement Device DiscoveryDialog  
                        
                        QDEBUG TRACE TASK 
                        		 find nearby BT devices 
                        
                        file      /media/f/QT/QT_PROJECT/TEST_PROJECT_14/mainwindow_cat_tab.cpp
                        function  on_pushButton_11_clicked
                        @line     206
                        TEMPORARY EXIT 
                        TRACE SCAN FLOW 
                        			 START TOK TRACE SCAN FLOW CONSTRUCTOR 
                        			DeviceDiscoveryDialog::DeviceDiscoveryDialog(QWidget *parent)
                        
                        
                        TEMPORARY exit  @line 
                        133
                        The program has unexpectedly finished.
                        /home/f/build-TEST_PROJECT-Desktop-Debug/TEST_PROJECT crashed
                        

                        Again - all I am asking - is it possible I have a timing problem?

                        jsulmJ Offline
                        jsulmJ Offline
                        jsulm
                        Lifetime Qt Champion
                        wrote on last edited by jsulm
                        #16

                        @AnneRanch said in Please help with lambda sytax:

                        connect(
                        this->ui->list,
                        // SIGNAL(ui->list->currentTextChanged()),
                        SIGNAL(ui->list->itemDoubleClicked(*pItem)),
                        // SIGNAL(DDD->ui->list->itemChanged(TEST_LABEL)),
                        // SIGNAL(itemClicked(QListWidgetItem *)),
                        // SIGNAL(itemChanged(TEST_LABEL)),
                        this->ui->plainTextEdit,
                        // SLOT(DDD->ui->plainTextEdit->appendPlainText(TEST_LABEL))
                        // SLOT(appendPlainText(TEST_LABEL))
                        SLOT(ui->plainTextEdit->appendPlainText(*pItem)));
                        // );

                        This is invalid connect() call. Please check https://doc.qt.io/qt-5/signalsandslots.html And it is better to use Qt5 connect() syntax to detect such issues during compile time instead of run time.
                        It should be

                        connect(
                            this->ui->list,
                            SIGNAL(itemDoubleClicked(QListWidgetItem*)),
                            this->ui->plainTextEdit,
                            SLOT(appendPlainText(QListWidgetItem*)));
                        

                        But this will also not work as QPlainTextEdit does not have a slot appendPlainText which takes a QListWidgetItem* as parameter (use new Qt5 connect syntax and a lambda)...

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

                        A 1 Reply Last reply
                        5
                        • A Anonymous_Banned275

                          Please note - I am posting this to illustrate the problem, please please please - NO comments on my programming style!

                          My primary goal is to duplicate XML "connect" using code.
                          The attached code and its variations generally compiles - that is one goal done.

                          HOWEVER - it crashes during run time and I SUSPECT the problem is
                          after
                          clicking button 11 my code builds new instance of scanner dialog and it has build-in timers . The "list" is , in theory, filed AFTER each item individual timer expire.
                          BUT
                          my test connect is executed immediately after the first timer expires and the "item" is changed .

                          I am asking - is it possible I have a timing problem?

                          Here is my current - under construction connect to copy the "list" lines.
                          All it does - just compiles and cannot be tested , in existing code , due to this issue.

                          #ifdef BYPASS
                              // interacts with pushing buitto 11
                              // keeps crashing
                              
                              connect(
                                          this->ui->list,
                                          //          SIGNAL(ui->list->currentTextChanged()),
                                          SIGNAL(ui->list->itemDoubleClicked(*pItem)),
                                          //           SIGNAL(DDD->ui->list->itemChanged(TEST_LABEL)),
                                          //           SIGNAL(itemClicked(QListWidgetItem *)),
                                          //              SIGNAL(itemChanged(TEST_LABEL)),
                                          this->ui->plainTextEdit,
                                          //           SLOT(DDD->ui->plainTextEdit->appendPlainText(TEST_LABEL))
                                          //             SLOT(appendPlainText(TEST_LABEL))
                                          SLOT(ui->plainTextEdit->appendPlainText(*pItem)));
                              //           );
                              
                          #endif
                              
                              
                          

                          This is how it tracks when working - without the code above

                          QDEBUG TRACE 
                          QDEBUG TRACE TASK 
                          		 END imoplement Device DiscoiveryDialog  
                          
                          QDEBUG TRACE TASK 
                          		 find nearby BT devices 
                          
                          file      /media/f/QT/QT_PROJECT/TEST_PROJECT_14/mainwindow_cat_tab.cpp
                          function  on_pushButton_11_clicked
                          @line     236
                          TEMPORARY EXIT 
                          /home/f/build-TEST_PROJECT-Desktop-Debug/TEST_PROJECT exited with code 0
                          

                          And this is failing track

                          QDEBUG TRACE 
                          QDEBUG TRACE TASK 
                          		 START imoplement Device DiscoveryDialog  
                          
                          QDEBUG TRACE TASK 
                          		 find nearby BT devices 
                          
                          file      /media/f/QT/QT_PROJECT/TEST_PROJECT_14/mainwindow_cat_tab.cpp
                          function  on_pushButton_11_clicked
                          @line     206
                          TEMPORARY EXIT 
                          TRACE SCAN FLOW 
                          			 START TOK TRACE SCAN FLOW CONSTRUCTOR 
                          			DeviceDiscoveryDialog::DeviceDiscoveryDialog(QWidget *parent)
                          
                          
                          TEMPORARY exit  @line 
                          133
                          The program has unexpectedly finished.
                          /home/f/build-TEST_PROJECT-Desktop-Debug/TEST_PROJECT crashed
                          

                          Again - all I am asking - is it possible I have a timing problem?

                          JonBJ Offline
                          JonBJ Offline
                          JonB
                          wrote on last edited by JonB
                          #17

                          @AnneRanch
                          As @jsulm has said. As long as you use the old-style SIGNAL & SLOT() macros, you are liable to have code which compiles OK but does not behave correctly at runtime. With the new style syntax, if the signal/slot code is wrong, you get told at compile-time. It might seem harder to get it right, but at least you know that when it does compile it will do what you expect when you run it; if it does not compile, you have to sort it out to be correct at that stage.

                          1 Reply Last reply
                          0
                          • jsulmJ jsulm

                            @AnneRanch said in Please help with lambda sytax:

                            connect(
                            this->ui->list,
                            // SIGNAL(ui->list->currentTextChanged()),
                            SIGNAL(ui->list->itemDoubleClicked(*pItem)),
                            // SIGNAL(DDD->ui->list->itemChanged(TEST_LABEL)),
                            // SIGNAL(itemClicked(QListWidgetItem *)),
                            // SIGNAL(itemChanged(TEST_LABEL)),
                            this->ui->plainTextEdit,
                            // SLOT(DDD->ui->plainTextEdit->appendPlainText(TEST_LABEL))
                            // SLOT(appendPlainText(TEST_LABEL))
                            SLOT(ui->plainTextEdit->appendPlainText(*pItem)));
                            // );

                            This is invalid connect() call. Please check https://doc.qt.io/qt-5/signalsandslots.html And it is better to use Qt5 connect() syntax to detect such issues during compile time instead of run time.
                            It should be

                            connect(
                                this->ui->list,
                                SIGNAL(itemDoubleClicked(QListWidgetItem*)),
                                this->ui->plainTextEdit,
                                SLOT(appendPlainText(QListWidgetItem*)));
                            

                            But this will also not work as QPlainTextEdit does not have a slot appendPlainText which takes a QListWidgetItem* as parameter (use new Qt5 connect syntax and a lambda)...

                            A Offline
                            A Offline
                            Anonymous_Banned275
                            wrote on last edited by
                            #18

                            @jsulm said in Please help with lambda sytax:

                            But this will also not work as QPlainTextEdit does not have a slot appendPlainText which takes a QListWidgetItem* as parameter (use new Qt5 connect syntax and a lambda)...

                            I do appreciate the post.
                            It may seems strange, but at this point I am NOT after "it" working.
                            I just need to figure out WHY adding this "connect" , in any form or format , crashes the program.
                            After I figure out the crasher I will work on form / format/ style.
                            Of course I could verify the "connect" using separate test program.

                            Pl45m4P 1 Reply Last reply
                            0
                            • A Anonymous_Banned275

                              Please note - I am posting this to illustrate the problem, please please please - NO comments on my programming style!

                              My primary goal is to duplicate XML "connect" using code.
                              The attached code and its variations generally compiles - that is one goal done.

                              HOWEVER - it crashes during run time and I SUSPECT the problem is
                              after
                              clicking button 11 my code builds new instance of scanner dialog and it has build-in timers . The "list" is , in theory, filed AFTER each item individual timer expire.
                              BUT
                              my test connect is executed immediately after the first timer expires and the "item" is changed .

                              I am asking - is it possible I have a timing problem?

                              Here is my current - under construction connect to copy the "list" lines.
                              All it does - just compiles and cannot be tested , in existing code , due to this issue.

                              #ifdef BYPASS
                                  // interacts with pushing buitto 11
                                  // keeps crashing
                                  
                                  connect(
                                              this->ui->list,
                                              //          SIGNAL(ui->list->currentTextChanged()),
                                              SIGNAL(ui->list->itemDoubleClicked(*pItem)),
                                              //           SIGNAL(DDD->ui->list->itemChanged(TEST_LABEL)),
                                              //           SIGNAL(itemClicked(QListWidgetItem *)),
                                              //              SIGNAL(itemChanged(TEST_LABEL)),
                                              this->ui->plainTextEdit,
                                              //           SLOT(DDD->ui->plainTextEdit->appendPlainText(TEST_LABEL))
                                              //             SLOT(appendPlainText(TEST_LABEL))
                                              SLOT(ui->plainTextEdit->appendPlainText(*pItem)));
                                  //           );
                                  
                              #endif
                                  
                                  
                              

                              This is how it tracks when working - without the code above

                              QDEBUG TRACE 
                              QDEBUG TRACE TASK 
                              		 END imoplement Device DiscoiveryDialog  
                              
                              QDEBUG TRACE TASK 
                              		 find nearby BT devices 
                              
                              file      /media/f/QT/QT_PROJECT/TEST_PROJECT_14/mainwindow_cat_tab.cpp
                              function  on_pushButton_11_clicked
                              @line     236
                              TEMPORARY EXIT 
                              /home/f/build-TEST_PROJECT-Desktop-Debug/TEST_PROJECT exited with code 0
                              

                              And this is failing track

                              QDEBUG TRACE 
                              QDEBUG TRACE TASK 
                              		 START imoplement Device DiscoveryDialog  
                              
                              QDEBUG TRACE TASK 
                              		 find nearby BT devices 
                              
                              file      /media/f/QT/QT_PROJECT/TEST_PROJECT_14/mainwindow_cat_tab.cpp
                              function  on_pushButton_11_clicked
                              @line     206
                              TEMPORARY EXIT 
                              TRACE SCAN FLOW 
                              			 START TOK TRACE SCAN FLOW CONSTRUCTOR 
                              			DeviceDiscoveryDialog::DeviceDiscoveryDialog(QWidget *parent)
                              
                              
                              TEMPORARY exit  @line 
                              133
                              The program has unexpectedly finished.
                              /home/f/build-TEST_PROJECT-Desktop-Debug/TEST_PROJECT crashed
                              

                              Again - all I am asking - is it possible I have a timing problem?

                              jsulmJ Offline
                              jsulmJ Offline
                              jsulm
                              Lifetime Qt Champion
                              wrote on last edited by
                              #19

                              @AnneRanch said in Please help with lambda sytax:

                              function on_pushButton_11_clicked
                              @line 206

                              Can you show your on_pushButton_11_clicked? The crash is there at line 206.

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

                              A 1 Reply Last reply
                              1
                              • A Anonymous_Banned275

                                @jsulm said in Please help with lambda sytax:

                                But this will also not work as QPlainTextEdit does not have a slot appendPlainText which takes a QListWidgetItem* as parameter (use new Qt5 connect syntax and a lambda)...

                                I do appreciate the post.
                                It may seems strange, but at this point I am NOT after "it" working.
                                I just need to figure out WHY adding this "connect" , in any form or format , crashes the program.
                                After I figure out the crasher I will work on form / format/ style.
                                Of course I could verify the "connect" using separate test program.

                                Pl45m4P Offline
                                Pl45m4P Offline
                                Pl45m4
                                wrote on last edited by Pl45m4
                                #20

                                @AnneRanch

                                Back to lambdas:

                                You said, you are struggling to understand lambda connections correctly.
                                It's not as complicated as it might look.

                                • You have your sender (first argument)

                                  connect(ui->list,.....)
                                  
                                • You have your sender's class + signal

                                   connect(ui->list, &QListWidget::itemDoubleClicked,.....)
                                  
                                • Then you can define a scope for your lambda

                                  connect(ui->list, &QListWidget::itemDoubleClicked, this,......)
                                  
                                • the last part consists of the capture, the function or slot arguments and the actual code itself, using the passed and captured values

                                  • Capture

                                    • "[ ]": None of the variables from current class / scope are captured and can be used inside lambda "code"
                                    • " [=]": Captures everything (by value!)
                                    • "[this] ": (current instance) or any combination of variables (e.g. [x, a]), to pick variables you need explicitely.
                                    • "[&]" or "[ &someVar ]": Captures by reference. Changes made inside lambda will affect and change the captured variable outside the lambda as well ( Thx, @JonB )
                                  • Signal / Slot arguments after capture inside ( .... ), e.g. if signal sends a QListWidgetItem, you need a (QListWidgetItem *item) here.

                                  • lambda code inside { .... }

                                    • do whatever you like and what you would put in your slot here.

                                One big advantage using lambda connections is, that you can connect signals to slots (or "code"), that would be incompatible using a "direct" connection because of any reason (e.g. parameter mismatch).

                                Simple example:

                                // signal
                                void signal(QString s);
                                // slot
                                void onSignalFired(int i);
                                

                                A direct connection of these two won't work neither using the SIGNAL(...) / SLOT( ... ) syntax
                                (-> crash / error at runtime),
                                nor using the function based connection &Class::signal... &Class::onSignalFired
                                ( -> wont compile).

                                With lambda, you can make it work:

                                connect(this, &Class::signal, [] (QString s) {  onSignalFired( s.toInt() ); } ); 
                                

                                Instead of calling the slot, you could also skip the slot and do whatever you want to do with this string inside the lambda directly, e.g. send your number to a QLineEdit ("A" would lead to a 65, simple ASCII).

                                @AnneRanch said in Please help with lambda sytax:

                                Here is my current - under construction connect to copy the "list" lines.
                                All it does - just compiles and cannot be tested , in existing code , due to this issue.

                                ... and this is exactly where you can make use of lambdas ( as @jsulm already said ).
                                Pass your QListWidgetItem from signal to your lambda, get the text from your item using text() (Qt Doc), then pass the text to QPlainTextEdit's appendPlainText(QString).


                                If debugging is the process of removing software bugs, then programming must be the process of putting them in.

                                ~E. W. Dijkstra

                                JonBJ 1 Reply Last reply
                                4
                                • Pl45m4P Pl45m4

                                  @AnneRanch

                                  Back to lambdas:

                                  You said, you are struggling to understand lambda connections correctly.
                                  It's not as complicated as it might look.

                                  • You have your sender (first argument)

                                    connect(ui->list,.....)
                                    
                                  • You have your sender's class + signal

                                     connect(ui->list, &QListWidget::itemDoubleClicked,.....)
                                    
                                  • Then you can define a scope for your lambda

                                    connect(ui->list, &QListWidget::itemDoubleClicked, this,......)
                                    
                                  • the last part consists of the capture, the function or slot arguments and the actual code itself, using the passed and captured values

                                    • Capture

                                      • "[ ]": None of the variables from current class / scope are captured and can be used inside lambda "code"
                                      • " [=]": Captures everything (by value!)
                                      • "[this] ": (current instance) or any combination of variables (e.g. [x, a]), to pick variables you need explicitely.
                                      • "[&]" or "[ &someVar ]": Captures by reference. Changes made inside lambda will affect and change the captured variable outside the lambda as well ( Thx, @JonB )
                                    • Signal / Slot arguments after capture inside ( .... ), e.g. if signal sends a QListWidgetItem, you need a (QListWidgetItem *item) here.

                                    • lambda code inside { .... }

                                      • do whatever you like and what you would put in your slot here.

                                  One big advantage using lambda connections is, that you can connect signals to slots (or "code"), that would be incompatible using a "direct" connection because of any reason (e.g. parameter mismatch).

                                  Simple example:

                                  // signal
                                  void signal(QString s);
                                  // slot
                                  void onSignalFired(int i);
                                  

                                  A direct connection of these two won't work neither using the SIGNAL(...) / SLOT( ... ) syntax
                                  (-> crash / error at runtime),
                                  nor using the function based connection &Class::signal... &Class::onSignalFired
                                  ( -> wont compile).

                                  With lambda, you can make it work:

                                  connect(this, &Class::signal, [] (QString s) {  onSignalFired( s.toInt() ); } ); 
                                  

                                  Instead of calling the slot, you could also skip the slot and do whatever you want to do with this string inside the lambda directly, e.g. send your number to a QLineEdit ("A" would lead to a 65, simple ASCII).

                                  @AnneRanch said in Please help with lambda sytax:

                                  Here is my current - under construction connect to copy the "list" lines.
                                  All it does - just compiles and cannot be tested , in existing code , due to this issue.

                                  ... and this is exactly where you can make use of lambdas ( as @jsulm already said ).
                                  Pass your QListWidgetItem from signal to your lambda, get the text from your item using text() (Qt Doc), then pass the text to QPlainTextEdit's appendPlainText(QString).

                                  JonBJ Offline
                                  JonBJ Offline
                                  JonB
                                  wrote on last edited by JonB
                                  #21

                                  @Pl45m4
                                  Since you've laid this out so neatly, may I suggest you add [&] to your Capture section, and note how it differs from [=]? Because some day someone's going to need it... :)

                                  1 Reply Last reply
                                  1
                                  • jsulmJ jsulm

                                    @AnneRanch said in Please help with lambda sytax:

                                    function on_pushButton_11_clicked
                                    @line 206

                                    Can you show your on_pushButton_11_clicked? The crash is there at line 206.

                                    A Offline
                                    A Offline
                                    Anonymous_Banned275
                                    wrote on last edited by
                                    #22

                                    @jsulm said in Please help with lambda sytax:

                                    @AnneRanch said in Please help with lambda sytax:

                                    function on_pushButton_11_clicked
                                    @line 206

                                    Can you show your on_pushButton_11_clicked? The crash is there at line 206.

                                    There it is.

                                    I have left in all the trace / debug stuff .
                                    And highlighted the line 206

                                    code// scan for nearby BT devices
                                    
                                    void MainWindow_CAT_TAB::on_pushButton_11_clicked()
                                    {
                                    #ifdef TRACE
                                        qDebug() << "QDEBUG TRACE ";
                                        qDebug() << "QDEBUG TRACE TASK \n\t\t void MainWindow_CAT_TAB::on_pushButton_11_clicked()  \n";
                                         qDebug() << "QDEBUG TRACE TASK \n\t\t find nearby BT devices \n";
                                        qDebug() << "file     " << __FILE__;
                                        qDebug() << "function "<<__FUNCTION__;
                                        qDebug() << "@line    " << __LINE__;
                                        qDebug()<<"TEMPORARY EXIT ";
                                        //exit(99);
                                    #endif
                                    //   ui->listWidget_5->(" addItem(on_pushButton_11_clicked()");
                                    //     ui->listWidget_5->(addItem(on_pushButton_11_clicked());
                                                 ui->listWidget_5->addItem(" addItem(on_pushButton_11_clicked()");
                                                 ui->listWidget_5->addItem(" addItem(on_pushButton_11_clicked()");
                                                 ui->listWidget_5->addItem("information_main.count())");
                                    
                                    
                                    #ifdef TRACE
                                        qDebug() << "QDEBUG TRACE ";
                                        qDebug() << "QDEBUG TRACE TASK \n\t\t START imoplement Device DiscoveryDialog  \n";
                                         qDebug() << "QDEBUG TRACE TASK \n\t\t find nearby BT devices \n";
                                        qDebug() << "file     " << __FILE__;
                                        qDebug() << "function "<<__FUNCTION__;
                                        **qDebug() << "@line    " << __LINE__;**
                                        qDebug()<<"TEMPORARY EXIT ";
                                        //exit(99);
                                    #endif
                                    
                                    // instatiate Devievce Discovery Dialog as in btscanner example
                                    DeviceDiscoveryDialog *DDD = new DeviceDiscoveryDialog();
                                    
                                    DDD->startScan();  // takes time 2 seconds for each device 
                                    
                                    DDD->show();
                                    
                                    #ifdef BYPASS
                                    // test add connect here
                                    connect(
                                                DDD->ui->list,
                                     //           SIGNAL(DDD->ui->list->itemChanged(TEST_LABEL)),
                                                  SIGNAL(itemChanged(TEST_LABEL)),
                                                DDD->ui->plainTextEdit,
                                     //           SLOT(DDD->ui->plainTextEdit->appendPlainText(TEST_LABEL))
                                                SLOT(appendPlainText(TEST_LABEL))
                                            );
                                    #endif
                                    
                                    
                                    #ifdef TRACE
                                        qDebug() << "QDEBUG TRACE ";
                                        qDebug() << "QDEBUG TRACE TASK \n\t\t END imoplement Device DiscoiveryDialog  \n";
                                         qDebug() << "QDEBUG TRACE TASK \n\t\t find nearby BT devices \n";
                                        qDebug() << "file     " << __FILE__;
                                        qDebug() << "function "<<__FUNCTION__;
                                        qDebug() << "@line    " << __LINE__;
                                        qDebug()<<"TEMPORARY EXIT ";
                                        //exit(99);
                                    #endif
                                    
                                    
                                    }_text
                                    
                                    1 Reply Last reply
                                    -1
                                    • Christian EhrlicherC Offline
                                      Christian EhrlicherC Offline
                                      Christian Ehrlicher
                                      Lifetime Qt Champion
                                      wrote on last edited by
                                      #23

                                      @AnneRanch said in Please help with lambda sytax:

                                      SIGNAL(itemChanged(TEST_LABEL)),

                                      And you really want to tell us that you read at least one sentence from what we're telling you here??

                                      Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
                                      Visit the Qt Academy at https://academy.qt.io/catalog

                                      A 1 Reply Last reply
                                      0
                                      • Christian EhrlicherC Christian Ehrlicher

                                        @AnneRanch said in Please help with lambda sytax:

                                        SIGNAL(itemChanged(TEST_LABEL)),

                                        And you really want to tell us that you read at least one sentence from what we're telling you here??

                                        A Offline
                                        A Offline
                                        Anonymous_Banned275
                                        wrote on last edited by
                                        #24

                                        Partial success.
                                        Using both old and new "connect" style throws "segmentation fault" at either one.

                                        It is my understanding that "connect" code placement is not critical - however my crash occurs exactly on "connect" which I have placed in a secondary dialog constructor. My main window dialog is primary.

                                        RTFM implies that passing null pointer may be the problem...

                                        A 1 Reply Last reply
                                        0
                                        • A Anonymous_Banned275

                                          Partial success.
                                          Using both old and new "connect" style throws "segmentation fault" at either one.

                                          It is my understanding that "connect" code placement is not critical - however my crash occurs exactly on "connect" which I have placed in a secondary dialog constructor. My main window dialog is primary.

                                          RTFM implies that passing null pointer may be the problem...

                                          A Offline
                                          A Offline
                                          Anonymous_Banned275
                                          wrote on last edited by
                                          #25

                                          @AnneRanch DONE!
                                          Ready to tackle lambda .
                                          Moral of the story - stay on original issue - it was my shallow knowledge of "connect" , my wrong syntax and my implementation of "connect" - applied in wrong place.

                                          Help from everybody assisting is very much appreciated.

                                          62318e6e-6ee2-4e8f-b993-51ed61c92d1b-image.png

                                          Pablo J. RoginaP 1 Reply Last reply
                                          1

                                          • Login

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