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. Button inherit stylesheet for no reason
QtWS25 Last Chance

Button inherit stylesheet for no reason

Scheduled Pinned Locked Moved Solved General and Desktop
qpushbuttmouseeventstylesheet
17 Posts 6 Posters 3.1k 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.
  • L Offline
    L Offline
    legitnameyo
    wrote on 22 Apr 2019, 15:48 last edited by legitnameyo
    #1

    The button "last_button" for some reason takes on the same style sheet as "the_button". This did not happen before I replaced QPushButton with QClickAgnostic.

    MainWindow.h

    private slots:
        void on_btn_left_click();
        void on_btn_right_click();
    
    private:
            QClickAgnostic * last_button = qobject_cast<QClickAgnostic *> ( sender() );
    
    

    MainWindow.cpp

    void MainWindow::on_btn_left_click() {
        // Styles the previously selected button to look like a normal button
        last_button->setStyleSheet(QString("QPushButton {color: #444444; background: #e6e6e6; border: 2px solid #cccccc; border-width: 0px 0px 2px 0px;} QPushButton:hover {border: 2px black solid; color: #333333;background-color: #F7F7F7;} QPushButton:pressed {background: #e6e6e6;}"));
    
         // retrieves the pressed button
         QClickAgnostic * the_button = qobject_cast<QClickAgnostic *> ( sender() );
    
         if(the_button)  {
             // code...
         
           // Styles the current button to look like a clicked button
            the_button->setStyleSheet(QString("QPushButton {color: #444444; background: #cccccc; border: 2px solid #cccccc; border-width: 0px 0px 2px 0px;} QPushButton:hover {border: 2px black solid; color: #333333; background-color: #F7F7F7;} QPushButton:pressed {background: #cccccc;}"));
    }
        // makes last button this button since this button will be last button next time a click event occurs
        // Has never, until QClickAgnostic, inherited the style sheet of the_button.
         last_button = the_button;
    }
    

    qclickagnostic.h

    #ifndef QCLICKAGNOSTIC_H
    #define QCLICKAGNOSTIC_H
    
    #include <QPushButton>
    #include <QMouseEvent>
    
    class QClickAgnostic : public QPushButton
    {
        Q_OBJECT
    
    public:
        explicit QClickAgnostic(QWidget *parent = nullptr);
    
    private slots:
        void mouseReleaseEvent(QMouseEvent *e);
    
    signals:
        void rightClicked();
        void leftClicked();
    
    public slots:
    
    };
    
    #endif // QCLICKAGNOSTIC_H
    

    qclickagnostic.cpp

    #include "qclickagnostic.h"
    
    QClickAgnostic::QClickAgnostic(QWidget *parent) : QPushButton(parent)
    {
    // empty
    }
    
    void QClickAgnostic::mouseReleaseEvent(QMouseEvent *e) {
        if(e->button() == Qt::LeftButton) {
            emit leftClicked();
        } else if(e->button() == Qt::RightButton) {
            emit rightClicked();
        }
    }
    
    
    1 Reply Last reply
    0
    • M Offline
      M Offline
      mrjj
      Lifetime Qt Champion
      wrote on 22 Apr 2019, 16:57 last edited by
      #2

      Hi
      But it seems you just set a pointer
      last_button = the_button;
      so last_button just points to the_button; and
      hence it will look exactly the same.

      1 Reply Last reply
      5
      • L Offline
        L Offline
        legitnameyo
        wrote on 23 Apr 2019, 16:54 last edited by legitnameyo
        #3

        Yes it seems as if you're right. How do I solve this? I haven't had this issue before when I declared both the_button and last_button as QPushButton instead of my custom QPushButton class

        J M 2 Replies Last reply 23 Apr 2019, 17:14
        0
        • L legitnameyo
          23 Apr 2019, 16:54

          Yes it seems as if you're right. How do I solve this? I haven't had this issue before when I declared both the_button and last_button as QPushButton instead of my custom QPushButton class

          J Offline
          J Offline
          JonB
          wrote on 23 Apr 2019, 17:14 last edited by
          #4

          @legitnameyo
          I'm not an expert C++-er, but I don't get how your code works.

          private:
                  QClickAgnostic * last_button = qobject_cast<QClickAgnostic *> ( sender() );
          

          What is sender() at the point this is initialized?

          void MainWindow::on_btn_left_click() {
              last_button->setStyleSheet(QString("QPushButton {color: #444444; background: #e6e6e6; border: 2px solid #cccccc; border-width: 0px 0px 2px 0px;} QPushButton:hover {border: 2px black solid; color: #333333;background-color: #F7F7F7;} QPushButton:pressed {background: #e6e6e6;}"));
          

          What is the value of last_button the very first time this function gets called?

          J 1 Reply Last reply 23 Apr 2019, 19:13
          2
          • L legitnameyo
            23 Apr 2019, 16:54

            Yes it seems as if you're right. How do I solve this? I haven't had this issue before when I declared both the_button and last_button as QPushButton instead of my custom QPushButton class

            M Offline
            M Offline
            mrjj
            Lifetime Qt Champion
            wrote on 23 Apr 2019, 19:03 last edited by mrjj
            #5

            @legitnameyo

            • . How do I solve this

            By doing it the Qt way.
            I assume you have a grid of buttons and only one to be selected at a given time so if you select another
            it should be drawn as normal and new as pressed. At least that's how i read your code.

            You can do that very easily with a QButtonGroup and the Checkable property on each button.
            Then Qt does the housekeeping for you.
            You can style the look when "selected" with QPushButton:checked
            That way you dont need last_button and you can apply the stylesheet to the parent and it will just work
            with setting / resetting the style.

            alt text

            alt text

            alt text

            alt text

            result
            alt text

            1 Reply Last reply
            6
            • J JonB
              23 Apr 2019, 17:14

              @legitnameyo
              I'm not an expert C++-er, but I don't get how your code works.

              private:
                      QClickAgnostic * last_button = qobject_cast<QClickAgnostic *> ( sender() );
              

              What is sender() at the point this is initialized?

              void MainWindow::on_btn_left_click() {
                  last_button->setStyleSheet(QString("QPushButton {color: #444444; background: #e6e6e6; border: 2px solid #cccccc; border-width: 0px 0px 2px 0px;} QPushButton:hover {border: 2px black solid; color: #333333;background-color: #F7F7F7;} QPushButton:pressed {background: #e6e6e6;}"));
              

              What is the value of last_button the very first time this function gets called?

              J Offline
              J Offline
              J.Hilk
              Moderators
              wrote on 23 Apr 2019, 19:13 last edited by
              #6

              @JonB

              What is sender() at the point this is initialized?

              as it's a qobject_cast and doesn't crash on start up, most likely a nullptr?

              What is the value of last_button the very first time this function gets called?

              as it's not checked against 0, it should fail. Maybe luck?

              using sender() is bad design anyway. One shouldn't use it if possible.

              @mrjj posted a nice qt alternative I would suggest the OP to use that ;)


              Be aware of the Qt Code of Conduct, when posting : https://forum.qt.io/topic/113070/qt-code-of-conduct


              Q: What's that?
              A: It's blue light.
              Q: What does it do?
              A: It turns blue.

              1 Reply Last reply
              4
              • L Offline
                L Offline
                legitnameyo
                wrote on 25 Apr 2019, 12:21 last edited by
                #7

                How do I implement this code way? I do my UI in code since that's what I prefer. This is what I've got so far and it isn't working...

                QButtonGroup *g_btns = new QButtonGroup(this);
                /* all buttons are created and I add the buttons in about this way*/
                btn1->setCheckable(true);
                //etc..
                g_btns->addButton(btn1);
                g_btns->addButton(btn2);
                g_btns->addButton(btn3);
                // etc ...
                
                      connect(g_btns, SIGNAL(buttonClicked(int)), this, SLOT(onGroupButtonClicked(int)));
                
                void MainWindow::onGroupButtonClicked(int btn_id) {
                qDebug() << "clicked!";
                }
                

                And this gives me nothing. The onGroupButtonClicked does not activate.

                J jsulmJ 2 Replies Last reply 25 Apr 2019, 12:25
                0
                • L legitnameyo
                  25 Apr 2019, 12:21

                  How do I implement this code way? I do my UI in code since that's what I prefer. This is what I've got so far and it isn't working...

                  QButtonGroup *g_btns = new QButtonGroup(this);
                  /* all buttons are created and I add the buttons in about this way*/
                  btn1->setCheckable(true);
                  //etc..
                  g_btns->addButton(btn1);
                  g_btns->addButton(btn2);
                  g_btns->addButton(btn3);
                  // etc ...
                  
                        connect(g_btns, SIGNAL(buttonClicked(int)), this, SLOT(onGroupButtonClicked(int)));
                  
                  void MainWindow::onGroupButtonClicked(int btn_id) {
                  qDebug() << "clicked!";
                  }
                  

                  And this gives me nothing. The onGroupButtonClicked does not activate.

                  J Offline
                  J Offline
                  J.Hilk
                  Moderators
                  wrote on 25 Apr 2019, 12:25 last edited by
                  #8

                  @legitnameyo I never used QButtonGroup, but a quick look into the documentation tells me, you never gave your added buttons an ID

                  void QButtonGroup::addButton(QAbstractButton *button, int id = -1)

                  I'm guessing here and say, that buttons with the ID of -1 do not emit the buttonClicked(int) signal


                  Be aware of the Qt Code of Conduct, when posting : https://forum.qt.io/topic/113070/qt-code-of-conduct


                  Q: What's that?
                  A: It's blue light.
                  Q: What does it do?
                  A: It turns blue.

                  M 1 Reply Last reply 25 Apr 2019, 12:47
                  3
                  • L legitnameyo
                    25 Apr 2019, 12:21

                    How do I implement this code way? I do my UI in code since that's what I prefer. This is what I've got so far and it isn't working...

                    QButtonGroup *g_btns = new QButtonGroup(this);
                    /* all buttons are created and I add the buttons in about this way*/
                    btn1->setCheckable(true);
                    //etc..
                    g_btns->addButton(btn1);
                    g_btns->addButton(btn2);
                    g_btns->addButton(btn3);
                    // etc ...
                    
                          connect(g_btns, SIGNAL(buttonClicked(int)), this, SLOT(onGroupButtonClicked(int)));
                    
                    void MainWindow::onGroupButtonClicked(int btn_id) {
                    qDebug() << "clicked!";
                    }
                    

                    And this gives me nothing. The onGroupButtonClicked does not activate.

                    jsulmJ Offline
                    jsulmJ Offline
                    jsulm
                    Lifetime Qt Champion
                    wrote on 25 Apr 2019, 12:26 last edited by
                    #9

                    @legitnameyo It should work. Do you get any warnings at runtime (related to connect)?
                    Is g_btns in connect() really the one you're creating at the beginning of the code snippet you provided?

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

                    1 Reply Last reply
                    3
                    • J J.Hilk
                      25 Apr 2019, 12:25

                      @legitnameyo I never used QButtonGroup, but a quick look into the documentation tells me, you never gave your added buttons an ID

                      void QButtonGroup::addButton(QAbstractButton *button, int id = -1)

                      I'm guessing here and say, that buttons with the ID of -1 do not emit the buttonClicked(int) signal

                      M Offline
                      M Offline
                      mrjj
                      Lifetime Qt Champion
                      wrote on 25 Apr 2019, 12:47 last edited by
                      #10

                      @J.Hilk
                      Was a good guess,
                      but it seems, it will use negative values for auto numbering and does, in fact, emit them.

                        QButtonGroup *buttonGroup = new QButtonGroup(this);
                      
                          buttonGroup->addButton( ui->pushButton_2);
                          buttonGroup->addButton( ui->pushButton_3);
                          buttonGroup->addButton( ui->pushButton_4);
                          buttonGroup->addButton( ui->pushButton_5);
                      
                      
                          connect(buttonGroup, static_cast<void(QButtonGroup::*)(int)>(&QButtonGroup::buttonClicked),
                          [ = ](int id) {
                              qDebug() << id;
                          });
                      
                      

                      outputs.
                      -2
                      -2
                      -3
                      -5
                      -4

                      J 1 Reply Last reply 25 Apr 2019, 12:56
                      1
                      • M mrjj
                        25 Apr 2019, 12:47

                        @J.Hilk
                        Was a good guess,
                        but it seems, it will use negative values for auto numbering and does, in fact, emit them.

                          QButtonGroup *buttonGroup = new QButtonGroup(this);
                        
                            buttonGroup->addButton( ui->pushButton_2);
                            buttonGroup->addButton( ui->pushButton_3);
                            buttonGroup->addButton( ui->pushButton_4);
                            buttonGroup->addButton( ui->pushButton_5);
                        
                        
                            connect(buttonGroup, static_cast<void(QButtonGroup::*)(int)>(&QButtonGroup::buttonClicked),
                            [ = ](int id) {
                                qDebug() << id;
                            });
                        
                        

                        outputs.
                        -2
                        -2
                        -3
                        -5
                        -4

                        J Offline
                        J Offline
                        J.Hilk
                        Moderators
                        wrote on 25 Apr 2019, 12:56 last edited by
                        #11

                        @mrjj
                        I find this behavior actually not very intuitive.

                        That the id increases when non is specified, maybe...
                        But a higher negative number !?


                        Be aware of the Qt Code of Conduct, when posting : https://forum.qt.io/topic/113070/qt-code-of-conduct


                        Q: What's that?
                        A: It's blue light.
                        Q: What does it do?
                        A: It turns blue.

                        M 1 Reply Last reply 25 Apr 2019, 13:01
                        0
                        • J J.Hilk
                          25 Apr 2019, 12:56

                          @mrjj
                          I find this behavior actually not very intuitive.

                          That the id increases when non is specified, maybe...
                          But a higher negative number !?

                          M Offline
                          M Offline
                          mrjj
                          Lifetime Qt Champion
                          wrote on 25 Apr 2019, 13:01 last edited by
                          #12

                          @J.Hilk
                          Yep. I had to test it as sounded odd it would auto number with negative values.
                          But it seems design wants to allow to have some auto numbered and some manually
                          even i don't see why.

                          J 1 Reply Last reply 25 Apr 2019, 13:13
                          1
                          • M mrjj
                            25 Apr 2019, 13:01

                            @J.Hilk
                            Yep. I had to test it as sounded odd it would auto number with negative values.
                            But it seems design wants to allow to have some auto numbered and some manually
                            even i don't see why.

                            J Offline
                            J Offline
                            JonB
                            wrote on 25 Apr 2019, 13:13 last edited by
                            #13

                            @mrjj
                            Negative-decrementing auto-numbers are usually used for "anonymous" items while allowing positive numbers for explicit use. Then the numbers won't clash.

                            1 Reply Last reply
                            3
                            • L Offline
                              L Offline
                              legitnameyo
                              wrote on 25 Apr 2019, 16:18 last edited by legitnameyo
                              #14

                              There is NO error such as this one below

                              QMetaObject::connectSlotsByName: No matching signal for onGroupButtonClicked(int)
                              

                              And yes g_btns is defined only ONCE. Everything is in the order I got it in my code. However one thing that might change things up is that I use a custom class for my buttons called QClickAgnostic, which inherits from QPushButton as such above

                              and the buttons are created like this

                                      QClickAgnostic *btn = new QClickAgnostic(ui->frame_of_btns);
                              
                              KillerSmathK 1 Reply Last reply 25 Apr 2019, 17:14
                              0
                              • L legitnameyo
                                25 Apr 2019, 16:18

                                There is NO error such as this one below

                                QMetaObject::connectSlotsByName: No matching signal for onGroupButtonClicked(int)
                                

                                And yes g_btns is defined only ONCE. Everything is in the order I got it in my code. However one thing that might change things up is that I use a custom class for my buttons called QClickAgnostic, which inherits from QPushButton as such above

                                and the buttons are created like this

                                        QClickAgnostic *btn = new QClickAgnostic(ui->frame_of_btns);
                                
                                KillerSmathK Offline
                                KillerSmathK Offline
                                KillerSmath
                                wrote on 25 Apr 2019, 17:14 last edited by
                                #15

                                @legitnameyo
                                You need to notify the ButtonGroup about the click event.

                                I took a look at the source code of the abstractbutton and noticed the button directly notifies the group that it was clicked. But you broke this step when you reimplemented the MouseReleaseEvent function.

                                See a snippet of this step.

                                void QAbstractButton::mouseReleaseEvent(QMouseEvent *e)
                                {
                                ...
                                    if (hitButton(e->pos())) {
                                        d->repeatTimer.stop();
                                        d->click(); // call click function 
                                        e->accept();
                                    } else {
                                        setDown(false);
                                        e->ignore();
                                    }
                                }
                                void QAbstractButtonPrivate::click()
                                {
                                    ...
                                    if (guard)
                                        emitReleased();
                                    if (guard)
                                        emitClicked(); // call emitClicked
                                }
                                
                                void QAbstractButtonPrivate::emitClicked()
                                {
                                  ...
                                #if QT_CONFIG(buttongroup)
                                    if (guard && group) {
                                        emit group->buttonClicked(group->id(q)); // emit the signal
                                        if (guard && group)
                                            emit group->buttonClicked(q); // emit the signal
                                    }
                                #endif
                                }
                                

                                So, you can solve this problem calling the click() function inside MouseReleaseEvent.

                                void QClickAgnostic::mouseReleaseEvent(QMouseEvent *e) {
                                    if(e->button() == Qt::LeftButton) {
                                        click(); // called
                                        emit leftClicked();
                                    } else if(e->button() == Qt::RightButton) {
                                        click(); // called
                                        emit rightClicked();
                                    }
                                }
                                

                                @Computer Science Student - Brazil
                                Web Developer and Researcher
                                “Sometimes it’s the people no one imagines anything of who do the things that no one can imagine.” - Alan Turing

                                M 1 Reply Last reply 25 Apr 2019, 17:22
                                5
                                • KillerSmathK KillerSmath
                                  25 Apr 2019, 17:14

                                  @legitnameyo
                                  You need to notify the ButtonGroup about the click event.

                                  I took a look at the source code of the abstractbutton and noticed the button directly notifies the group that it was clicked. But you broke this step when you reimplemented the MouseReleaseEvent function.

                                  See a snippet of this step.

                                  void QAbstractButton::mouseReleaseEvent(QMouseEvent *e)
                                  {
                                  ...
                                      if (hitButton(e->pos())) {
                                          d->repeatTimer.stop();
                                          d->click(); // call click function 
                                          e->accept();
                                      } else {
                                          setDown(false);
                                          e->ignore();
                                      }
                                  }
                                  void QAbstractButtonPrivate::click()
                                  {
                                      ...
                                      if (guard)
                                          emitReleased();
                                      if (guard)
                                          emitClicked(); // call emitClicked
                                  }
                                  
                                  void QAbstractButtonPrivate::emitClicked()
                                  {
                                    ...
                                  #if QT_CONFIG(buttongroup)
                                      if (guard && group) {
                                          emit group->buttonClicked(group->id(q)); // emit the signal
                                          if (guard && group)
                                              emit group->buttonClicked(q); // emit the signal
                                      }
                                  #endif
                                  }
                                  

                                  So, you can solve this problem calling the click() function inside MouseReleaseEvent.

                                  void QClickAgnostic::mouseReleaseEvent(QMouseEvent *e) {
                                      if(e->button() == Qt::LeftButton) {
                                          click(); // called
                                          emit leftClicked();
                                      } else if(e->button() == Qt::RightButton) {
                                          click(); // called
                                          emit rightClicked();
                                      }
                                  }
                                  
                                  M Offline
                                  M Offline
                                  mrjj
                                  Lifetime Qt Champion
                                  wrote on 25 Apr 2019, 17:22 last edited by
                                  #16

                                  @KillerSmath
                                  Good digging !

                                  1 Reply Last reply
                                  1
                                  • L Offline
                                    L Offline
                                    legitnameyo
                                    wrote on 25 Apr 2019, 17:45 last edited by
                                    #17

                                    @KillerSmath fix did the work, combined with @mrjj QGroupButton! I added this code to style the pressed button

                                    void MainWindow::onGroupButtonClicked(int btn_id) {
                                        g_btns->button(btn_id)->setStyleSheet(QString("QPushButton {color: #444444; background: #cccccc; border: 2px solid #cccccc; border-width: 0px 0px 2px 0px;} QPushButton:hover {border: 2px black solid; color: #333333; background-color: #F7F7F7;} QPushButton:pressed {background: #cccccc;}"));
                                    }
                                    
                                    

                                    Thanks a lot guys!

                                    1 Reply Last reply
                                    1

                                    1/17

                                    22 Apr 2019, 15:48

                                    • Login

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