Qt (C++): dynamically style an individual tab in QTabWidget

孤者浪人 提交于 2019-12-24 06:43:33

问题


I know, that this question has been discussed here and on other sites, but there has not been a really solution yet, although I think, that I'm not the only one with this problem:

How can I individually and dynamically access a single tab (not its content resp. the widget in the tab) for styling purposes, such as changing the background color or adding graphical effects to it? An application could be to notify the user, that a tab requires his attention, by letting it flash in another color (like in the windows task bar, if a window wants to get focus). There is a function to change the text color, why not more? Stylesheets can be used to access the selected, the first etc. tab, but not a specific one by its index. Some people talked about subclassing QTabBar, but I do not know, how this will lead to the desired solution. Is there any possibility to achieve this and if yes, please provide an example.


回答1:


In order to access each style of each QTabBar tab you must overwrite the paintEvent() method of it.

The generic way of doing this should have the following structure:

void paintEvent(QPaintEvent *event){
    QStylePainter painter(this);
    QStyleOptionTab opt;

    for(int index = 0; index < count(); index++)
    {
        initStyleOption(&opt,index);
        /*Here make the changes*/
        painter.drawControl(QStyle::CE_TabBarTabShape, opt);
        painter.drawControl(QStyle::CE_TabBarTabLabel,opt);
    }
}

In this part I show an example of how to create a QTabWidget where it shows a tab that blinks and only ends the blinking if we click on that tab

TabBarAlert:

class TabBarAlert : public QTabBar
{
    int indexAlert = -1;
    QColor mColor;
    Q_OBJECT
public:
    TabBarAlert(QWidget *parent = Q_NULLPTR):QTabBar(parent)
    {
        mColor = Qt::red;
    }
    void setIndexAlert(int index){
        if(indexAlert == index)
            return;
        indexAlert = index;
        update();
    }

    int getIndexAlert() const{
        return indexAlert;
    }

    QColor getColor() const{
        return mColor;
    }
    void setColor(const QColor &color){
        if(color == mColor)
            return;
        mColor = color;
        update();
    }

protected:
    void paintEvent(QPaintEvent *event){

        if(indexAlert> -1 && indexAlert < count()){
            QStylePainter painter(this);
            QStyleOptionTab opt;

            for(int i = 0;i < count();i++)
            {
                initStyleOption(&opt,i);

                if(indexAlert == i)
                    opt.palette.setColor(QPalette::Button, mColor);
                painter.drawControl(QStyle::CE_TabBarTabShape, opt);
                painter.drawControl(QStyle::CE_TabBarTabLabel,opt);
            }
        }
        else{
            QTabBar::paintEvent(event);
        }
    }

};

TabWidgetAlert:

class TabWidgetAlert : public QTabWidget
{
    TabBarAlert *tb;
    QTimer *timer;
    bool on = false;
    int indexAlert = -1;

    Q_OBJECT
public:
    TabWidgetAlert(QWidget *parent = Q_NULLPTR):QTabWidget(parent)
    {
        tb = new TabBarAlert(this);
        setTabBar(tb);
        tb->setColor(Qt::black);

        /*
        *Disable the alert if the current tab matches the alert tab.
        */
        connect(this, &TabWidgetAlert::currentChanged, [this](int index){
            if(index == tb->getIndexAlert()){
                tb->setIndexAlert(-1);
                on = false;
                timer->stop();
           }
        });

        timer = new QTimer(this);

        /*
        *Create the blink
        */
        connect(timer, &QTimer::timeout, [this](){
            tb->setIndexAlert(on? indexAlert: -1);
            on = !on;
        });
    }

    void setAlert(int index){
        indexAlert = index;
        timer->start(100);
    }
};

The complete example can be found at the following link



来源:https://stackoverflow.com/questions/45909147/qt-c-dynamically-style-an-individual-tab-in-qtabwidget

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!