#include "ElaComboBoxStyle.h" #include #include #include #include #include "ElaTheme.h" ElaComboBoxStyle::ElaComboBoxStyle(QStyle* style) { _pExpandIconRotate = 0; _pExpandMarkWidth = 0; _themeMode = eTheme->getThemeMode(); connect(eTheme, &ElaTheme::themeModeChanged, this, [=](ElaThemeType::ThemeMode themeMode) { _themeMode = themeMode; }); } ElaComboBoxStyle::~ElaComboBoxStyle() { } void ElaComboBoxStyle::drawPrimitive(PrimitiveElement element, const QStyleOption* option, QPainter* painter, const QWidget* widget) const { switch (element) { case QStyle::PE_Widget: case QStyle::PE_PanelLineEdit: { return; } #ifndef Q_OS_WIN case PE_PanelMenu: { return; } case PE_IndicatorArrowDown: { return; } #endif default: { break; } } QProxyStyle::drawPrimitive(element, option, painter, widget); } void ElaComboBoxStyle::drawControl(ControlElement element, const QStyleOption* option, QPainter* painter, const QWidget* widget) const { switch (element) { case QStyle::CE_ComboBoxLabel: { return; } case QStyle::CE_ShapedFrame: { //container区域 if (widget->objectName() == "ElaComboBoxContainer") { QRect viewRect = option->rect; painter->save(); painter->setRenderHints(QPainter::Antialiasing | QPainter::TextAntialiasing); eTheme->drawEffectShadow(painter, viewRect, _shadowBorderWidth, 6); QRect foregroundRect(viewRect.x() + _shadowBorderWidth, viewRect.y(), viewRect.width() - 2 * _shadowBorderWidth, viewRect.height() - _shadowBorderWidth); painter->setPen(ElaThemeColor(_themeMode, PopupBorder)); painter->setBrush(ElaThemeColor(_themeMode, PopupBase)); painter->drawRoundedRect(foregroundRect, 3, 3); painter->restore(); } return; } case QStyle::CE_ItemViewItem: { //覆盖高亮 if (const QStyleOptionViewItem* vopt = qstyleoption_cast(option)) { int margin = 2; painter->save(); painter->setRenderHints(QPainter::Antialiasing | QPainter::SmoothPixmapTransform); painter->setPen(Qt::NoPen); QPainterPath path; QRect optionRect = option->rect; optionRect.adjust(margin, margin, -margin, -margin); #ifndef Q_OS_WIN optionRect.adjust(6, 0, -6, 0); #endif path.addRoundedRect(optionRect, 5, 5); if (option->state & QStyle::State_Selected) { if (option->state & QStyle::State_MouseOver) { // 选中时覆盖 painter->setBrush(ElaThemeColor(_themeMode, BasicSelectedHoverAlpha)); painter->drawPath(path); } else { // 选中 painter->setBrush(ElaThemeColor(_themeMode, BasicSelectedAlpha)); painter->drawPath(path); } //选中Mark painter->setPen(Qt::NoPen); painter->setBrush(ElaThemeColor(_themeMode, PrimaryNormal)); painter->drawRoundedRect(QRectF(optionRect.x() + 3, optionRect.y() + optionRect.height() * 0.2, 3, optionRect.height() - +optionRect.height() * 0.4), 2, 2); } else { if (option->state & QStyle::State_MouseOver) { // 覆盖时颜色 painter->setBrush(ElaThemeColor(_themeMode, BasicHoverAlpha)); painter->drawPath(path); } } // 文字绘制 painter->setPen(ElaThemeColor(_themeMode, BasicText)); painter->drawText(QRect(option->rect.x() + 15, option->rect.y(), option->rect.width() - 15, option->rect.height()), Qt::AlignVCenter, vopt->text); painter->restore(); } return; } default: { break; } } QProxyStyle::drawControl(element, option, painter, widget); } void ElaComboBoxStyle::drawComplexControl(ComplexControl control, const QStyleOptionComplex* option, QPainter* painter, const QWidget* widget) const { switch (control) { case QStyle::CC_ComboBox: { //主体显示绘制 if (const QStyleOptionComboBox* copt = qstyleoption_cast(option)) { painter->save(); painter->setRenderHints(QPainter::SmoothPixmapTransform | QPainter::Antialiasing | QPainter::TextAntialiasing); //背景绘制 bool isEnabled = copt->state.testFlag(QStyle::State_Enabled); painter->setPen(ElaThemeColor(_themeMode, BasicBorder)); painter->setBrush(isEnabled ? (copt->state.testFlag(QStyle::State_HasFocus) && copt->editable) ? ElaThemeColor(_themeMode, DialogBase) : copt->state.testFlag(QStyle::State_MouseOver) ? ElaThemeColor(_themeMode, BasicHover) : ElaThemeColor(_themeMode, BasicBase) : ElaThemeColor(_themeMode, BasicDisable)); QRect comboBoxRect = copt->rect; comboBoxRect.adjust(_shadowBorderWidth, 1, -_shadowBorderWidth, -1); painter->drawRoundedRect(comboBoxRect, 3, 3); // 底边线绘制 painter->setPen(ElaThemeColor(_themeMode, BasicBaseLine)); painter->drawLine(comboBoxRect.x() + 3, comboBoxRect.y() + comboBoxRect.height(), comboBoxRect.x() + comboBoxRect.width() - 3, comboBoxRect.y() + comboBoxRect.height()); //文字绘制 if (!copt->editable) { QRect textRect = subControlRect(QStyle::CC_ComboBox, copt, QStyle::SC_ScrollBarSubLine, widget); painter->setPen(isEnabled ? ElaThemeColor(_themeMode, BasicText) : ElaThemeColor(_themeMode, BasicTextDisable)); painter->drawText(textRect, Qt::AlignVCenter | Qt::AlignLeft, copt->currentText); } //展开指示器绘制 painter->setPen(Qt::NoPen); painter->setBrush(ElaThemeColor(_themeMode, PrimaryNormal)); painter->drawRoundedRect(QRectF(comboBoxRect.center().x() - _pExpandMarkWidth, comboBoxRect.y() + comboBoxRect.height() - 3, _pExpandMarkWidth * 2, 3), 2, 2); // 展开图标绘制 QRect expandIconRect = subControlRect(QStyle::CC_ComboBox, copt, QStyle::SC_ScrollBarAddPage, widget); if (expandIconRect.isValid()) { QFont iconFont = QFont("ElaAwesome"); iconFont.setPixelSize(17); painter->setFont(iconFont); painter->setPen(isEnabled ? ElaThemeColor(_themeMode, BasicText) : ElaThemeColor(_themeMode, BasicTextDisable)); painter->translate(expandIconRect.x() + (qreal)expandIconRect.width() / 2, expandIconRect.y() + (qreal)expandIconRect.height() / 2); painter->rotate(_pExpandIconRotate); painter->translate(-expandIconRect.x() - (qreal)expandIconRect.width() / 2, -expandIconRect.y() - (qreal)expandIconRect.height() / 2); painter->drawText(expandIconRect, Qt::AlignCenter, QChar((unsigned short)ElaIconType::AngleDown)); painter->restore(); } } return; } default: { break; } } QProxyStyle::drawComplexControl(control, option, painter, widget); } QRect ElaComboBoxStyle::subControlRect(ComplexControl cc, const QStyleOptionComplex* opt, SubControl sc, const QWidget* widget) const { switch (cc) { case QStyle::CC_ComboBox: { switch (sc) { case QStyle::SC_ScrollBarSubLine: { //文字区域 QRect textRect = QProxyStyle::subControlRect(cc, opt, sc, widget); textRect.setLeft(16); textRect.setRight(textRect.right() - 15); return textRect; } case QStyle::SC_ScrollBarAddPage: { //展开图标区域 QRect expandIconRect = QProxyStyle::subControlRect(cc, opt, sc, widget); expandIconRect.setLeft(expandIconRect.left() - 25); return expandIconRect; } default: { break; } } break; } default: { break; } } return QProxyStyle::subControlRect(cc, opt, sc, widget); } QSize ElaComboBoxStyle::sizeFromContents(ContentsType type, const QStyleOption* option, const QSize& size, const QWidget* widget) const { switch (type) { case QStyle::CT_ItemViewItem: { QSize itemSize = QProxyStyle::sizeFromContents(type, option, size, widget); itemSize.setHeight(35); return itemSize; } case QStyle::CT_ComboBox: { QSize comboBoxSize = QProxyStyle::sizeFromContents(type, option, size, widget); comboBoxSize.setWidth(comboBoxSize.width() + 26); return comboBoxSize; } default: { break; } } return QProxyStyle::sizeFromContents(type, option, size, widget); }