Check if buttons hidden on the widget



  • Hi! I want to create the search by button text and display the message when no button is found.

    My code:

    QList<QPushButton *> allButtons = testWidget->findChildren<QPushButton *>();
    
    connect(testLineEdit, &QLineEdit::textChanged, [this](const QString &text) {
            for (QPushButton *button : allButtons) {
                 if (button->text().contains(text, Qt::CaseInsensitive)) {
                     button->setVisible(true);
                 } else {
                     button->setVisible(false);
                 }
            }
    });
    

    This code works, but I can't detect when all buttons are hidden (not visible) on the widget.

    I have tried to check when editing is finished but it displays no found even when 1 item is found:

    connect(testLineEdit, &QLineEdit::editingFinished, [this]() {
            bool isHidden = false;
    
            for (QPushButton *button: allButtons) {
                 if (!button->isVisible() && !testLineEdit->text().isEmpty()) {
                     isHidden = true;
                 } else {
                     isHidden = false;
                 }
            }
    
            qDebug() << isHidden;
    
            if (isHidden) {
                qDebug() << "Hidden!";
            }
     });
    

    Any ideas how to check if all buttons are hidden? Thanks.



  • So, I removed the connect(testLineEdit, &QLineEdit::editingFinished... and fixed it like this:

    bool isButtonVisible = false;
    
    connect(testLineEdit, &QLineEdit::textChanged, [this, isButtonVisible](const QString &text) {
        for (QPushButton *button: allButtons) {
           if (!text.isEmpty()) {
              if (button->text().contains(data, Qt::CaseInsensitive)) {
                  button->setVisible(true);
                  isButtonVisible = true;
                  break;
              }
    
              button->setVisible(false);
              isButtonVisible = false;
           } else {
             button->setVisible(true);
           }
        }
    
      if (!isButtonVisible) {
            qDebug() << "No button is found!";
      }
    });
    

    After some checking, it still not working as expected. For example, when full search string provided, other buttons are visible, not hidden.



  • I tried to search by indexOf function but it returns -1 even when 1 item is found? The same with contains(), it returns false but some buttons are visible. Any ideas why? Thanks.

    Code:

    int testIndex = 0;
     connect(testLineEdit, &QLineEdit::textChanged, [this, testIndex ](const QString &text) mutable {
            for (QPushButton *button: allButtons) {
                if (!text.isEmpty()) {
                    testIndex = button->text().indexOf(text, 0, Qt::CaseInsensitive);
    
                    qDebug() << testIndex;
    
                    if (testIndex != -1) {
                        button->setVisible(true);
                    } else if (testIndex == -1) {
                        button->setVisible(false);
                        qDebug() << "No item is found!";
                    }
                } else {
                    button->setVisible(true);
                }
            }
        });
    

  • Lifetime Qt Champion

    Hi,

    You logic is a bit strange. Shouldn't you rather start by doing a two pass logic ?
    i.e.:

    1. Check all buttons for text and set visible property
    2. Check all buttons for visibility

    Once you have that running properly, you can refactor the code to do it in one pass. There are several techniques to know whether all buttons are hidden.



  • @SGaist

    I will check and fix it. Thanks.



  • @SGaist

    I have tried it:

    1. Loop to find the searched buttons text works well:
           for (QPushButton *button : allButtons) {
                if (!text.isEmpty()) {
                    if (!button->text().contains(text, Qt::CaseInsensitive)) {
                        button->setVisible(false);
                    } else {
                        button->setVisible(true);
                    }
                } else {
                    button->setVisible(true);
                }
            }
    
    1. The problem is that label is shown when some buttons are visible, I want to make this label visible only when all buttons are hidden. Checking buttons visibility with boolean doesn't work in this case.

    So, I need to check the widget for the visible/hidden buttons. What are other techniques to know whether all buttons are hidden? Thanks.


  • Lifetime Qt Champion

    Hi
    A fast test using your code works as expected so I do wonder why it won't for you.

    alt text

      ui->label->setVisible(false);
    
        connect(ui->lineEdit, &QLineEdit::textChanged, [this](const QString & text) {
            QList<QPushButton *> allButtons = ui->testwidget->findChildren<QPushButton *>();
            for (QPushButton *button : allButtons) {
                if (button->text().contains(text, Qt::CaseInsensitive)) {
                    button->setVisible(true);
                } else {
                    button->setVisible(false);
                }
                bool allHidden = true;
                for (QPushButton *button : allButtons) {
                    if ( button->isVisible()) {
                        allHidden = false;
                        continue;
                    }
                }
                ui->label->setVisible(allHidden);
            }
        });
    
    


  • @mrjj

    Hi! Yes, my code works except for this part:

    bool allHidden = true;
    
    for (QPushButton *button : allButtons) {
            if (button->isVisible()) {
                 allHidden = false;
                 continue;
            }
    }
    
    ui->label->setVisible(allHidden);
    

    Now it works as it should. The issue is resolved. Thank you.


  • Lifetime Qt Champion

    @Cobra91151
    Ehh, ok :)
    Guess the continue might have made the difference.



  • @mrjj

    I have checked it, and even without continue it works well. I think my logic was not correct.


  • Lifetime Qt Champion

    @Cobra91151
    Well the continue is just optimization.
    if one is visible, no reason to check the others.
    Works the same checking all, though.
    Yeah, i guess so. even i didn't notice what
    but maybe both checking text and visibility in
    the same loop had some side effect.


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.