c++qt

QCombobox disabled state styling


I need to style custom QComboBox's disabled state. For normal state I use stylesheet like that:

"QComboBox {"
    "border: 1px solid grey;" 
    "border-radius: 8px;" 
    "combobox-popup: 0;" 
    "background: transparent;"
    "padding: 0px 0px 0px 10px;""}" 

And it works OK.

When I use "QComboBox:disabled{}" stylesheet nothing happens and widget is drawn with usual disabled colors. What should I do?

Here's full widget code(widget is created in Designer):

customdropdown::customdropdown(QWidget *parent) : QComboBox(parent)
{
    this->view()->window()->setWindowFlags(Qt::Popup | Qt::FramelessWindowHint | Qt::NoDropShadowWindowHint );
    this->view()->window()->setAttribute(Qt::WA_TranslucentBackground);
    this->setItemDelegate(new Delegate());
    setStyleSheet("QComboBox {"                                 //ComboBox
         "border: 1px solid grey;"
         "border-radius: 8px;"
         "combobox-popup: 0;"
         "background: transparent;"
         "padding: 0px 0px 0px 10px;""}"
   "QComboBox QAbstractItemView {"
          "color: black;"
          "border: 1px solid grey;"
          "border-radius: 8px;""}"
    "QListView::item {"
          "height: 26px;""}"
    "QComboBox::down-arrow {"
         "image: url("\":/rsc/img/down_arrow.png\"");""}"
    "QComboBox::drop-down:button {"
          "border: 1px solid grey;"
          "border-radius: 8px;"
          "border-left: none;"
          "background-color: transparent;"
          "width: 30px;""}"
    "QComboBox:disabled{"
          "border: 1px solid red;"
          "border-radius: 8px;"
          "combobox-popup: 0;"
          "background: red;"
          "padding: 0px 0px 0px 10px;""}");
}

void Delegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
    QPainterPath path;
    path.addRect(option.rect.x(), option.rect.y(), option.rect.width(), option.rect.height());
    if (index.row() == (index.model()->rowCount()-1))  //if the last item
    {
        path.clear();
        path.addRoundedRect( option.rect, QString("8").toInt(), QString("8").toInt() );
        path.addRect( QRect( (option.rect.x()+option.rect.width()-10), option.rect.y(), 10, 10 ) ); // Top right corner not rounded
        path.addRect( QRect( option.rect.x(), option.rect.y(), 10, 10 ) ); // TOp left corner not rounded
    }
    painter->save();
    painter->setClipping(true);
    painter->setClipPath(path);
    QStyledItemDelegate::paint(painter, option, index);
    painter->restore();
}

Solution

  • I can't fully understand how it works, but the problem is in the order in which the widgets are initialized after ui->setupUi.

    Found two things that can help if your correct stylesheet doesn't work:

    1. custom widget declaration shouldn't be in mainwindow.cpp
    2. widget stylesheet should be applied in some method(NOT in the constructor)

    In my case I added initWin() method to my custom widget, moved setStylesheet() into it and then called initWin() from mainwindow(AFTER ui->setupUi) like this: ui->_objectName_->initWin(). If there's several widget you need to style, you can access them with

    foreach (auto var, this->findChildren<_className_ *>()) 
        {
            var->initWin();
        }