135void QCommonStyle::drawPrimitive(PrimitiveElement pe,
const QStyleOption *opt, QPainter *p,
136 const QWidget *widget)
const
138 Q_D(
const QCommonStyle);
140 case PE_FrameButtonBevel:
141 case PE_FrameButtonTool:
142 qDrawShadeRect(p, opt->rect, opt->palette,
143 opt->state & (State_Sunken | State_On), 1, 0);
145 case PE_PanelButtonCommand:
146 case PE_PanelButtonBevel:
147 case PE_PanelButtonTool:
148 case PE_IndicatorButtonDropDown:
149 qDrawShadePanel(p, opt->rect, opt->palette,
150 opt->state & (State_Sunken | State_On), 1,
151 &opt->palette.brush(QPalette::Button));
153 case PE_IndicatorItemViewItemCheck:
154 proxy()->drawPrimitive(PE_IndicatorCheckBox, opt, p, widget);
156 case PE_IndicatorCheckBox:
157 if (opt->state & State_NoChange) {
158 p->setPen(opt->palette.windowText().color());
159 p->fillRect(opt->rect, opt->palette.brush(QPalette::Button));
160 p->drawRect(opt->rect);
161 p->drawLine(opt->rect.topLeft(), opt->rect.bottomRight());
163 qDrawShadePanel(p, opt->rect.x(), opt->rect.y(), opt->rect.width(), opt->rect.height(),
164 opt->palette, opt->state & (State_Sunken | State_On), 1,
165 &opt->palette.brush(QPalette::Button));
168 case PE_IndicatorRadioButton: {
169 QRect ir = opt->rect;
170 p->setPen(opt->palette.dark().color());
171 p->drawArc(opt->rect, 0, 5760);
172 if (opt->state & (State_Sunken | State_On)) {
173 ir.adjust(2, 2, -2, -2);
174 p->setBrush(opt->palette.windowText());
178 case PE_FrameFocusRect:
179 if (
const QStyleOptionFocusRect *fropt = qstyleoption_cast<
const QStyleOptionFocusRect *>(opt)) {
180 QColor bg = fropt->backgroundColor;
184 bg.getHsv(&h, &s, &v);
190 color = opt->palette.windowText().color();
192 const QRect focusRect = opt->rect.adjusted(1, 1, -1, -1);
193 qDrawPlainRect(p, focusRect, color, 1);
196 case PE_IndicatorMenuCheckMark: {
197 const int markW = opt->rect.width() > 7 ? 7 : opt->rect.width();
198 const int markH = markW;
199 int posX = opt->rect.x() + (opt->rect.width() - markW)/2 + 1;
200 int posY = opt->rect.y() + (opt->rect.height() - markH)/2;
208 for (i = 0; i < markW/2; ++i) {
209 a << QLineF(xx, yy, xx, yy + 2);
214 for (; i < markH; ++i) {
215 a << QLineF(xx, yy, xx, yy + 2);
219 if (!(opt->state & State_Enabled) && !(opt->state & State_On)) {
220 QPainterStateGuard psg(p);
222 p->setPen(opt->palette.light().color());
225 p->setPen((opt->state & State_On) ? opt->palette.highlightedText().color() : opt->palette.text().color());
230 if (
const QStyleOptionFrame *frame = qstyleoption_cast<
const QStyleOptionFrame *>(opt)) {
231 if (pe == PE_FrameMenu || (frame->state & State_Sunken) || (frame->state & State_Raised)) {
232 qDrawShadePanel(p, frame->rect, frame->palette, frame->state & State_Sunken,
235 qDrawPlainRect(p, frame->rect, frame->palette.windowText().color(), frame->lineWidth);
239#if QT_CONFIG(toolbar)
240 case PE_PanelMenuBar:
241 if (widget && qobject_cast<QToolBar *>(widget->parentWidget()))
243 if (
const QStyleOptionFrame *frame = qstyleoption_cast<
const QStyleOptionFrame *>(opt)){
244 qDrawShadePanel(p, frame->rect, frame->palette,
false, frame->lineWidth,
245 &frame->palette.brush(QPalette::Button));
248 else if (
const QStyleOptionToolBar *frame = qstyleoption_cast<
const QStyleOptionToolBar *>(opt)){
249 qDrawShadePanel(p, frame->rect, frame->palette,
false, frame->lineWidth,
250 &frame->palette.brush(QPalette::Button));
256 case PE_PanelToolBar:
259#if QT_CONFIG(progressbar)
260 case PE_IndicatorProgressChunk:
262 bool vertical =
false;
263 if (
const QStyleOptionProgressBar *pb = qstyleoption_cast<
const QStyleOptionProgressBar *>(opt))
264 vertical = !(pb->state & QStyle::State_Horizontal);
266 p->fillRect(opt->rect.x(), opt->rect.y() + 3, opt->rect.width() -2, opt->rect.height() - 6,
267 opt->palette.brush(QPalette::Highlight));
269 p->fillRect(opt->rect.x() + 2, opt->rect.y(), opt->rect.width() -6, opt->rect.height() - 2,
270 opt->palette.brush(QPalette::Highlight));
275 case PE_IndicatorBranch: {
276 static const int decoration_size = 9;
277 int mid_h = opt->rect.x() + opt->rect.width() / 2;
278 int mid_v = opt->rect.y() + opt->rect.height() / 2;
283 if (opt->state & State_Children) {
284 int delta = decoration_size / 2;
289 p->drawLine(bef_h + 2, bef_v + 4, bef_h + 6, bef_v + 4);
290 if (!(opt->state & State_Open))
291 p->drawLine(bef_h + 4, bef_v + 2, bef_h + 4, bef_v + 6);
292 QPen oldPen = p->pen();
293 p->setPen(opt->palette.dark().color());
294 p->drawRect(bef_h, bef_v, decoration_size - 1, decoration_size - 1);
297 QBrush brush(opt->palette.dark().color(), Qt::Dense4Pattern);
298 if (opt->state & State_Item) {
299 if (opt->direction == Qt::RightToLeft)
300 p->fillRect(opt->rect.left(), mid_v, bef_h - opt->rect.left(), 1, brush);
302 p->fillRect(aft_h, mid_v, opt->rect.right() - aft_h + 1, 1, brush);
304 if (opt->state & State_Sibling)
305 p->fillRect(mid_h, aft_v, 1, opt->rect.bottom() - aft_v + 1, brush);
306 if (opt->state & (State_Open | State_Children | State_Item | State_Sibling))
307 p->fillRect(mid_h, opt->rect.y(), 1, bef_v - opt->rect.y(), brush);
309 case PE_FrameStatusBarItem:
310 qDrawShadeRect(p, opt->rect, opt->palette,
true, 1, 0,
nullptr);
312 case PE_IndicatorHeaderArrow:
313 if (
const QStyleOptionHeader *header = qstyleoption_cast<
const QStyleOptionHeader *>(opt)) {
314 QPainterStateGuard psg(p, QPainterStateGuard::InitialState::NoSave);
315 if (header->sortIndicator & QStyleOptionHeader::SortUp) {
317 p->setPen(QPen(opt->palette.light(), 0));
318 p->drawLine(opt->rect.x() + opt->rect.width(), opt->rect.y(),
319 opt->rect.x() + opt->rect.width() / 2, opt->rect.y() + opt->rect.height());
320 p->setPen(QPen(opt->palette.dark(), 0));
321 const QPoint points[] = {
322 QPoint(opt->rect.x() + opt->rect.width() / 2, opt->rect.y() + opt->rect.height()),
323 QPoint(opt->rect.x(), opt->rect.y()),
324 QPoint(opt->rect.x() + opt->rect.width(), opt->rect.y()),
326 p->drawPolyline(points,
sizeof points /
sizeof *points);
327 }
else if (header->sortIndicator & QStyleOptionHeader::SortDown) {
329 p->setPen(QPen(opt->palette.light(), 0));
330 const QPoint points[] = {
331 QPoint(opt->rect.x(), opt->rect.y() + opt->rect.height()),
332 QPoint(opt->rect.x() + opt->rect.width(), opt->rect.y() + opt->rect.height()),
333 QPoint(opt->rect.x() + opt->rect.width() / 2, opt->rect.y()),
335 p->drawPolyline(points,
sizeof points /
sizeof *points);
336 p->setPen(QPen(opt->palette.dark(), 0));
337 p->drawLine(opt->rect.x(), opt->rect.y() + opt->rect.height(),
338 opt->rect.x() + opt->rect.width() / 2, opt->rect.y());
343 case PE_FrameTabBarBase:
344 if (
const QStyleOptionTabBarBase *tbb
345 = qstyleoption_cast<
const QStyleOptionTabBarBase *>(opt)) {
346 QPainterStateGuard psg(p);
347 switch (tbb->shape) {
348 case QTabBar::RoundedNorth:
349 case QTabBar::TriangularNorth:
350 p->setPen(QPen(tbb->palette.light(), 0));
351 p->drawLine(tbb->rect.topLeft(), tbb->rect.topRight());
353 case QTabBar::RoundedWest:
354 case QTabBar::TriangularWest:
355 p->setPen(QPen(tbb->palette.light(), 0));
356 p->drawLine(tbb->rect.topLeft(), tbb->rect.bottomLeft());
358 case QTabBar::RoundedSouth:
359 case QTabBar::TriangularSouth:
360 p->setPen(QPen(tbb->palette.shadow(), 0));
361 p->drawLine(tbb->rect.left(), tbb->rect.bottom(),
362 tbb->rect.right(), tbb->rect.bottom());
363 p->setPen(QPen(tbb->palette.dark(), 0));
364 p->drawLine(tbb->rect.left(), tbb->rect.bottom() - 1,
365 tbb->rect.right() - 1, tbb->rect.bottom() - 1);
367 case QTabBar::RoundedEast:
368 case QTabBar::TriangularEast:
369 p->setPen(QPen(tbb->palette.dark(), 0));
370 p->drawLine(tbb->rect.topRight(), tbb->rect.bottomRight());
375 case PE_IndicatorTabClose: {
376 if (d->tabBarcloseButtonIcon.isNull())
377 d->tabBarcloseButtonIcon = proxy()->standardIcon(QStyle::SP_TabCloseButton, opt, widget);
379 const int size = proxy()->pixelMetric(QStyle::PM_SmallIconSize, opt, widget);
380 QIcon::Mode mode = opt->state & State_Enabled ?
381 (opt->state & State_Raised ? QIcon::Active : QIcon::Normal)
383 if (!opt->state.testAnyFlags(State_Raised | State_Sunken | State_Selected))
384 mode = QIcon::Disabled;
386 QIcon::State state = opt->state & State_Sunken ? QIcon::On : QIcon::Off;
387 QPixmap pixmap = d->tabBarcloseButtonIcon.pixmap(QSize(size, size), QStyleHelper::getDpr(p), mode, state);
388 proxy()->drawItemPixmap(p, opt->rect, Qt::AlignCenter, pixmap);
394 case PE_FrameTabWidget:
396 qDrawWinPanel(p, opt->rect, opt->palette,
false,
nullptr);
398 case PE_FrameLineEdit:
399 proxy()->drawPrimitive(PE_Frame, opt, p, widget);
401#if QT_CONFIG(groupbox)
402 case PE_FrameGroupBox:
403 if (
const QStyleOptionFrame *frame = qstyleoption_cast<
const QStyleOptionFrame *>(opt)) {
404 if (frame->features & QStyleOptionFrame::Flat) {
405 QRect fr = frame->rect;
406 QPoint p1(fr.x(), fr.y() + 1);
407 QPoint p2(fr.x() + fr.width(), p1.y());
408 qDrawShadeLine(p, p1, p2, frame->palette,
true,
409 frame->lineWidth, frame->midLineWidth);
411 qDrawShadeRect(p, frame->rect.x(), frame->rect.y(), frame->rect.width(),
412 frame->rect.height(), frame->palette,
true,
413 frame->lineWidth, frame->midLineWidth);
418#if QT_CONFIG(dockwidget)
419 case PE_FrameDockWidget:
420 if (
const QStyleOptionFrame *frame = qstyleoption_cast<
const QStyleOptionFrame *>(opt)) {
421 int lw = frame->lineWidth;
423 lw = proxy()->pixelMetric(PM_DockWidgetFrameWidth, opt, widget);
425 qDrawShadePanel(p, frame->rect, frame->palette,
false, lw);
429#if QT_CONFIG(toolbar)
430 case PE_IndicatorToolBarHandle: {
431 QPainterStateGuard psg(p);
432 p->translate(opt->rect.x(), opt->rect.y());
433 if (opt->state & State_Horizontal) {
434 int x = opt->rect.width() / 3;
435 if (opt->direction == Qt::RightToLeft)
437 if (opt->rect.height() > 4) {
438 qDrawShadePanel(p, x, 2, 3, opt->rect.height() - 4,
439 opt->palette,
false, 1,
nullptr);
440 qDrawShadePanel(p, x+3, 2, 3, opt->rect.height() - 4,
441 opt->palette,
false, 1,
nullptr);
444 if (opt->rect.width() > 4) {
445 int y = opt->rect.height() / 3;
446 qDrawShadePanel(p, 2, y, opt->rect.width() - 4, 3,
447 opt->palette,
false, 1,
nullptr);
448 qDrawShadePanel(p, 2, y+3, opt->rect.width() - 4, 3,
449 opt->palette,
false, 1,
nullptr);
454 case PE_IndicatorToolBarSeparator:
457 if (opt->state & State_Horizontal) {
458 p1 = QPoint(opt->rect.width()/2, 0);
459 p2 = QPoint(p1.x(), opt->rect.height());
461 p1 = QPoint(0, opt->rect.height()/2);
462 p2 = QPoint(opt->rect.width(), p1.y());
464 qDrawShadeLine(p, p1, p2, opt->palette, 1, 1, 0);
468#if QT_CONFIG(spinbox)
469 case PE_IndicatorSpinPlus:
470 case PE_IndicatorSpinMinus: {
472 int fw = proxy()->pixelMetric(PM_DefaultFrameWidth, opt, widget);
473 QRect br = r.adjusted(fw, fw, -fw, -fw);
478 QPainterStateGuard psg(p);
479 const qreal devicePixelRatio = QStyleHelper::getDpr(p);
480 if (!qFuzzyCompare(devicePixelRatio, qreal(1))) {
481 const qreal inverseScale = qreal(1) / devicePixelRatio;
482 p->scale(inverseScale, inverseScale);
483 x = qRound(devicePixelRatio * x);
484 y = qRound(devicePixelRatio * y);
485 w = qRound(devicePixelRatio * w);
486 h = qRound(devicePixelRatio * h);
487 p->translate(0.5, 0.5);
489 int len = std::min(w, h);
492 int step = (len + 4) / 5;
495 const int step2 = step / 2;
496 QPoint center(x + w / 2, y + h / 2);
497 if (opt->state & State_Sunken) {
498 center += QPoint(proxy()->pixelMetric(PM_ButtonShiftHorizontal, opt, widget),
499 proxy()->pixelMetric(PM_ButtonShiftVertical, opt, widget));
501 p->translate(center);
502 p->fillRect(-len / 2, -step2, len, step, opt->palette.buttonText());
503 if (pe == PE_IndicatorSpinPlus)
504 p->fillRect(-step2, -len / 2, step, len, opt->palette.buttonText());
506 case PE_IndicatorSpinUp:
507 case PE_IndicatorSpinDown: {
509 int fw = proxy()->pixelMetric(PM_DefaultFrameWidth, opt, widget);
515 QPainterStateGuard psg(p);
516 const qreal devicePixelRatio = QStyleHelper::getDpr(p);
517 if (!qFuzzyCompare(devicePixelRatio, qreal(1))) {
518 const qreal inverseScale = qreal(1) / devicePixelRatio;
519 p->scale(inverseScale, inverseScale);
520 x = qRound(devicePixelRatio * x);
521 y = qRound(devicePixelRatio * y);
522 w = qRound(devicePixelRatio * w);
523 h = qRound(devicePixelRatio * h);
524 p->translate(0.5, 0.5);
534 int sx = x + w / 2 - sw / 2;
535 int sy = y + h / 2 - sh / 2;
537 if (pe == PE_IndicatorSpinUp && fw)
542 if (opt->state & State_Sunken) {
543 bsx = proxy()->pixelMetric(PM_ButtonShiftHorizontal, opt, widget);
544 bsy = proxy()->pixelMetric(PM_ButtonShiftVertical, opt, widget);
546 p->translate(sx + bsx, sy + bsy);
547 p->setPen(opt->palette.buttonText().color());
548 p->setBrush(opt->palette.buttonText());
549 if (pe == PE_IndicatorSpinDown) {
550 const QPoint points[] = { QPoint(0, 1), QPoint(sw-1, 1), QPoint(sh-2, sh-1) };
551 p->drawPolygon(points,
sizeof points /
sizeof *points);
553 const QPoint points[] = { QPoint(0, sh-1), QPoint(sw-1, sh-1), QPoint(sh-2, 1) };
554 p->drawPolygon(points,
sizeof points /
sizeof *points);
558 case PE_PanelTipLabel: {
559 const QBrush brush(opt->palette.toolTipBase());
560 qDrawPlainRect(p, opt->rect, opt->palette.toolTipText().color(), 1, &brush);
564 case PE_IndicatorTabTear:
565 if (
const QStyleOptionTab *tab = qstyleoption_cast<
const QStyleOptionTab *>(opt)) {
566 bool rtl = tab->direction == Qt::RightToLeft;
567 const bool horizontal = tab->rect.height() > tab->rect.width();
568 const bool isSelected = tab->state.testFlag(State_Selected);
569 const int margin = 4;
573 QRect rect = tab->rect.adjusted(rtl ? margin : 0, 0, rtl ? 1 : -margin, 0);
574 rect.setTop(rect.top() + (isSelected ? 1 : 3));
575 rect.setBottom(rect.bottom() - (isSelected ? 0 : 2));
577 path.moveTo(QPoint(rtl ? rect.right() : rect.left(), rect.top()));
579 for (
int jags = 1; jags <= count; ++jags, rtl = !rtl)
580 path.lineTo(QPoint(rtl ? rect.left() : rect.right(), rect.top() + jags * rect.height()/count));
582 QRect rect = tab->rect.adjusted(0, 0, 0, -margin);
583 rect.setLeft(rect.left() + (isSelected ? 1 : 3));
584 rect.setRight(rect.right() - (isSelected ? 0 : 2));
586 path.moveTo(QPoint(rect.left(), rect.top()));
588 for (
int jags = 1; jags <= count; ++jags, rtl = !rtl)
589 path.lineTo(QPoint(rect.left() + jags * rect.width()/count, rtl ? rect.top() : rect.bottom()));
592 p->setPen(QPen(tab->palette.dark(), qreal(.8)));
593 p->setBrush(tab->palette.window());
594 p->setRenderHint(QPainter::Antialiasing);
599#if QT_CONFIG(lineedit)
600 case PE_PanelLineEdit:
601 if (
const QStyleOptionFrame *panel = qstyleoption_cast<
const QStyleOptionFrame *>(opt)) {
602 p->fillRect(panel->rect.adjusted(panel->lineWidth, panel->lineWidth, -panel->lineWidth, -panel->lineWidth),
603 panel->palette.brush(QPalette::Base));
605 if (panel->lineWidth > 0)
606 proxy()->drawPrimitive(PE_FrameLineEdit, panel, p, widget);
610#if QT_CONFIG(columnview)
611 case PE_IndicatorColumnViewArrow: {
612 if (
const QStyleOptionViewItem *viewOpt = qstyleoption_cast<
const QStyleOptionViewItem *>(opt)) {
613 bool reverse = (viewOpt->direction == Qt::RightToLeft);
614 QPainterStateGuard psg(p);
616 int x = viewOpt->rect.x() + 1;
617 int offset = (viewOpt->rect.height() / 3);
618 int height = (viewOpt->rect.height()) - offset * 2;
621 int x2 = x + height - 1;
623 x = viewOpt->rect.x() + viewOpt->rect.width() - 1;
626 path.moveTo(x, viewOpt->rect.y() + offset);
627 path.lineTo(x, viewOpt->rect.y() + offset + height);
628 path.lineTo(x2, viewOpt->rect.y() + offset+height/2);
630 if (viewOpt->state & QStyle::State_Selected ) {
631 if (viewOpt->showDecorationSelected) {
632 QColor color = viewOpt->palette.color(QPalette::Active, QPalette::HighlightedText);
636 QColor color = viewOpt->palette.color(QPalette::Active, QPalette::WindowText);
642 QColor color = viewOpt->palette.color(QPalette::Active, QPalette::Mid);
649 if (!(viewOpt->state & QStyle::State_Selected)) {
651 lines.moveTo(x, viewOpt->rect.y() + offset);
652 lines.lineTo(x, viewOpt->rect.y() + offset + height);
653 lines.moveTo(x, viewOpt->rect.y() + offset);
654 lines.lineTo(x2, viewOpt->rect.y() + offset+height/2);
655 QColor color = viewOpt->palette.color(QPalette::Active, QPalette::Dark);
662 case PE_IndicatorItemViewItemDrop: {
663 QRect rect = opt->rect;
664 if (opt->rect.height() == 0)
665 p->drawLine(rect.topLeft(), rect.topRight());
669#if QT_CONFIG(itemviews)
670 case PE_PanelItemViewRow:
671 if (
const QStyleOptionViewItem *vopt = qstyleoption_cast<
const QStyleOptionViewItem *>(opt)) {
672 QPalette::ColorGroup cg = (widget ? widget->isEnabled() : (vopt->state & QStyle::State_Enabled))
673 ? QPalette::Normal : QPalette::Disabled;
674 if (cg == QPalette::Normal && !(vopt->state & QStyle::State_Active))
675 cg = QPalette::Inactive;
677 if ((vopt->state & QStyle::State_Selected) && vopt->showDecorationSelected)
678 p->fillRect(vopt->rect, vopt->palette.brush(cg, QPalette::Highlight));
679 else if (vopt->features & QStyleOptionViewItem::Alternate)
680 p->fillRect(vopt->rect, vopt->palette.brush(cg, QPalette::AlternateBase));
683 case PE_PanelItemViewItem:
684 if (
const QStyleOptionViewItem *vopt = qstyleoption_cast<
const QStyleOptionViewItem *>(opt)) {
685 QPalette::ColorGroup cg = (widget ? widget->isEnabled() : (vopt->state & QStyle::State_Enabled))
686 ? QPalette::Normal : QPalette::Disabled;
687 if (cg == QPalette::Normal && !(vopt->state & QStyle::State_Active))
688 cg = QPalette::Inactive;
690 if (vopt->showDecorationSelected && (vopt->state & QStyle::State_Selected)) {
691 p->fillRect(vopt->rect, vopt->palette.brush(cg, QPalette::Highlight));
693 if (vopt->backgroundBrush.style() != Qt::NoBrush) {
694 QPainterStateGuard psg(p);
695 p->setBrushOrigin(vopt->rect.topLeft());
696 p->fillRect(vopt->rect, vopt->backgroundBrush);
699 if (vopt->state & QStyle::State_Selected) {
700 QRect textRect = subElementRect(QStyle::SE_ItemViewItemText, opt, widget);
701 p->fillRect(textRect, vopt->palette.brush(cg, QPalette::Highlight));
707 case PE_PanelScrollAreaCorner: {
708 const QBrush brush(opt->palette.brush(QPalette::Window));
709 p->fillRect(opt->rect, brush);
711 case PE_IndicatorArrowUp:
712 case PE_IndicatorArrowDown:
713 case PE_IndicatorArrowRight:
714 case PE_IndicatorArrowLeft:
716 const QRect &r = opt->rect;
717 if (r.width() <= 1 || r.height() <= 1)
719 int size = qMin(r.height(), r.width());
721 const qreal dpr = QStyleHelper::getDpr(p);
722 const QString pixmapName = QStyleHelper::uniqueName(
"$qt_ia-"_L1
723 % QLatin1StringView(metaObject()->className())
724 % HexString<uint>(pe),
725 opt, QSize(size, size), dpr);
726 if (!QPixmapCache::find(pixmapName, &pixmap)) {
728 const int border = 1 * dpr;
729 const int sizeDpr = size * dpr;
730 int width = sizeDpr - 2 * border - 1;
731 int height = width / 2;
732 const int add = ((width & 1) == 1);
733 if (pe == PE_IndicatorArrowRight || pe == PE_IndicatorArrowLeft)
734 std::swap(width, height);
735 pixmap = styleCachePixmap(QSize(sizeDpr, sizeDpr), 1);
737 std::array<QPointF, 4> poly;
739 case PE_IndicatorArrowUp:
740 poly = {QPointF(0, height), QPointF(width, height),
741 QPointF(width / 2 + add, 0), QPointF(width / 2, 0)};
743 case PE_IndicatorArrowDown:
744 poly = {QPointF(0, 0), QPointF(width, 0),
745 QPointF(width / 2 + add, height), QPointF(width / 2, height)};
747 case PE_IndicatorArrowRight:
748 poly = {QPointF(0, 0), QPointF(0, height),
749 QPointF(width, height / 2 + add), QPointF(width, height / 2)};
751 case PE_IndicatorArrowLeft:
752 poly = {QPointF(width, 0), QPointF(width, height),
753 QPointF(0, height / 2 + add), QPointF(0, height / 2)};
759 QPainter imagePainter(&pixmap);
760 imagePainter.translate((sizeDpr - width) / 2, (sizeDpr - height) / 2);
761 if (opt->state & State_Sunken) {
762 const auto bsx = proxy()->pixelMetric(PM_ButtonShiftHorizontal, opt, widget);
763 const auto bsy = proxy()->pixelMetric(PM_ButtonShiftVertical, opt, widget);
764 imagePainter.translate(bsx, bsy);
766 imagePainter.setPen(opt->palette.buttonText().color());
767 imagePainter.setBrush(opt->palette.buttonText());
769 if (!(opt->state & State_Enabled)) {
770 const int ofs = qRound(1 * dpr);
771 imagePainter.translate(ofs, ofs);
772 imagePainter.setBrush(opt->palette.light());
773 imagePainter.setPen(opt->palette.light().color());
774 imagePainter.drawPolygon(poly.data(),
int(poly.size()));
775 imagePainter.drawPoints(poly.data(),
int(poly.size()));
776 imagePainter.translate(-ofs, -ofs);
777 imagePainter.setBrush(opt->palette.mid());
778 imagePainter.setPen(opt->palette.mid().color());
780 imagePainter.drawPolygon(poly.data(),
int(poly.size()));
782 imagePainter.drawPoints(poly.data(),
int(poly.size()));
784 pixmap.setDevicePixelRatio(dpr);
785 QPixmapCache::insert(pixmapName, pixmap);
787 int xOffset = r.x() + (r.width() - size)/2;
788 int yOffset = r.y() + (r.height() - size)/2;
789 p->drawPixmap(xOffset, yOffset, pixmap);
1292void QCommonStyle::drawControl(ControlElement element,
const QStyleOption *opt,
1293 QPainter *p,
const QWidget *widget)
const
1295 Q_D(
const QCommonStyle);
1299 if (
const QStyleOptionButton *btn = qstyleoption_cast<
const QStyleOptionButton *>(opt)) {
1300 proxy()->drawControl(CE_PushButtonBevel, btn, p, widget);
1301 QStyleOptionButton subopt = *btn;
1302 subopt.rect = subElementRect(SE_PushButtonContents, btn, widget);
1303 proxy()->drawControl(CE_PushButtonLabel, &subopt, p, widget);
1304 if (btn->state & State_HasFocus) {
1305 QStyleOptionFocusRect fropt;
1306 fropt.QStyleOption::operator=(*btn);
1307 fropt.rect = subElementRect(SE_PushButtonFocusRect, btn, widget);
1308 proxy()->drawPrimitive(PE_FrameFocusRect, &fropt, p, widget);
1312 case CE_PushButtonBevel:
1313 if (
const QStyleOptionButton *btn = qstyleoption_cast<
const QStyleOptionButton *>(opt)) {
1314 QRect br = btn->rect;
1315 int dbi = proxy()->pixelMetric(PM_ButtonDefaultIndicator, btn, widget);
1316 if (btn->features & QStyleOptionButton::DefaultButton)
1317 proxy()->drawPrimitive(PE_FrameDefaultButton, opt, p, widget);
1318 if (btn->features & QStyleOptionButton::AutoDefaultButton)
1319 br.setCoords(br.left() + dbi, br.top() + dbi, br.right() - dbi, br.bottom() - dbi);
1320 if (!(btn->features & (QStyleOptionButton::Flat | QStyleOptionButton::CommandLinkButton))
1321 || btn->state & (State_Sunken | State_On)
1322 || (btn->features & QStyleOptionButton::CommandLinkButton && btn->state & State_MouseOver)) {
1323 QStyleOptionButton tmpBtn = *btn;
1325 proxy()->drawPrimitive(PE_PanelButtonCommand, &tmpBtn, p, widget);
1327 if (btn->features & QStyleOptionButton::HasMenu) {
1328 int mbi = proxy()->pixelMetric(PM_MenuButtonIndicator, btn, widget);
1329 QRect ir = btn->rect;
1330 QStyleOptionButton newBtn = *btn;
1331 newBtn.rect = QRect(ir.right() - mbi - 2, ir.height()/2 - mbi/2 + 3, mbi - 6, mbi - 6);
1332 newBtn.rect = visualRect(btn->direction, br, newBtn.rect);
1333 proxy()->drawPrimitive(PE_IndicatorArrowDown, &newBtn, p, widget);
1337 case CE_PushButtonLabel:
1338 if (
const QStyleOptionButton *button = qstyleoption_cast<
const QStyleOptionButton *>(opt)) {
1339 QRect textRect = button->rect;
1340 int tf = Qt::AlignVCenter | Qt::TextShowMnemonic;
1341 if (!proxy()->styleHint(SH_UnderlineShortcut, button, widget))
1342 tf |= Qt::TextHideMnemonic;
1344 if (button->features & QStyleOptionButton::HasMenu) {
1345 int indicatorSize = proxy()->pixelMetric(PM_MenuButtonIndicator, button, widget);
1346 if (button->direction == Qt::LeftToRight)
1347 textRect = textRect.adjusted(0, 0, -indicatorSize, 0);
1349 textRect = textRect.adjusted(indicatorSize, 0, 0, 0);
1352 if (!button->icon.isNull()) {
1354 QIcon::Mode mode = button->state & State_Enabled ? QIcon::Normal : QIcon::Disabled;
1355 if (mode == QIcon::Normal && button->state & State_HasFocus)
1356 mode = QIcon::Active;
1357 QIcon::State state = QIcon::Off;
1358 if (button->state & State_On)
1361 QPixmap pixmap = button->icon.pixmap(button->iconSize, QStyleHelper::getDpr(p), mode, state);
1362 int pixmapWidth = pixmap.width() / pixmap.devicePixelRatio();
1363 int pixmapHeight = pixmap.height() / pixmap.devicePixelRatio();
1364 int labelWidth = pixmapWidth;
1365 int labelHeight = pixmapHeight;
1366 int iconSpacing = 4;
1367 if (!button->text.isEmpty()) {
1368 int textWidth = button->fontMetrics.boundingRect(opt->rect, tf, button->text).width();
1369 labelWidth += (textWidth + iconSpacing);
1372 QRect iconRect = QRect(textRect.x() + (textRect.width() - labelWidth) / 2,
1373 textRect.y() + (textRect.height() - labelHeight) / 2,
1374 pixmapWidth, pixmapHeight);
1376 iconRect = visualRect(button->direction, textRect, iconRect);
1378 if (button->direction == Qt::RightToLeft)
1379 textRect.setRight(iconRect.left() - iconSpacing / 2);
1381 textRect.setLeft(iconRect.left() + iconRect.width() + iconSpacing / 2);
1384 if (p->layoutDirection() == button->direction)
1385 tf |= Qt::AlignLeft;
1387 tf |= Qt::AlignRight;
1389 if (button->state & (State_On | State_Sunken))
1390 iconRect.translate(proxy()->pixelMetric(PM_ButtonShiftHorizontal, opt, widget),
1391 proxy()->pixelMetric(PM_ButtonShiftVertical, opt, widget));
1392 p->drawPixmap(iconRect, pixmap);
1394 tf |= Qt::AlignHCenter;
1396 if (button->state & (State_On | State_Sunken))
1397 textRect.translate(proxy()->pixelMetric(PM_ButtonShiftHorizontal, opt, widget),
1398 proxy()->pixelMetric(PM_ButtonShiftVertical, opt, widget));
1400 proxy()->drawItemText(p, textRect, tf, button->palette, (button->state & State_Enabled),
1401 button->text, QPalette::ButtonText);
1404 case CE_RadioButton:
1406 if (
const QStyleOptionButton *btn = qstyleoption_cast<
const QStyleOptionButton *>(opt)) {
1407 bool isRadio = (element == CE_RadioButton);
1408 QStyleOptionButton subopt = *btn;
1409 subopt.rect = subElementRect(isRadio ? SE_RadioButtonIndicator
1410 : SE_CheckBoxIndicator, btn, widget);
1411 proxy()->drawPrimitive(isRadio ? PE_IndicatorRadioButton : PE_IndicatorCheckBox,
1412 &subopt, p, widget);
1413 subopt.rect = subElementRect(isRadio ? SE_RadioButtonContents
1414 : SE_CheckBoxContents, btn, widget);
1415 proxy()->drawControl(isRadio ? CE_RadioButtonLabel : CE_CheckBoxLabel, &subopt, p, widget);
1416 if (btn->state & State_HasFocus) {
1417 QStyleOptionFocusRect fropt;
1418 fropt.QStyleOption::operator=(*btn);
1419 fropt.rect = subElementRect(isRadio ? SE_RadioButtonFocusRect
1420 : SE_CheckBoxFocusRect, btn, widget);
1421 proxy()->drawPrimitive(PE_FrameFocusRect, &fropt, p, widget);
1425 case CE_RadioButtonLabel:
1426 case CE_CheckBoxLabel:
1427 if (
const QStyleOptionButton *btn = qstyleoption_cast<
const QStyleOptionButton *>(opt)) {
1428 int alignment = visualAlignment(btn->direction, Qt::AlignLeft | Qt::AlignVCenter);
1430 if (!proxy()->styleHint(SH_UnderlineShortcut, btn, widget))
1431 alignment |= Qt::TextHideMnemonic;
1432 QRect textRect = btn->rect;
1433 if (!btn->icon.isNull()) {
1434 const auto pix = btn->icon.pixmap(btn->iconSize, QStyleHelper::getDpr(p),
1435 btn->state & State_Enabled ? QIcon::Normal : QIcon::Disabled);
1436 proxy()->drawItemPixmap(p, btn->rect, alignment, pix);
1437 if (btn->direction == Qt::RightToLeft)
1438 textRect.setRight(textRect.right() - btn->iconSize.width() - 4);
1440 textRect.setLeft(textRect.left() + btn->iconSize.width() + 4);
1442 if (!btn->text.isEmpty()){
1443 proxy()->drawItemText(p, textRect, alignment | Qt::TextShowMnemonic,
1444 btn->palette, btn->state & State_Enabled, btn->text, QPalette::WindowText);
1449 case CE_MenuScroller: {
1450 QStyleOption arrowOpt = *opt;
1451 arrowOpt.state |= State_Enabled;
1452 proxy()->drawPrimitive(((opt->state & State_DownArrow) ? PE_IndicatorArrowDown : PE_IndicatorArrowUp),
1453 &arrowOpt, p, widget);
1455 case CE_MenuTearoff:
1456 if (opt->state & State_Selected)
1457 p->fillRect(opt->rect, opt->palette.brush(QPalette::Highlight));
1459 p->fillRect(opt->rect, opt->palette.brush(QPalette::Button));
1460 p->setPen(QPen(opt->palette.dark().color(), 1, Qt::DashLine));
1461 p->drawLine(opt->rect.x() + 2, opt->rect.y() + opt->rect.height() / 2 - 1,
1462 opt->rect.x() + opt->rect.width() - 4,
1463 opt->rect.y() + opt->rect.height() / 2 - 1);
1464 p->setPen(QPen(opt->palette.light().color(), 1, Qt::DashLine));
1465 p->drawLine(opt->rect.x() + 2, opt->rect.y() + opt->rect.height() / 2,
1466 opt->rect.x() + opt->rect.width() - 4, opt->rect.y() + opt->rect.height() / 2);
1469#if QT_CONFIG(menubar)
1470 case CE_MenuBarItem:
1471 if (
const QStyleOptionMenuItem *mbi = qstyleoption_cast<
const QStyleOptionMenuItem *>(opt)) {
1472 int alignment = Qt::AlignCenter | Qt::TextShowMnemonic | Qt::TextDontClip
1473 | Qt::TextSingleLine;
1474 if (!proxy()->styleHint(SH_UnderlineShortcut, mbi, widget))
1475 alignment |= Qt::TextHideMnemonic;
1476 int iconExtent = proxy()->pixelMetric(PM_SmallIconSize, opt, widget);
1477 QPixmap pix = mbi->icon.pixmap(QSize(iconExtent, iconExtent), QStyleHelper::getDpr(p), (mbi->state & State_Enabled) ? QIcon::Normal : QIcon::Disabled);
1479 proxy()->drawItemPixmap(p,mbi->rect, alignment, pix);
1481 proxy()->drawItemText(p, mbi->rect, alignment, mbi->palette, mbi->state & State_Enabled,
1482 mbi->text, QPalette::ButtonText);
1485 case CE_MenuBarEmptyArea:
1486 if (widget && !widget->testAttribute(Qt::WA_NoSystemBackground))
1487 p->eraseRect(opt->rect);
1490#if QT_CONFIG(progressbar)
1491 case CE_ProgressBar:
1492 if (
const QStyleOptionProgressBar *pb
1493 = qstyleoption_cast<
const QStyleOptionProgressBar *>(opt)) {
1494 QStyleOptionProgressBar subopt = *pb;
1495 subopt.rect = subElementRect(SE_ProgressBarGroove, pb, widget);
1496 proxy()->drawControl(CE_ProgressBarGroove, &subopt, p, widget);
1497 subopt.rect = subElementRect(SE_ProgressBarContents, pb, widget);
1498 proxy()->drawControl(CE_ProgressBarContents, &subopt, p, widget);
1499 if (pb->textVisible) {
1500 subopt.rect = subElementRect(SE_ProgressBarLabel, pb, widget);
1501 proxy()->drawControl(CE_ProgressBarLabel, &subopt, p, widget);
1505 case CE_ProgressBarGroove:
1506 if (opt->rect.isValid())
1507 qDrawShadePanel(p, opt->rect, opt->palette,
true, 1,
1508 &opt->palette.brush(QPalette::Window));
1510 case CE_ProgressBarLabel:
1511 if (
const QStyleOptionProgressBar *pb = qstyleoption_cast<
const QStyleOptionProgressBar *>(opt)) {
1512 const bool vertical = !(pb->state & QStyle::State_Horizontal);
1514 QPalette::ColorRole textRole = QPalette::NoRole;
1515 if ((pb->textAlignment & Qt::AlignCenter) && pb->textVisible
1516 && ((qint64(pb->progress) - qint64(pb->minimum)) * 2 >= (qint64(pb->maximum) - qint64(pb->minimum)))) {
1517 textRole = QPalette::HighlightedText;
1519 QRect shadowRect(pb->rect);
1520 shadowRect.translate(1,1);
1521 QColor shadowColor = (pb->palette.color(textRole).value() <= 128)
1522 ? QColor(255,255,255,160) : QColor(0,0,0,160);
1523 QPalette shadowPalette = pb->palette;
1524 shadowPalette.setColor(textRole, shadowColor);
1525 proxy()->drawItemText(p, shadowRect, Qt::AlignCenter | Qt::TextSingleLine, shadowPalette,
1526 pb->state & State_Enabled, pb->text, textRole);
1528 proxy()->drawItemText(p, pb->rect, Qt::AlignCenter | Qt::TextSingleLine, pb->palette,
1529 pb->state & State_Enabled, pb->text, textRole);
1533 case CE_ProgressBarContents:
1534 if (
const QStyleOptionProgressBar *pb = qstyleoption_cast<
const QStyleOptionProgressBar *>(opt)) {
1536 QRect rect = pb->rect;
1537 const bool vertical = !(pb->state & QStyle::State_Horizontal);
1538 const bool inverted = pb->invertedAppearance;
1539 qint64 minimum = qint64(pb->minimum);
1540 qint64 maximum = qint64(pb->maximum);
1541 qint64 progress = qint64(pb->progress);
1546 rect = QRect(rect.y(), rect.x(), rect.height(), rect.width());
1548 m.translate(0, -(rect.height() + rect.y()*2));
1551 QPalette pal2 = pb->palette;
1553 if (pal2.highlight() == pal2.window())
1554 pal2.setColor(QPalette::Highlight, pb->palette.color(QPalette::Active,
1555 QPalette::Highlight));
1556 bool reverse = ((!vertical && (pb->direction == Qt::RightToLeft)) || vertical);
1559 int w = rect.width();
1560 if (pb->minimum == 0 && pb->maximum == 0) {
1562 int x = (progress - minimum) % (w * 2);
1565 x = reverse ? rect.right() - x : x + rect.x();
1566 p->setPen(QPen(pal2.highlight().color(), 4));
1567 p->drawLine(x, rect.y(), x, rect.height());
1569 const int unit_width = proxy()->pixelMetric(PM_ProgressBarChunkWidth, pb, widget);
1575 u = ((rect.width() + unit_width) / unit_width);
1578 qint64 p_v = progress - minimum;
1579 qint64 t_s = (maximum - minimum) ? (maximum - minimum) : qint64(1);
1581 if (u > 0 && p_v >= INT_MAX / u && t_s >= u) {
1589 tnu = nu = p_v * u / t_s;
1591 if (nu * unit_width > w)
1599 int x0 = reverse ? rect.right() - ((unit_width > 1) ? unit_width : 0)
1602 QStyleOptionProgressBar pbBits = *pb;
1604 pbBits.palette = pal2;
1605 int myY = pbBits.rect.y();
1606 int myHeight = pbBits.rect.height();
1607 pbBits.state &= QStyle::State_Horizontal;
1608 for (
int i = 0; i < nu; ++i) {
1609 pbBits.rect.setRect(x0 + x, myY, unit_width, myHeight);
1610 pbBits.rect = m.mapRect(QRectF(pbBits.rect)).toRect();
1611 proxy()->drawPrimitive(PE_IndicatorProgressChunk, &pbBits, p, widget);
1612 x += reverse ? -unit_width : unit_width;
1618 int pixels_left = w - (nu * unit_width);
1619 int offset = reverse ? x0 + x + unit_width-pixels_left : x0 + x;
1620 pbBits.rect.setRect(offset, myY, pixels_left, myHeight);
1621 pbBits.rect = m.mapRect(QRectF(pbBits.rect)).toRect();
1622 proxy()->drawPrimitive(PE_IndicatorProgressChunk, &pbBits, p, widget);
1628 case CE_HeaderLabel:
1629 if (
const QStyleOptionHeader *header = qstyleoption_cast<
const QStyleOptionHeader *>(opt)) {
1630 QRect rect = header->rect;
1631 if (!header->icon.isNull()) {
1632 const int iconExtent = proxy()->pixelMetric(PM_SmallIconSize, opt, widget);
1633 const QRect aligned = alignedRect(header->direction, header->iconAlignment,
1634 QSize(iconExtent, iconExtent), rect);
1635 header->icon.paint(p, aligned, Qt::AlignCenter,
1636 header->state.testFlag(State_Enabled) ? QIcon::Normal
1639 const int margin = proxy()->pixelMetric(QStyle::PM_HeaderMargin, opt, widget);
1640 if (header->direction == Qt::LeftToRight)
1641 rect.setLeft(rect.left() + iconExtent + margin);
1643 rect.setRight(rect.right() - iconExtent - margin);
1645 QFontMetrics fm(header->fontMetrics);
1646 if (header->state & QStyle::State_On) {
1647 QFont fnt = p->font();
1649 if (!(fnt.resolveMask() & QFont::WeightResolved)) {
1652 fm = QFontMetrics((p->font()));
1655 QString text = header->text;
1656 if (
const QStyleOptionHeaderV2 *headerV2 = qstyleoption_cast<
const QStyleOptionHeaderV2 *>(header)) {
1657 if (headerV2->textElideMode != Qt::ElideNone)
1658 text = fm.elidedText(header->text, headerV2->textElideMode, rect.width());
1660 proxy()->drawItemText(p, rect, header->textAlignment, header->palette,
1661 header->state.testFlag(State_Enabled), text, QPalette::ButtonText);
1664#if QT_CONFIG(toolbutton)
1665 case CE_ToolButtonLabel:
1666 if (
const QStyleOptionToolButton *toolbutton
1667 = qstyleoption_cast<
const QStyleOptionToolButton *>(opt)) {
1668 QRect rect = toolbutton->rect;
1671 if (toolbutton->state & (State_Sunken | State_On)) {
1672 shiftX = proxy()->pixelMetric(PM_ButtonShiftHorizontal, toolbutton, widget);
1673 shiftY = proxy()->pixelMetric(PM_ButtonShiftVertical, toolbutton, widget);
1676 bool hasArrow = toolbutton->features & QStyleOptionToolButton::Arrow;
1677 if (((!hasArrow && toolbutton->icon.isNull()) && !toolbutton->text.isEmpty())
1678 || toolbutton->toolButtonStyle == Qt::ToolButtonTextOnly) {
1679 int alignment = Qt::AlignCenter | Qt::TextShowMnemonic;
1680 if (!proxy()->styleHint(SH_UnderlineShortcut, opt, widget))
1681 alignment |= Qt::TextHideMnemonic;
1682 rect.translate(shiftX, shiftY);
1683 p->setFont(toolbutton->font);
1684 const QString text = d->toolButtonElideText(toolbutton, rect, alignment);
1685 proxy()->drawItemText(p, rect, alignment, toolbutton->palette,
1686 opt->state & State_Enabled, text,
1687 QPalette::ButtonText);
1690 QSize pmSize = toolbutton->iconSize;
1691 if (!toolbutton->icon.isNull()) {
1692 QIcon::State state = toolbutton->state & State_On ? QIcon::On : QIcon::Off;
1694 if (!(toolbutton->state & State_Enabled))
1695 mode = QIcon::Disabled;
1696 else if ((opt->state & State_MouseOver) && (opt->state & State_AutoRaise))
1697 mode = QIcon::Active;
1699 mode = QIcon::Normal;
1700 pm = toolbutton->icon.pixmap(toolbutton->rect.size().boundedTo(toolbutton->iconSize), QStyleHelper::getDpr(p),
1702 pmSize = pm.size() / pm.devicePixelRatio();
1705 if (toolbutton->toolButtonStyle != Qt::ToolButtonIconOnly) {
1706 p->setFont(toolbutton->font);
1709 int alignment = Qt::TextShowMnemonic;
1710 if (!proxy()->styleHint(SH_UnderlineShortcut, opt, widget))
1711 alignment |= Qt::TextHideMnemonic;
1713 if (toolbutton->toolButtonStyle == Qt::ToolButtonTextUnderIcon) {
1714 pr.setHeight(pmSize.height() + 4);
1715 tr.adjust(0, pr.height() - 1, 0, -1);
1716 pr.translate(shiftX, shiftY);
1718 proxy()->drawItemPixmap(p, pr, Qt::AlignCenter, pm);
1720 drawArrow(proxy(), toolbutton, pr, p, widget);
1722 alignment |= Qt::AlignCenter;
1724 pr.setWidth(pmSize.width() + 4);
1725 tr.adjust(pr.width(), 0, 0, 0);
1726 pr.translate(shiftX, shiftY);
1728 proxy()->drawItemPixmap(p, QStyle::visualRect(opt->direction, rect, pr), Qt::AlignCenter, pm);
1730 drawArrow(proxy(), toolbutton, pr, p, widget);
1732 alignment |= Qt::AlignLeft | Qt::AlignVCenter;
1734 tr.translate(shiftX, shiftY);
1735 const QString text = d->toolButtonElideText(toolbutton, tr, alignment);
1736 proxy()->drawItemText(p, QStyle::visualRect(opt->direction, rect, tr), alignment, toolbutton->palette,
1737 toolbutton->state & State_Enabled, text,
1738 QPalette::ButtonText);
1740 rect.translate(shiftX, shiftY);
1742 drawArrow(proxy(), toolbutton, rect, p, widget);
1744 proxy()->drawItemPixmap(p, rect, Qt::AlignCenter, pm);
1751#if QT_CONFIG(toolbox)
1753 if (
const QStyleOptionToolBox *tb = qstyleoption_cast<
const QStyleOptionToolBox *>(opt)) {
1754 proxy()->drawControl(CE_ToolBoxTabShape, tb, p, widget);
1755 proxy()->drawControl(CE_ToolBoxTabLabel, tb, p, widget);
1758 case CE_ToolBoxTabShape:
1759 if (
const QStyleOptionToolBox *tb = qstyleoption_cast<
const QStyleOptionToolBox *>(opt)) {
1760 p->setPen(tb->palette.mid().color().darker(150));
1761 int d = 20 + tb->rect.height() - 3;
1762 if (tb->direction != Qt::RightToLeft) {
1763 const QPoint points[] = {
1764 QPoint(-1, tb->rect.height() + 1),
1766 QPoint(tb->rect.width() - d, 1),
1767 QPoint(tb->rect.width() - 20, tb->rect.height() - 2),
1768 QPoint(tb->rect.width() - 1, tb->rect.height() - 2),
1769 QPoint(tb->rect.width() - 1, tb->rect.height() + 1),
1770 QPoint(-1, tb->rect.height() + 1),
1772 p->drawPolygon(points,
sizeof points /
sizeof *points);
1774 const QPoint points[] = {
1775 QPoint(tb->rect.width(), tb->rect.height() + 1),
1776 QPoint(tb->rect.width(), 1),
1778 QPoint(20 - 1, tb->rect.height() - 2),
1779 QPoint(0, tb->rect.height() - 2),
1780 QPoint(0, tb->rect.height() + 1),
1781 QPoint(tb->rect.width(), tb->rect.height() + 1),
1783 p->drawPolygon(points,
sizeof points /
sizeof *points);
1785 p->setPen(tb->palette.light().color());
1786 if (tb->direction != Qt::RightToLeft) {
1787 p->drawLine(0, 2, tb->rect.width() - d, 2);
1788 p->drawLine(tb->rect.width() - d - 1, 2, tb->rect.width() - 21, tb->rect.height() - 1);
1789 p->drawLine(tb->rect.width() - 20, tb->rect.height() - 1,
1790 tb->rect.width(), tb->rect.height() - 1);
1792 p->drawLine(tb->rect.width() - 1, 2, d - 1, 2);
1793 p->drawLine(d, 2, 20, tb->rect.height() - 1);
1794 p->drawLine(19, tb->rect.height() - 1,
1795 -1, tb->rect.height() - 1);
1797 p->setBrush(Qt::NoBrush);
1801#if QT_CONFIG(tabbar)
1803 if (
const QStyleOptionTab *tab = qstyleoption_cast<
const QStyleOptionTab *>(opt)) {
1804 proxy()->drawControl(CE_TabBarTabShape, tab, p, widget);
1805 proxy()->drawControl(CE_TabBarTabLabel, tab, p, widget);
1808 case CE_TabBarTabShape:
1809 if (
const QStyleOptionTab *tab = qstyleoption_cast<
const QStyleOptionTab *>(opt)) {
1810 QPainterStateGuard psg(p);
1811 QRect rect(tab->rect);
1812 bool selected = tab->state & State_Selected;
1813 bool onlyOne = tab->position == QStyleOptionTab::OnlyOneTab;
1814 int tabOverlap = onlyOne ? 0 : proxy()->pixelMetric(PM_TabBarTabOverlap, opt, widget);
1817 switch (tab->shape) {
1818 case QTabBar::TriangularNorth:
1819 rect.adjust(0, 0, 0, -tabOverlap);
1821 rect.adjust(1, 1, -1, 0);
1823 case QTabBar::TriangularSouth:
1824 rect.adjust(0, tabOverlap, 0, 0);
1826 rect.adjust(1, 0, -1, -1);
1828 case QTabBar::TriangularEast:
1829 rect.adjust(tabOverlap, 0, 0, 0);
1831 rect.adjust(0, 1, -1, -1);
1833 case QTabBar::TriangularWest:
1834 rect.adjust(0, 0, -tabOverlap, 0);
1836 rect.adjust(1, 1, 0, -1);
1843 p->setPen(QPen(tab->palette.windowText(), 0));
1845 p->setBrush(tab->palette.base());
1847 if (widget && widget->parentWidget())
1848 p->setBrush(widget->parentWidget()->palette().window());
1850 p->setBrush(tab->palette.window());
1856 switch (tab->shape) {
1857 case QTabBar::TriangularNorth:
1858 case QTabBar::TriangularSouth: {
1859 a.setPoint(0, 0, -1);
1860 a.setPoint(1, 0, 0);
1861 y = rect.height() - 2;
1863 a.setPoint(2, x++, y - 1);
1865 a.setPoint(3, x++, y++);
1866 a.setPoint(4, x, y);
1869 int right = rect.width() - 1;
1870 for (i = 0; i < 5; ++i)
1871 a.setPoint(9 - i, right - a.point(i).x(), a.point(i).y());
1872 if (tab->shape == QTabBar::TriangularNorth)
1873 for (i = 0; i < 10; ++i)
1874 a.setPoint(i, a.point(i).x(), rect.height() - 1 - a.point(i).y());
1876 a.translate(rect.left(), rect.top());
1877 p->setRenderHint(QPainter::Antialiasing);
1878 p->translate(0, 0.5);
1884 case QTabBar::TriangularEast:
1885 case QTabBar::TriangularWest: {
1886 a.setPoint(0, -1, 0);
1887 a.setPoint(1, 0, 0);
1888 x = rect.width() - 2;
1890 a.setPoint(2, x - 1, y++);
1892 a.setPoint(3, x++, y++);
1893 a.setPoint(4, x, y);
1895 int bottom = rect.height() - 1;
1896 for (i = 0; i < 5; ++i)
1897 a.setPoint(9 - i, a.point(i).x(), bottom - a.point(i).y());
1898 if (tab->shape == QTabBar::TriangularWest)
1899 for (i = 0; i < 10; ++i)
1900 a.setPoint(i, rect.width() - 1 - a.point(i).x(), a.point(i).y());
1901 a.translate(rect.left(), rect.top());
1902 p->setRenderHint(QPainter::Antialiasing);
1903 p->translate(0.5, 0);
1913 case CE_ToolBoxTabLabel:
1914 if (
const QStyleOptionToolBox *tb = qstyleoption_cast<
const QStyleOptionToolBox *>(opt)) {
1915 bool enabled = tb->state & State_Enabled;
1916 bool selected = tb->state & State_Selected;
1917 int iconExtent = proxy()->pixelMetric(QStyle::PM_SmallIconSize, tb, widget);
1918 QPixmap pm = tb->icon.pixmap(QSize(iconExtent, iconExtent), QStyleHelper::getDpr(p),
1919 enabled ? QIcon::Normal : QIcon::Disabled);
1921 QRect cr = subElementRect(QStyle::SE_ToolBoxTabContents, tb, widget);
1926 tr.adjust(4, 0, -8, 0);
1928 int iw = pm.width() / pm.devicePixelRatio() + 4;
1929 ih = pm.height()/ pm.devicePixelRatio();
1930 ir = QRect(cr.left() + 4, cr.top(), iw + 2, ih);
1931 tr = QRect(ir.right(), cr.top(), cr.width() - ir.right() - 4, cr.height());
1934 if (selected && proxy()->styleHint(QStyle::SH_ToolBox_SelectedPageTitleBold, tb, widget)) {
1940 QString txt = tb->fontMetrics.elidedText(tb->text, Qt::ElideRight, tr.width());
1943 p->drawPixmap(ir.left(), (tb->rect.height() - ih) / 2, pm);
1945 int alignment = Qt::AlignLeft | Qt::AlignVCenter | Qt::TextShowMnemonic;
1946 if (!proxy()->styleHint(QStyle::SH_UnderlineShortcut, tb, widget))
1947 alignment |= Qt::TextHideMnemonic;
1948 proxy()->drawItemText(p, tr, alignment, tb->palette, enabled, txt, QPalette::ButtonText);
1950 if (!txt.isEmpty() && opt->state & State_HasFocus) {
1951 QStyleOptionFocusRect opt;
1953 opt.palette = tb->palette;
1954 opt.state = QStyle::State_None;
1955 proxy()->drawPrimitive(QStyle::PE_FrameFocusRect, &opt, p, widget);
1959 case CE_TabBarTabLabel:
1960 if (
const QStyleOptionTab *tab = qstyleoption_cast<
const QStyleOptionTab *>(opt)) {
1961 QRect tr = tab->rect;
1962 bool verticalTabs = tab->shape == QTabBar::RoundedEast
1963 || tab->shape == QTabBar::RoundedWest
1964 || tab->shape == QTabBar::TriangularEast
1965 || tab->shape == QTabBar::TriangularWest;
1967 int alignment = Qt::AlignCenter | Qt::TextShowMnemonic;
1968 if (!proxy()->styleHint(SH_UnderlineShortcut, opt, widget))
1969 alignment |= Qt::TextHideMnemonic;
1971 QPainterStateGuard psg(p, QPainterStateGuard::InitialState::NoSave);
1974 int newX, newY, newRot;
1975 if (tab->shape == QTabBar::RoundedEast || tab->shape == QTabBar::TriangularEast) {
1976 newX = tr.width() + tr.x();
1981 newY = tr.y() + tr.height();
1984 QTransform m = QTransform::fromTranslate(newX, newY);
1986 p->setTransform(m,
true);
1989 d->tabLayout(tab, widget, &tr, &iconRect);
1992 if (tab->position != QStyleOptionTab::TabPosition::Moving)
1993 tr = proxy()->subElementRect(SE_TabBarTabText, opt, widget);
1995 if (!tab->icon.isNull()) {
1996 const auto mode = (tab->state & State_Enabled) ? QIcon::Normal : QIcon::Disabled;
1997 const auto state = (tab->state & State_Selected) ? QIcon::On : QIcon::Off;
1998 tab->icon.paint(p, iconRect, Qt::AlignCenter, mode, state);
2001 proxy()->drawItemText(p, tr, alignment, tab->palette, tab->state & State_Enabled, tab->text,
2002 widget ? widget->foregroundRole() : QPalette::WindowText);
2006 if (tab->state & State_HasFocus) {
2007 const int OFFSET = 1 + pixelMetric(PM_DefaultFrameWidth, opt, widget);
2010 x1 = tab->rect.left();
2011 x2 = tab->rect.right() - 1;
2013 QStyleOptionFocusRect fropt;
2014 fropt.QStyleOption::operator=(*tab);
2015 fropt.rect.setRect(x1 + 1 + OFFSET, tab->rect.y() + OFFSET,
2016 x2 - x1 - 2*OFFSET, tab->rect.height() - 2*OFFSET);
2017 drawPrimitive(PE_FrameFocusRect, &fropt, p, widget);
2022#if QT_CONFIG(sizegrip)
2024 QPainterStateGuard psg(p);
2026 opt->rect.getRect(&x, &y, &w, &h);
2028 int sw = qMin(h, w);
2030 p->translate(0, h - w);
2032 p->translate(w - h, 0);
2039 if (
const QStyleOptionSizeGrip *sgOpt = qstyleoption_cast<
const QStyleOptionSizeGrip *>(opt))
2040 corner = sgOpt->corner;
2041 else if (opt->direction == Qt::RightToLeft)
2042 corner = Qt::BottomLeftCorner;
2044 corner = Qt::BottomRightCorner;
2046 if (corner == Qt::BottomLeftCorner) {
2048 for (
int i = 0; i < 4; ++i) {
2049 p->setPen(opt->palette.light().color());
2050 p->drawLine(x, sy - 1 , sx + 1, sw);
2051 p->setPen(opt->palette.dark().color());
2052 p->drawLine(x, sy, sx, sw);
2053 p->setPen(opt->palette.dark().color());
2054 p->drawLine(x, sy + 1, sx - 1, sw);
2058 }
else if (corner == Qt::BottomRightCorner) {
2059 for (
int i = 0; i < 4; ++i) {
2060 p->setPen(opt->palette.light().color());
2061 p->drawLine(sx - 1, sw, sw, sy - 1);
2062 p->setPen(opt->palette.dark().color());
2063 p->drawLine(sx, sw, sw, sy);
2064 p->setPen(opt->palette.dark().color());
2065 p->drawLine(sx + 1, sw, sw, sy + 1);
2069 }
else if (corner == Qt::TopRightCorner) {
2071 for (
int i = 0; i < 4; ++i) {
2072 p->setPen(opt->palette.light().color());
2073 p->drawLine(sx - 1, y, sw, sy + 1);
2074 p->setPen(opt->palette.dark().color());
2075 p->drawLine(sx, y, sw, sy);
2076 p->setPen(opt->palette.dark().color());
2077 p->drawLine(sx + 1, y, sw, sy - 1);
2081 }
else if (corner == Qt::TopLeftCorner) {
2082 for (
int i = 0; i < 4; ++i) {
2083 p->setPen(opt->palette.light().color());
2084 p->drawLine(x, sy - 1, sx - 1, y);
2085 p->setPen(opt->palette.dark().color());
2086 p->drawLine(x, sy, sx, y);
2087 p->setPen(opt->palette.dark().color());
2088 p->drawLine(x, sy + 1, sx + 1, y);
2095#if QT_CONFIG(rubberband)
2096 case CE_RubberBand: {
2097 if (
const QStyleOptionRubberBand *rbOpt = qstyleoption_cast<
const QStyleOptionRubberBand *>(opt)) {
2098 QPixmap tiledPixmap(16, 16);
2099 QPainter pixmapPainter(&tiledPixmap);
2100 pixmapPainter.setPen(Qt::NoPen);
2101 pixmapPainter.setBrush(Qt::Dense4Pattern);
2102 pixmapPainter.setBackground(QBrush(opt->palette.base()));
2103 pixmapPainter.setBackgroundMode(Qt::OpaqueMode);
2104 pixmapPainter.drawRect(0, 0, tiledPixmap.width(), tiledPixmap.height());
2105 pixmapPainter.end();
2107 tiledPixmap = QPixmap::fromImage(tiledPixmap.toImage());
2109 QPainterStateGuard psg(p);
2110 QRect r = opt->rect;
2111 QStyleHintReturnMask mask;
2112 if (proxy()->styleHint(QStyle::SH_RubberBand_Mask, opt, widget, &mask))
2113 p->setClipRegion(mask.region);
2114 p->drawTiledPixmap(r.x(), r.y(), r.width(), r.height(), tiledPixmap);
2115 p->setPen(opt->palette.color(QPalette::Active, QPalette::WindowText));
2116 p->setBrush(Qt::NoBrush);
2117 p->drawRect(r.adjusted(0, 0, -1, -1));
2118 if (rbOpt->shape == QRubberBand::Rectangle)
2119 p->drawRect(r.adjusted(3, 3, -4, -4));
2123#if QT_CONFIG(dockwidget)
2124 case CE_DockWidgetTitle:
2125 if (
const QStyleOptionDockWidget *dwOpt = qstyleoption_cast<
const QStyleOptionDockWidget *>(opt)) {
2126 QRect r = dwOpt->rect.adjusted(0, 0, -1, -1);
2127 if (dwOpt->movable) {
2128 p->setPen(dwOpt->palette.color(QPalette::Dark));
2132 if (!dwOpt->title.isEmpty()) {
2133 const bool verticalTitleBar = dwOpt->verticalTitleBar;
2135 QPainterStateGuard psg(p, QPainterStateGuard::InitialState::NoSave);
2136 if (verticalTitleBar) {
2140 p->translate(r.left(), r.top() + r.width());
2142 p->translate(-r.left(), -r.top());
2145 const int indent = p->fontMetrics().descent();
2146 proxy()->drawItemText(p, r.adjusted(indent + 1, 1, -indent - 1, -1),
2147 Qt::AlignLeft | Qt::AlignVCenter | Qt::TextHideMnemonic, dwOpt->palette,
2148 dwOpt->state & State_Enabled, dwOpt->title,
2149 QPalette::WindowText);
2155 if (
const QStyleOptionHeader *header = qstyleoption_cast<
const QStyleOptionHeader *>(opt)) {
2156 QPainterStateGuard psg(p);
2157 p->setClipRect(opt->rect);
2158 proxy()->drawControl(CE_HeaderSection, header, p, widget);
2160 QStyleOptionHeaderV2 subopt;
2161 QStyleOptionHeader &v1Copy = subopt;
2162 if (
auto v2 = qstyleoption_cast<
const QStyleOptionHeaderV2 *>(opt))
2166 subopt.rect = subElementRect(SE_HeaderLabel, header, widget);
2167 if (subopt.rect.isValid())
2168 proxy()->drawControl(CE_HeaderLabel, &subopt, p, widget);
2169 if (header->sortIndicator != QStyleOptionHeader::None) {
2170 subopt.rect = subElementRect(SE_HeaderArrow, opt, widget);
2171 proxy()->drawPrimitive(PE_IndicatorHeaderArrow, &subopt, p, widget);
2176 p->fillRect(opt->rect, opt->palette.windowText());
2178 case CE_HeaderSection:
2179 qDrawShadePanel(p, opt->rect, opt->palette,
2180 opt->state & State_Sunken, 1,
2181 &opt->palette.brush(QPalette::Button));
2183 case CE_HeaderEmptyArea:
2184 p->fillRect(opt->rect, opt->palette.window());
2186#if QT_CONFIG(combobox)
2187 case CE_ComboBoxLabel:
2188 if (
const QStyleOptionComboBox *cb = qstyleoption_cast<
const QStyleOptionComboBox *>(opt)) {
2189 QRect editRect = proxy()->subControlRect(CC_ComboBox, cb, SC_ComboBoxEditField, widget);
2190 QPainterStateGuard psg(p);
2191 p->setClipRect(editRect);
2192 if (!cb->currentIcon.isNull()) {
2193 QIcon::Mode mode = cb->state & State_Enabled ? QIcon::Normal
2195 QPixmap pixmap = cb->currentIcon.pixmap(cb->iconSize, QStyleHelper::getDpr(p), mode);
2196 QRect iconRect(editRect);
2197 iconRect.setWidth(cb->iconSize.width() + 4);
2198 iconRect = alignedRect(cb->direction,
2199 Qt::AlignLeft | Qt::AlignVCenter,
2200 iconRect.size(), editRect);
2202 p->fillRect(iconRect, opt->palette.brush(QPalette::Base));
2203 proxy()->drawItemPixmap(p, iconRect, Qt::AlignCenter, pixmap);
2205 if (cb->direction == Qt::RightToLeft)
2206 editRect.translate(-4 - cb->iconSize.width(), 0);
2208 editRect.translate(cb->iconSize.width() + 4, 0);
2210 if (!cb->currentText.isEmpty() && !cb->editable) {
2212 proxy()->drawItemText(p, editRect.adjusted(2, 0, -2, 0),
2213 visualAlignment(cb->direction, cb->textAlignment),
2214 cb->palette, cb->state & State_Enabled, cb->currentText);
2219#if QT_CONFIG(toolbar)
2221 if (
const QStyleOptionToolBar *toolBar = qstyleoption_cast<
const QStyleOptionToolBar *>(opt)) {
2223 QStyleOptionFrame frame;
2224 frame.QStyleOption::operator=(*toolBar);
2225 frame.lineWidth = toolBar->lineWidth;
2226 frame.midLineWidth = toolBar->midLineWidth;
2227 proxy()->drawPrimitive(PE_PanelToolBar, opt, p, widget);
2229 if (widget && qobject_cast<QToolBar *>(widget->parentWidget()))
2231 qDrawShadePanel(p, toolBar->rect, toolBar->palette,
false, toolBar->lineWidth,
2232 &toolBar->palette.brush(QPalette::Button));
2236 case CE_ColumnViewGrip: {
2238 QLinearGradient g(0, 0, opt->rect.width(), 0);
2239 g.setColorAt(0, opt->palette.color(QPalette::Active, QPalette::Mid));
2240 g.setColorAt(0.5, Qt::white);
2241 p->fillRect(QRect(0, 0, opt->rect.width(), opt->rect.height()), g);
2245 pen.setWidth(opt->rect.width()/20);
2246 pen.setColor(opt->palette.color(QPalette::Active, QPalette::Dark));
2249 int line1starting = opt->rect.width()*8 / 20;
2250 int line2starting = opt->rect.width()*13 / 20;
2251 int top = opt->rect.height()*20/75;
2252 int bottom = opt->rect.height() - 1 - top;
2253 p->drawLine(line1starting, top, line1starting, bottom);
2254 p->drawLine(line2starting, top, line2starting, bottom);
2258#if QT_CONFIG(itemviews)
2259 case CE_ItemViewItem:
2260 if (
const QStyleOptionViewItem *vopt = qstyleoption_cast<
const QStyleOptionViewItem *>(opt)) {
2261 QPainterStateGuard psg(p);
2263 const QRegion clipRegion = p->hasClipping() ? (p->clipRegion() & opt->rect) : opt->rect;
2264 p->setClipRegion(clipRegion);
2266 QRect checkRect = proxy()->subElementRect(SE_ItemViewItemCheckIndicator, vopt, widget);
2267 QRect iconRect = proxy()->subElementRect(SE_ItemViewItemDecoration, vopt, widget);
2268 QRect textRect = proxy()->subElementRect(SE_ItemViewItemText, vopt, widget);
2271 proxy()->drawPrimitive(PE_PanelItemViewItem, opt, p, widget);
2274 if (vopt->features & QStyleOptionViewItem::HasCheckIndicator) {
2275 QStyleOptionViewItem option(*vopt);
2276 option.rect = checkRect;
2277 option.state = option.state & ~QStyle::State_HasFocus;
2279 switch (vopt->checkState) {
2281 option.state |= QStyle::State_Off;
2283 case Qt::PartiallyChecked:
2284 option.state |= QStyle::State_NoChange;
2287 option.state |= QStyle::State_On;
2290 proxy()->drawPrimitive(QStyle::PE_IndicatorItemViewItemCheck, &option, p, widget);
2294 QIcon::Mode mode = QIcon::Normal;
2295 if (!(vopt->state & QStyle::State_Enabled))
2296 mode = QIcon::Disabled;
2297 else if (vopt->state & QStyle::State_Selected)
2298 mode = QIcon::Selected;
2299 QIcon::State state = vopt->state & QStyle::State_Open ? QIcon::On : QIcon::Off;
2300 vopt->icon.paint(p, iconRect, vopt->decorationAlignment, mode, state);
2303 if (!vopt->text.isEmpty()) {
2304 QPalette::ColorGroup cg = vopt->state & QStyle::State_Enabled
2305 ? QPalette::Normal : QPalette::Disabled;
2306 if (cg == QPalette::Normal && !(vopt->state & QStyle::State_Active))
2307 cg = QPalette::Inactive;
2309 if (vopt->state & QStyle::State_Selected) {
2310 p->setPen(vopt->palette.color(cg, QPalette::HighlightedText));
2312 p->setPen(vopt->palette.color(cg, QPalette::Text));
2314 d->viewItemDrawText(p, vopt, textRect);
2318 if (vopt->state & QStyle::State_HasFocus) {
2319 QStyleOptionFocusRect o;
2320 o.QStyleOption::operator=(*vopt);
2321 o.rect = proxy()->subElementRect(SE_ItemViewItemFocusRect, vopt, widget);
2322 o.state |= QStyle::State_KeyboardFocusChange;
2323 o.state |= QStyle::State_Item;
2324 QPalette::ColorGroup cg = (vopt->state & QStyle::State_Enabled)
2325 ? QPalette::Normal : QPalette::Disabled;
2326 o.backgroundColor = vopt->palette.color(cg, (vopt->state & QStyle::State_Selected)
2327 ? QPalette::Highlight : QPalette::Window);
2328 proxy()->drawPrimitive(QStyle::PE_FrameFocusRect, &o, p, widget);
2335 case CE_ShapedFrame:
2336 if (
const QStyleOptionFrame *f = qstyleoption_cast<
const QStyleOptionFrame *>(opt)) {
2337 int frameShape = f->frameShape;
2338 int frameShadow = QFrame::Plain;
2339 if (f->state & QStyle::State_Sunken) {
2340 frameShadow = QFrame::Sunken;
2341 }
else if (f->state & QStyle::State_Raised) {
2342 frameShadow = QFrame::Raised;
2345 int lw = f->lineWidth;
2346 int mlw = f->midLineWidth;
2347 QPalette::ColorRole foregroundRole = QPalette::WindowText;
2349 foregroundRole = widget->foregroundRole();
2351 switch (frameShape) {
2353 if (frameShadow == QFrame::Plain) {
2354 qDrawPlainRect(p, f->rect, f->palette.color(foregroundRole), lw);
2356 qDrawShadeRect(p, f->rect, f->palette, frameShadow == QFrame::Sunken, lw, mlw);
2359 case QFrame::StyledPanel:
2363 widget->style()->drawPrimitive(QStyle::PE_Frame, opt, p, widget);
2365 proxy()->drawPrimitive(QStyle::PE_Frame, opt, p, widget);
2369 if (frameShadow == QFrame::Plain) {
2370 qDrawPlainRect(p, f->rect, f->palette.color(foregroundRole), lw);
2372 qDrawShadePanel(p, f->rect, f->palette, frameShadow == QFrame::Sunken, lw);
2375 case QFrame::WinPanel:
2376 if (frameShadow == QFrame::Plain) {
2377 qDrawPlainRect(p, f->rect, f->palette.color(foregroundRole), lw);
2379 qDrawWinPanel(p, f->rect, f->palette, frameShadow == QFrame::Sunken);
2383 case QFrame::VLine: {
2385 if (frameShape == QFrame::HLine) {
2386 p1 = QPoint(opt->rect.x(), opt->rect.y() + opt->rect.height() / 2);
2387 p2 = QPoint(opt->rect.x() + opt->rect.width(), p1.y());
2389 p1 = QPoint(opt->rect.x() + opt->rect.width() / 2, opt->rect.y());
2390 p2 = QPoint(p1.x(), p1.y() + opt->rect.height());
2392 if (frameShadow == QFrame::Plain) {
2393 QPen oldPen = p->pen();
2394 p->setPen(QPen(opt->palette.brush(foregroundRole), lw));
2395 p->drawLine(p1, p2);
2398 qDrawShadeLine(p, p1, p2, f->palette, frameShadow == QFrame::Sunken, lw, mlw);
2409#if !QT_CONFIG(tabbar) && !QT_CONFIG(itemviews)
2417QRect QCommonStyle::subElementRect(SubElement sr,
const QStyleOption *opt,
2418 const QWidget *widget)
const
2420 Q_D(
const QCommonStyle);
2423 case SE_PushButtonContents:
2424 if (
const QStyleOptionButton *btn = qstyleoption_cast<
const QStyleOptionButton *>(opt)) {
2426 dx1 = proxy()->pixelMetric(PM_DefaultFrameWidth, btn, widget);
2427 if (btn->features & QStyleOptionButton::AutoDefaultButton)
2428 dx1 += proxy()->pixelMetric(PM_ButtonDefaultIndicator, btn, widget);
2430 r.setRect(opt->rect.x() + dx1, opt->rect.y() + dx1, opt->rect.width() - dx2,
2431 opt->rect.height() - dx2);
2432 r = visualRect(opt->direction, opt->rect, r);
2435 case SE_PushButtonFocusRect:
2436 if (
const QStyleOptionButton *btn = qstyleoption_cast<
const QStyleOptionButton *>(opt)) {
2437 int dbw1 = 0, dbw2 = 0;
2438 if (btn->features & QStyleOptionButton::AutoDefaultButton){
2439 dbw1 = proxy()->pixelMetric(PM_ButtonDefaultIndicator, btn, widget);
2443 int dfw1 = proxy()->pixelMetric(PM_DefaultFrameWidth, btn, widget) + 1,
2446 r.setRect(btn->rect.x() + dfw1 + dbw1, btn->rect.y() + dfw1 + dbw1,
2447 btn->rect.width() - dfw2 - dbw2, btn->rect.height()- dfw2 - dbw2);
2448 r = visualRect(opt->direction, opt->rect, r);
2451 case SE_PushButtonBevel:
2454 r = visualRect(opt->direction, opt->rect, r);
2457 case SE_CheckBoxIndicator:
2459 int h = proxy()->pixelMetric(PM_IndicatorHeight, opt, widget);
2460 r.setRect(opt->rect.x(), opt->rect.y() + ((opt->rect.height() - h) / 2),
2461 proxy()->pixelMetric(PM_IndicatorWidth, opt, widget), h);
2462 r = visualRect(opt->direction, opt->rect, r);
2466 case SE_CheckBoxContents:
2469 QRect ir = visualRect(opt->direction, opt->rect,
2470 subElementRect(SE_CheckBoxIndicator, opt, widget));
2471 int spacing = proxy()->pixelMetric(PM_CheckBoxLabelSpacing, opt, widget);
2472 r.setRect(ir.right() + spacing, opt->rect.y(), opt->rect.width() - ir.width() - spacing,
2473 opt->rect.height());
2474 r = visualRect(opt->direction, opt->rect, r);
2478 case SE_CheckBoxFocusRect:
2479 if (
const QStyleOptionButton *btn = qstyleoption_cast<
const QStyleOptionButton *>(opt)) {
2480 if (btn->icon.isNull() && btn->text.isEmpty()) {
2481 r = subElementRect(SE_CheckBoxIndicator, opt, widget);
2482 r.adjust(1, 1, -1, -1);
2486 QRect cr = visualRect(btn->direction, btn->rect,
2487 subElementRect(SE_CheckBoxContents, btn, widget));
2489 QRect iconRect, textRect;
2490 if (!btn->text.isEmpty()) {
2491 textRect = itemTextRect(opt->fontMetrics, cr, Qt::AlignAbsolute | Qt::AlignLeft
2492 | Qt::AlignVCenter | Qt::TextShowMnemonic,
2493 btn->state & State_Enabled, btn->text);
2495 if (!btn->icon.isNull()) {
2496 iconRect = itemPixmapRect(cr, Qt::AlignAbsolute | Qt::AlignLeft | Qt::AlignVCenter
2497 | Qt::TextShowMnemonic,
2498 btn->icon.pixmap(btn->iconSize, QStyleHelper::getDpr(widget), QIcon::Normal));
2499 if (!textRect.isEmpty())
2500 textRect.translate(iconRect.right() + 4, 0);
2502 r = iconRect | textRect;
2503 r.adjust(-3, -2, 3, 2);
2504 r = r.intersected(btn->rect);
2505 r = visualRect(btn->direction, btn->rect, r);
2509 case SE_RadioButtonIndicator:
2511 int h = proxy()->pixelMetric(PM_ExclusiveIndicatorHeight, opt, widget);
2512 r.setRect(opt->rect.x(), opt->rect.y() + ((opt->rect.height() - h) / 2),
2513 proxy()->pixelMetric(PM_ExclusiveIndicatorWidth, opt, widget), h);
2514 r = visualRect(opt->direction, opt->rect, r);
2518 case SE_RadioButtonContents:
2520 QRect ir = visualRect(opt->direction, opt->rect,
2521 subElementRect(SE_RadioButtonIndicator, opt, widget));
2522 int spacing = proxy()->pixelMetric(PM_RadioButtonLabelSpacing, opt, widget);
2523 r.setRect(ir.right() + spacing, opt->rect.y(), opt->rect.width() - ir.width() - spacing,
2524 opt->rect.height());
2525 r = visualRect(opt->direction, opt->rect, r);
2529 case SE_RadioButtonFocusRect:
2530 if (
const QStyleOptionButton *btn = qstyleoption_cast<
const QStyleOptionButton *>(opt)) {
2531 if (btn->icon.isNull() && btn->text.isEmpty()) {
2532 r = subElementRect(SE_RadioButtonIndicator, opt, widget);
2533 r.adjust(1, 1, -1, -1);
2536 QRect cr = visualRect(btn->direction, btn->rect,
2537 subElementRect(SE_RadioButtonContents, opt, widget));
2539 QRect iconRect, textRect;
2540 if (!btn->text.isEmpty()){
2541 textRect = itemTextRect(opt->fontMetrics, cr, Qt::AlignAbsolute | Qt::AlignLeft | Qt::AlignVCenter
2542 | Qt::TextShowMnemonic, btn->state & State_Enabled, btn->text);
2544 if (!btn->icon.isNull()) {
2545 iconRect = itemPixmapRect(cr, Qt::AlignAbsolute | Qt::AlignLeft | Qt::AlignVCenter | Qt::TextShowMnemonic,
2546 btn->icon.pixmap(btn->iconSize, QStyleHelper::getDpr(widget), QIcon::Normal));
2547 if (!textRect.isEmpty())
2548 textRect.translate(iconRect.right() + 4, 0);
2550 r = iconRect | textRect;
2551 r.adjust(-3, -2, 3, 2);
2552 r = r.intersected(btn->rect);
2553 r = visualRect(btn->direction, btn->rect, r);
2556#if QT_CONFIG(slider)
2557 case SE_SliderFocusRect:
2558 if (
const QStyleOptionSlider *slider = qstyleoption_cast<
const QStyleOptionSlider *>(opt)) {
2559 int tickOffset = proxy()->pixelMetric(PM_SliderTickmarkOffset, slider, widget);
2560 int thickness = proxy()->pixelMetric(PM_SliderControlThickness, slider, widget);
2561 if (slider->orientation == Qt::Horizontal)
2562 r.setRect(0, tickOffset - 1, slider->rect.width(), thickness + 2);
2564 r.setRect(tickOffset - 1, 0, thickness + 2, slider->rect.height());
2565 r = r.intersected(slider->rect);
2566 r = visualRect(opt->direction, opt->rect, r);
2570#if QT_CONFIG(progressbar)
2571 case SE_ProgressBarGroove:
2572 case SE_ProgressBarContents:
2573 case SE_ProgressBarLabel:
2574 if (
const QStyleOptionProgressBar *pb = qstyleoption_cast<
const QStyleOptionProgressBar *>(opt)) {
2576 const bool vertical = !(pb->state & QStyle::State_Horizontal);
2578 if (pb->textVisible)
2579 textw = qMax(pb->fontMetrics.horizontalAdvance(pb->text), pb->fontMetrics.horizontalAdvance(
"100%"_L1)) + 6;
2582 if ((pb->textAlignment & Qt::AlignCenter) == 0) {
2583 if (sr != SE_ProgressBarLabel)
2584 r.setCoords(pb->rect.left(), pb->rect.top(),
2585 pb->rect.right() - textw, pb->rect.bottom());
2587 r.setCoords(pb->rect.right() - textw, pb->rect.top(),
2588 pb->rect.right(), pb->rect.bottom());
2592 r = visualRect(pb->direction, pb->rect, r);
2596#if QT_CONFIG(combobox)
2597 case SE_ComboBoxFocusRect:
2598 if (
const QStyleOptionComboBox *cb = qstyleoption_cast<
const QStyleOptionComboBox *>(opt)) {
2599 int margin = cb->frame ? 3 : 0;
2600 r.setRect(opt->rect.left() + margin, opt->rect.top() + margin,
2601 opt->rect.width() - 2*margin - 16, opt->rect.height() - 2*margin);
2602 r = visualRect(opt->direction, opt->rect, r);
2606#if QT_CONFIG(toolbox)
2607 case SE_ToolBoxTabContents:
2609 r.adjust(0, 0, -30, 0);
2612 case SE_HeaderLabel: {
2613 int margin = proxy()->pixelMetric(QStyle::PM_HeaderMargin, opt, widget);
2614 r.setRect(opt->rect.x() + margin, opt->rect.y() + margin,
2615 opt->rect.width() - margin * 2, opt->rect.height() - margin * 2);
2617 if (
const QStyleOptionHeader *header = qstyleoption_cast<
const QStyleOptionHeader *>(opt)) {
2619 if (header->sortIndicator != QStyleOptionHeader::None) {
2620 if (opt->state & State_Horizontal)
2621 r.setWidth(r.width() - (opt->rect.height() / 2) - (margin * 2));
2623 r.setHeight(r.height() - (opt->rect.width() / 2) - (margin * 2));
2626 r = visualRect(opt->direction, opt->rect, r);
2628 case SE_HeaderArrow: {
2629 int h = opt->rect.height();
2630 int w = opt->rect.width();
2631 int x = opt->rect.x();
2632 int y = opt->rect.y();
2633 int margin = proxy()->pixelMetric(QStyle::PM_HeaderMargin, opt, widget);
2635 if (opt->state & State_Horizontal) {
2636 int horiz_size = h / 2;
2637 r.setRect(x + w - margin * 2 - horiz_size, y + 5,
2638 horiz_size, h - margin * 2 - 5);
2640 int vert_size = w / 2;
2641 r.setRect(x + 5, y + h - margin * 2 - vert_size,
2642 w - margin * 2 - 5, vert_size);
2644 r = visualRect(opt->direction, opt->rect, r);
2647 case SE_RadioButtonClickRect:
2648 r = subElementRect(SE_RadioButtonFocusRect, opt, widget);
2649 r |= subElementRect(SE_RadioButtonIndicator, opt, widget);
2651 case SE_CheckBoxClickRect:
2652 r = subElementRect(SE_CheckBoxFocusRect, opt, widget);
2653 r |= subElementRect(SE_CheckBoxIndicator, opt, widget);
2655#if QT_CONFIG(tabwidget)
2656 case SE_TabWidgetTabBar:
2657 if (
const QStyleOptionTabWidgetFrame *twf
2658 = qstyleoption_cast<
const QStyleOptionTabWidgetFrame *>(opt)) {
2659 r.setSize(twf->tabBarSize);
2660 const uint alingMask = Qt::AlignLeft | Qt::AlignRight | Qt::AlignHCenter;
2661 switch (twf->shape) {
2662 case QTabBar::RoundedNorth:
2663 case QTabBar::TriangularNorth:
2666 r.setWidth(qMin(r.width(), twf->rect.width()
2667 - twf->leftCornerWidgetSize.width()
2668 - twf->rightCornerWidgetSize.width()));
2669 switch (proxy()->styleHint(SH_TabBar_Alignment, twf, widget) & alingMask) {
2672 r.moveTopLeft(QPoint(twf->leftCornerWidgetSize.width(), 0));
2674 case Qt::AlignHCenter:
2675 r.moveTopLeft(QPoint(twf->rect.center().x() - qRound(r.width() / 2.0f)
2676 + (twf->leftCornerWidgetSize.width() / 2)
2677 - (twf->rightCornerWidgetSize.width() / 2), 0));
2679 case Qt::AlignRight:
2680 r.moveTopLeft(QPoint(twf->rect.width() - twf->tabBarSize.width()
2681 - twf->rightCornerWidgetSize.width(), 0));
2684 r = visualRect(twf->direction, twf->rect, r);
2686 case QTabBar::RoundedSouth:
2687 case QTabBar::TriangularSouth:
2688 r.setWidth(qMin(r.width(), twf->rect.width()
2689 - twf->leftCornerWidgetSize.width()
2690 - twf->rightCornerWidgetSize.width()));
2691 switch (proxy()->styleHint(SH_TabBar_Alignment, twf, widget) & alingMask) {
2694 r.moveTopLeft(QPoint(twf->leftCornerWidgetSize.width(),
2695 twf->rect.height() - twf->tabBarSize.height()));
2697 case Qt::AlignHCenter:
2698 r.moveTopLeft(QPoint(twf->rect.center().x() - qRound(r.width() / 2.0f)
2699 + (twf->leftCornerWidgetSize.width() / 2)
2700 - (twf->rightCornerWidgetSize.width() / 2),
2701 twf->rect.height() - twf->tabBarSize.height()));
2703 case Qt::AlignRight:
2704 r.moveTopLeft(QPoint(twf->rect.width() - twf->tabBarSize.width()
2705 - twf->rightCornerWidgetSize.width(),
2706 twf->rect.height() - twf->tabBarSize.height()));
2709 r = visualRect(twf->direction, twf->rect, r);
2711 case QTabBar::RoundedEast:
2712 case QTabBar::TriangularEast:
2713 r.setHeight(qMin(r.height(), twf->rect.height()
2714 - twf->leftCornerWidgetSize.height()
2715 - twf->rightCornerWidgetSize.height()));
2716 switch (proxy()->styleHint(SH_TabBar_Alignment, twf, widget) & alingMask) {
2719 r.moveTopLeft(QPoint(twf->rect.width() - twf->tabBarSize.width(),
2720 twf->leftCornerWidgetSize.height()));
2722 case Qt::AlignHCenter:
2723 r.moveTopLeft(QPoint(twf->rect.width() - twf->tabBarSize.width(),
2724 twf->rect.center().y() - r.height() / 2));
2726 case Qt::AlignRight:
2727 r.moveTopLeft(QPoint(twf->rect.width() - twf->tabBarSize.width(),
2728 twf->rect.height() - twf->tabBarSize.height()
2729 - twf->rightCornerWidgetSize.height()));
2733 case QTabBar::RoundedWest:
2734 case QTabBar::TriangularWest:
2735 r.setHeight(qMin(r.height(), twf->rect.height()
2736 - twf->leftCornerWidgetSize.height()
2737 - twf->rightCornerWidgetSize.height()));
2738 switch (proxy()->styleHint(SH_TabBar_Alignment, twf, widget) & alingMask) {
2741 r.moveTopLeft(QPoint(0, twf->leftCornerWidgetSize.height()));
2743 case Qt::AlignHCenter:
2744 r.moveTopLeft(QPoint(0, twf->rect.center().y() - r.height() / 2));
2746 case Qt::AlignRight:
2747 r.moveTopLeft(QPoint(0, twf->rect.height() - twf->tabBarSize.height()
2748 - twf->rightCornerWidgetSize.height()));
2755 case SE_TabWidgetTabPane:
2756 case SE_TabWidgetTabContents:
2757 if (
const QStyleOptionTabWidgetFrame *twf = qstyleoption_cast<
const QStyleOptionTabWidgetFrame *>(opt)) {
2758 QStyleOptionTab tabopt;
2759 tabopt.shape = twf->shape;
2760 int overlap = proxy()->pixelMetric(PM_TabBarBaseOverlap, &tabopt, widget);
2761 if (twf->lineWidth == 0)
2763 switch (twf->shape) {
2764 case QTabBar::RoundedNorth:
2765 case QTabBar::TriangularNorth:
2766 r = QRect(QPoint(0,qMax(twf->tabBarSize.height() - overlap, 0)),
2767 QSize(twf->rect.width(), qMin(twf->rect.height() - twf->tabBarSize.height() + overlap, twf->rect.height())));
2769 case QTabBar::RoundedSouth:
2770 case QTabBar::TriangularSouth:
2771 r = QRect(QPoint(0,0), QSize(twf->rect.width(), qMin(twf->rect.height() - twf->tabBarSize.height() + overlap, twf->rect.height())));
2773 case QTabBar::RoundedEast:
2774 case QTabBar::TriangularEast:
2775 r = QRect(QPoint(0, 0), QSize(qMin(twf->rect.width() - twf->tabBarSize.width() + overlap, twf->rect.width()), twf->rect.height()));
2777 case QTabBar::RoundedWest:
2778 case QTabBar::TriangularWest:
2779 r = QRect(QPoint(qMax(twf->tabBarSize.width() - overlap, 0), 0),
2780 QSize(qMin(twf->rect.width() - twf->tabBarSize.width() + overlap, twf->rect.width()), twf->rect.height()));
2783 if (sr == SE_TabWidgetTabContents && twf->lineWidth > 0)
2784 r.adjust(2, 2, -2, -2);
2787 case SE_TabWidgetLeftCorner:
2788 if (
const QStyleOptionTabWidgetFrame *twf = qstyleoption_cast<
const QStyleOptionTabWidgetFrame *>(opt)) {
2789 QRect paneRect = subElementRect(SE_TabWidgetTabPane, twf, widget);
2790 switch (twf->shape) {
2791 case QTabBar::RoundedNorth:
2792 case QTabBar::TriangularNorth:
2793 r = QRect(QPoint(paneRect.x(), paneRect.y() - twf->leftCornerWidgetSize.height()),
2794 twf->leftCornerWidgetSize);
2796 case QTabBar::RoundedSouth:
2797 case QTabBar::TriangularSouth:
2798 r = QRect(QPoint(paneRect.x(), paneRect.height()), twf->leftCornerWidgetSize);
2803 r = visualRect(twf->direction, twf->rect, r);
2806 case SE_TabWidgetRightCorner:
2807 if (
const QStyleOptionTabWidgetFrame *twf = qstyleoption_cast<
const QStyleOptionTabWidgetFrame *>(opt)) {
2808 QRect paneRect = subElementRect(SE_TabWidgetTabPane, twf, widget);
2809 switch (twf->shape) {
2810 case QTabBar::RoundedNorth:
2811 case QTabBar::TriangularNorth:
2812 r = QRect(QPoint(paneRect.width() - twf->rightCornerWidgetSize.width(),
2813 paneRect.y() - twf->rightCornerWidgetSize.height()),
2814 twf->rightCornerWidgetSize);
2816 case QTabBar::RoundedSouth:
2817 case QTabBar::TriangularSouth:
2818 r = QRect(QPoint(paneRect.width() - twf->rightCornerWidgetSize.width(),
2819 paneRect.height()), twf->rightCornerWidgetSize);
2824 r = visualRect(twf->direction, twf->rect, r);
2827 case SE_TabBarTabText:
2828 if (
const QStyleOptionTab *tab = qstyleoption_cast<
const QStyleOptionTab *>(opt)) {
2829 QRect dummyIconRect;
2830 d->tabLayout(tab, widget, &r, &dummyIconRect);
2833 case SE_TabBarTabLeftButton:
2834 case SE_TabBarTabRightButton:
2835 if (
const QStyleOptionTab *tab = qstyleoption_cast<
const QStyleOptionTab *>(opt)) {
2836 bool selected = tab->state & State_Selected;
2837 int verticalShift = proxy()->pixelMetric(QStyle::PM_TabBarTabShiftVertical, tab, widget);
2838 int horizontalShift = proxy()->pixelMetric(QStyle::PM_TabBarTabShiftHorizontal, tab, widget);
2839 int hpadding = proxy()->pixelMetric(QStyle::PM_TabBarTabHSpace, opt, widget) / 2;
2841 bool verticalTabs = tab->shape == QTabBar::RoundedEast
2842 || tab->shape == QTabBar::RoundedWest
2843 || tab->shape == QTabBar::TriangularEast
2844 || tab->shape == QTabBar::TriangularWest;
2846 QRect tr = tab->rect;
2847 if (tab->shape == QTabBar::RoundedSouth || tab->shape == QTabBar::TriangularSouth)
2848 verticalShift = -verticalShift;
2850 qSwap(horizontalShift, verticalShift);
2851 horizontalShift *= -1;
2852 verticalShift *= -1;
2854 if (tab->shape == QTabBar::RoundedWest || tab->shape == QTabBar::TriangularWest)
2855 horizontalShift = -horizontalShift;
2857 tr.adjust(0, 0, horizontalShift, verticalShift);
2860 tr.setBottom(tr.bottom() - verticalShift);
2861 tr.setRight(tr.right() - horizontalShift);
2864 QSize size = (sr == SE_TabBarTabLeftButton) ? tab->leftButtonSize : tab->rightButtonSize;
2865 int w = size.width();
2866 int h = size.height();
2868 bool atTheTop =
true;
2869 switch (tab->shape) {
2870 case QTabBar::RoundedWest:
2871 case QTabBar::TriangularWest:
2872 atTheTop = (sr == SE_TabBarTabLeftButton);
2874 case QTabBar::RoundedEast:
2875 case QTabBar::TriangularEast:
2876 atTheTop = (sr == SE_TabBarTabRightButton);
2879 const int midHeight =
2880 tr.y() +
static_cast<
int>(qCeil(
float(tr.height() - h) / 2));
2881 if (sr == SE_TabBarTabLeftButton)
2882 r = QRect(tab->rect.x() + hpadding, midHeight, w, h);
2884 r = QRect(tab->rect.right() - w - hpadding, midHeight, w, h);
2885 r = visualRect(tab->direction, tab->rect, r);
2890 const int midWidth = tr.x() + ((tr.width() - w) / 2);
2892 r = QRect(midWidth, tr.y() + tab->rect.height() - hpadding - h, w, h);
2894 r = QRect(midWidth, tr.y() + hpadding, w, h);
2900#if QT_CONFIG(tabbar)
2901 case SE_TabBarTearIndicator:
2902 if (
const QStyleOptionTab *tab = qstyleoption_cast<
const QStyleOptionTab *>(opt)) {
2903 switch (tab->shape) {
2904 case QTabBar::RoundedNorth:
2905 case QTabBar::TriangularNorth:
2906 case QTabBar::RoundedSouth:
2907 case QTabBar::TriangularSouth:
2908 r.setRect(tab->rect.left(), tab->rect.top(), 8, opt->rect.height());
2910 case QTabBar::RoundedWest:
2911 case QTabBar::TriangularWest:
2912 case QTabBar::RoundedEast:
2913 case QTabBar::TriangularEast:
2914 r.setRect(tab->rect.left(), tab->rect.top(), opt->rect.width(), 8);
2919 r = visualRect(opt->direction, opt->rect, r);
2922 case SE_TabBarScrollLeftButton: {
2923 const bool vertical = opt->rect.width() < opt->rect.height();
2924 const Qt::LayoutDirection ld = widget->layoutDirection();
2925 const int buttonWidth = proxy()->pixelMetric(QStyle::PM_TabBarScrollButtonWidth,
nullptr, widget);
2926 const int buttonOverlap = proxy()->pixelMetric(QStyle::PM_TabBar_ScrollButtonOverlap,
nullptr, widget);
2928 r = vertical ? QRect(0, opt->rect.height() - (buttonWidth * 2) + buttonOverlap, opt->rect.width(), buttonWidth)
2929 : QStyle::visualRect(ld, opt->rect, QRect(opt->rect.width() - (buttonWidth * 2) + buttonOverlap, 0, buttonWidth, opt->rect.height()));
2931 case SE_TabBarScrollRightButton: {
2932 const bool vertical = opt->rect.width() < opt->rect.height();
2933 const Qt::LayoutDirection ld = widget->layoutDirection();
2934 const int buttonWidth = proxy()->pixelMetric(QStyle::PM_TabBarScrollButtonWidth,
nullptr, widget);
2936 r = vertical ? QRect(0, opt->rect.height() - buttonWidth, opt->rect.width(), buttonWidth)
2937 : QStyle::visualRect(ld, opt->rect, QRect(opt->rect.width() - buttonWidth, 0, buttonWidth, opt->rect.height()));
2940 case SE_TreeViewDisclosureItem:
2943 case SE_LineEditContents:
2944 if (
const QStyleOptionFrame *f = qstyleoption_cast<
const QStyleOptionFrame *>(opt)) {
2945 r = f->rect.adjusted(f->lineWidth, f->lineWidth, -f->lineWidth, -f->lineWidth);
2946 r = visualRect(opt->direction, opt->rect, r);
2949 case SE_FrameContents:
2950 if (
const QStyleOptionFrame *f = qstyleoption_cast<
const QStyleOptionFrame *>(opt)) {
2951 int fw = proxy()->pixelMetric(PM_DefaultFrameWidth, f, widget);
2952 r = opt->rect.adjusted(fw, fw, -fw, -fw);
2953 r = visualRect(opt->direction, opt->rect, r);
2956 case SE_ShapedFrameContents:
2957 if (
const QStyleOptionFrame *f = qstyleoption_cast<
const QStyleOptionFrame *>(opt)) {
2958 int frameShape = f->frameShape;
2959 int frameShadow = QFrame::Plain;
2960 if (f->state & QStyle::State_Sunken) {
2961 frameShadow = QFrame::Sunken;
2962 }
else if (f->state & QStyle::State_Raised) {
2963 frameShadow = QFrame::Raised;
2968 switch (frameShape) {
2969 case QFrame::NoFrame:
2976 switch (frameShadow) {
2978 frameWidth = f->lineWidth;
2980 case QFrame::Raised:
2981 case QFrame::Sunken:
2982 frameWidth = (
short)(f->lineWidth*2 + f->midLineWidth);
2987 case QFrame::StyledPanel:
2991 return widget->style()->subElementRect(QStyle::SE_FrameContents, opt, widget);
2993 return subElementRect(QStyle::SE_FrameContents, opt, widget);
2995 case QFrame::WinPanel:
3000 switch (frameShadow) {
3002 case QFrame::Raised:
3003 case QFrame::Sunken:
3004 frameWidth = f->lineWidth;
3009 r = f->rect.adjusted(frameWidth, frameWidth, -frameWidth, -frameWidth);
3012#if QT_CONFIG(dockwidget)
3013 case SE_DockWidgetCloseButton:
3014 case SE_DockWidgetFloatButton:
3015 case SE_DockWidgetTitleBarText:
3016 case SE_DockWidgetIcon: {
3017 int iconSize = proxy()->pixelMetric(PM_SmallIconSize, opt, widget);
3018 int buttonMargin = proxy()->pixelMetric(PM_DockWidgetTitleBarButtonMargin, opt, widget);
3019 int margin = proxy()->pixelMetric(QStyle::PM_DockWidgetTitleMargin, opt, widget);
3020 QRect rect = opt->rect;
3022 const QStyleOptionDockWidget *dwOpt
3023 = qstyleoption_cast<
const QStyleOptionDockWidget*>(opt);
3024 bool canClose = dwOpt ==
nullptr ?
true : dwOpt->closable;
3025 bool canFloat = dwOpt ==
nullptr ?
false : dwOpt->floatable;
3027 const bool verticalTitleBar = dwOpt && dwOpt->verticalTitleBar;
3032 if (verticalTitleBar)
3033 rect = rect.transposed();
3037 int right = rect.right();
3038 int left = rect.left();
3042 QSize sz = proxy()->standardIcon(QStyle::SP_TitleBarCloseButton,
3043 opt, widget).actualSize(QSize(iconSize, iconSize));
3044 sz += QSize(buttonMargin, buttonMargin);
3045 if (verticalTitleBar)
3046 sz = sz.transposed();
3047 closeRect = QRect(right - sz.width(),
3048 rect.center().y() - sz.height()/2,
3049 sz.width(), sz.height());
3050 right = closeRect.left() - 1;
3052 if (sr == SE_DockWidgetCloseButton) {
3059 QSize sz = proxy()->standardIcon(QStyle::SP_TitleBarNormalButton,
3060 opt, widget).actualSize(QSize(iconSize, iconSize));
3061 sz += QSize(buttonMargin, buttonMargin);
3062 if (verticalTitleBar)
3063 sz = sz.transposed();
3064 floatRect = QRect(right - sz.width(),
3065 rect.center().y() - sz.height()/2,
3066 sz.width(), sz.height());
3067 right = floatRect.left() - 1;
3069 if (sr == SE_DockWidgetFloatButton) {
3075 if (
const QDockWidget *dw = qobject_cast<
const QDockWidget*>(widget)) {
3077 if (dw->isFloating())
3078 icon = dw->windowIcon();
3080 && icon.cacheKey() != QApplication::windowIcon().cacheKey()) {
3081 QSize sz = icon.actualSize(QSize(r.height(), r.height()));
3082 if (verticalTitleBar)
3083 sz = sz.transposed();
3084 iconRect = QRect(left, rect.center().y() - sz.height()/2,
3085 sz.width(), sz.height());
3086 left = iconRect.right() + margin;
3089 if (sr == SE_DockWidgetIcon) {
3094 QRect textRect = QRect(left, rect.top(),
3095 right - left, rect.height());
3096 if (sr == SE_DockWidgetTitleBarText) {
3103 if (verticalTitleBar) {
3104 r = QRect(rect.left() + r.top() - rect.top(),
3105 rect.top() + rect.right() - r.right(),
3106 r.height(), r.width());
3108 r = visualRect(opt->direction, rect, r);
3113#if QT_CONFIG(itemviews)
3114 case SE_ItemViewItemCheckIndicator:
3115 if (!qstyleoption_cast<
const QStyleOptionViewItem *>(opt)) {
3116 r = subElementRect(SE_CheckBoxIndicator, opt, widget);
3120 case SE_ItemViewItemDecoration:
3121 case SE_ItemViewItemText:
3122 case SE_ItemViewItemFocusRect:
3123 if (
const QStyleOptionViewItem *vopt = qstyleoption_cast<
const QStyleOptionViewItem *>(opt)) {
3124 if (!d->isViewItemCached(*vopt)) {
3125 d->viewItemLayout(vopt, &d->checkRect, &d->decorationRect, &d->displayRect,
false);
3126 if (d->cachedOption) {
3127 delete d->cachedOption;
3128 d->cachedOption =
nullptr;
3130 d->cachedOption =
new QStyleOptionViewItem(*vopt);
3132 if (sr == SE_ItemViewItemCheckIndicator)
3134 else if (sr == SE_ItemViewItemDecoration)
3135 r = d->decorationRect;
3136 else if (sr == SE_ItemViewItemText || sr == SE_ItemViewItemFocusRect)
3141#if QT_CONFIG(toolbar)
3142 case SE_ToolBarHandle:
3143 if (
const QStyleOptionToolBar *tbopt = qstyleoption_cast<
const QStyleOptionToolBar *>(opt)) {
3144 if (tbopt->features & QStyleOptionToolBar::Movable) {
3147 const QToolBar *tb = qobject_cast<
const QToolBar*>(widget);
3148 const QMargins margins = tb && tb->layout() ? tb->layout()->contentsMargins() : QMargins(2, 2, 2, 2);
3149 const int handleExtent = proxy()->pixelMetric(QStyle::PM_ToolBarHandleExtent, opt, tb);
3150 if (tbopt->state & QStyle::State_Horizontal) {
3151 r = QRect(margins.left(), margins.top(),
3153 tbopt->rect.height() - (margins.top() + margins.bottom()));
3154 r = QStyle::visualRect(tbopt->direction, tbopt->rect, r);
3156 r = QRect(margins.left(), margins.top(),
3157 tbopt->rect.width() - (margins.left() + margins.right()),
3168#if !QT_CONFIG(tabwidget) && !QT_CONFIG(itemviews)
3215void QCommonStyle::drawComplexControl(ComplexControl cc,
const QStyleOptionComplex *opt,
3216 QPainter *p,
const QWidget *widget)
const
3219#if QT_CONFIG(slider)
3221 if (
const QStyleOptionSlider *slider = qstyleoption_cast<
const QStyleOptionSlider *>(opt)) {
3222 if (slider->subControls == SC_SliderTickmarks) {
3223 int tickOffset = proxy()->pixelMetric(PM_SliderTickmarkOffset, slider, widget);
3224 int ticks = slider->tickPosition;
3225 int thickness = proxy()->pixelMetric(PM_SliderControlThickness, slider, widget);
3226 int len = proxy()->pixelMetric(PM_SliderLength, slider, widget);
3227 int available = proxy()->pixelMetric(PM_SliderSpaceAvailable, slider, widget);
3228 int interval = slider->tickInterval;
3229 if (interval <= 0) {
3230 interval = slider->singleStep;
3231 if (QStyle::sliderPositionFromValue(slider->minimum, slider->maximum, interval,
3233 - QStyle::sliderPositionFromValue(slider->minimum, slider->maximum,
3235 interval = slider->pageStep;
3239 int fudge = len / 2;
3242 QPainterStateGuard psg(p);
3243 p->translate(slider->rect.x(), slider->rect.y());
3244 p->setPen(slider->palette.windowText().color());
3245 int v = slider->minimum;
3246 while (v <= slider->maximum + 1) {
3247 if (v == slider->maximum + 1 && interval == 1)
3249 const int v_ = qMin(v, slider->maximum);
3250 pos = QStyle::sliderPositionFromValue(slider->minimum, slider->maximum,
3251 v_, available) + fudge;
3252 if (slider->orientation == Qt::Horizontal) {
3253 if (ticks & QSlider::TicksAbove)
3254 p->drawLine(pos, 0, pos, tickOffset - 2);
3255 if (ticks & QSlider::TicksBelow)
3256 p->drawLine(pos, tickOffset + thickness + 1, pos,
3257 slider->rect.height()-1);
3259 if (ticks & QSlider::TicksAbove)
3260 p->drawLine(0, pos, tickOffset - 2, pos);
3261 if (ticks & QSlider::TicksBelow)
3262 p->drawLine(tickOffset + thickness + 1, pos,
3263 slider->rect.width()-1, pos);
3266 int nextInterval = v + interval;
3267 if (nextInterval < v)
3275#if QT_CONFIG(scrollbar)
3277 if (
const QStyleOptionSlider *scrollbar = qstyleoption_cast<
const QStyleOptionSlider *>(opt)) {
3279 QStyleOptionSlider newScrollbar = *scrollbar;
3280 State saveFlags = scrollbar->state;
3282 if (scrollbar->subControls & SC_ScrollBarSubLine) {
3283 newScrollbar.state = saveFlags;
3284 newScrollbar.rect = proxy()->subControlRect(cc, &newScrollbar, SC_ScrollBarSubLine, widget);
3285 if (newScrollbar.rect.isValid()) {
3286 if (!(scrollbar->activeSubControls & SC_ScrollBarSubLine))
3287 newScrollbar.state &= ~(State_Sunken | State_MouseOver);
3288 proxy()->drawControl(CE_ScrollBarSubLine, &newScrollbar, p, widget);
3291 if (scrollbar->subControls & SC_ScrollBarAddLine) {
3292 newScrollbar.rect = scrollbar->rect;
3293 newScrollbar.state = saveFlags;
3294 newScrollbar.rect = proxy()->subControlRect(cc, &newScrollbar, SC_ScrollBarAddLine, widget);
3295 if (newScrollbar.rect.isValid()) {
3296 if (!(scrollbar->activeSubControls & SC_ScrollBarAddLine))
3297 newScrollbar.state &= ~(State_Sunken | State_MouseOver);
3298 proxy()->drawControl(CE_ScrollBarAddLine, &newScrollbar, p, widget);
3301 if (scrollbar->subControls & SC_ScrollBarSubPage) {
3302 newScrollbar.rect = scrollbar->rect;
3303 newScrollbar.state = saveFlags;
3304 newScrollbar.rect = proxy()->subControlRect(cc, &newScrollbar, SC_ScrollBarSubPage, widget);
3305 if (newScrollbar.rect.isValid()) {
3306 if (!(scrollbar->activeSubControls & SC_ScrollBarSubPage))
3307 newScrollbar.state &= ~(State_Sunken | State_MouseOver);
3308 proxy()->drawControl(CE_ScrollBarSubPage, &newScrollbar, p, widget);
3311 if (scrollbar->subControls & SC_ScrollBarAddPage) {
3312 newScrollbar.rect = scrollbar->rect;
3313 newScrollbar.state = saveFlags;
3314 newScrollbar.rect = proxy()->subControlRect(cc, &newScrollbar, SC_ScrollBarAddPage, widget);
3315 if (newScrollbar.rect.isValid()) {
3316 if (!(scrollbar->activeSubControls & SC_ScrollBarAddPage))
3317 newScrollbar.state &= ~(State_Sunken | State_MouseOver);
3318 proxy()->drawControl(CE_ScrollBarAddPage, &newScrollbar, p, widget);
3321 if (scrollbar->subControls & SC_ScrollBarFirst) {
3322 newScrollbar.rect = scrollbar->rect;
3323 newScrollbar.state = saveFlags;
3324 newScrollbar.rect = proxy()->subControlRect(cc, &newScrollbar, SC_ScrollBarFirst, widget);
3325 if (newScrollbar.rect.isValid()) {
3326 if (!(scrollbar->activeSubControls & SC_ScrollBarFirst))
3327 newScrollbar.state &= ~(State_Sunken | State_MouseOver);
3328 proxy()->drawControl(CE_ScrollBarFirst, &newScrollbar, p, widget);
3331 if (scrollbar->subControls & SC_ScrollBarLast) {
3332 newScrollbar.rect = scrollbar->rect;
3333 newScrollbar.state = saveFlags;
3334 newScrollbar.rect = proxy()->subControlRect(cc, &newScrollbar, SC_ScrollBarLast, widget);
3335 if (newScrollbar.rect.isValid()) {
3336 if (!(scrollbar->activeSubControls & SC_ScrollBarLast))
3337 newScrollbar.state &= ~(State_Sunken | State_MouseOver);
3338 proxy()->drawControl(CE_ScrollBarLast, &newScrollbar, p, widget);
3341 if (scrollbar->subControls & SC_ScrollBarSlider) {
3342 newScrollbar.rect = scrollbar->rect;
3343 newScrollbar.state = saveFlags;
3344 newScrollbar.rect = proxy()->subControlRect(cc, &newScrollbar, SC_ScrollBarSlider, widget);
3345 if (newScrollbar.rect.isValid()) {
3346 if (!(scrollbar->activeSubControls & SC_ScrollBarSlider))
3347 newScrollbar.state &= ~(State_Sunken | State_MouseOver);
3348 proxy()->drawControl(CE_ScrollBarSlider, &newScrollbar, p, widget);
3350 if (scrollbar->state & State_HasFocus) {
3351 QStyleOptionFocusRect fropt;
3352 fropt.QStyleOption::operator=(newScrollbar);
3353 fropt.rect.setRect(newScrollbar.rect.x() + 2, newScrollbar.rect.y() + 2,
3354 newScrollbar.rect.width() - 5,
3355 newScrollbar.rect.height() - 5);
3356 proxy()->drawPrimitive(PE_FrameFocusRect, &fropt, p, widget);
3363#if QT_CONFIG(spinbox)
3365 if (
const QStyleOptionSpinBox *sb = qstyleoption_cast<
const QStyleOptionSpinBox *>(opt)) {
3366 QStyleOptionSpinBox copy = *sb;
3367 PrimitiveElement pe;
3369 if (sb->frame && (sb->subControls & SC_SpinBoxFrame)) {
3370 QRect r = proxy()->subControlRect(CC_SpinBox, sb, SC_SpinBoxFrame, widget);
3371 qDrawWinPanel(p, r, sb->palette,
true);
3374 if (sb->subControls & SC_SpinBoxUp) {
3375 copy.subControls = SC_SpinBoxUp;
3376 QPalette pal2 = sb->palette;
3377 if (!(sb->stepEnabled & QAbstractSpinBox::StepUpEnabled)) {
3378 pal2.setCurrentColorGroup(QPalette::Disabled);
3379 copy.state &= ~State_Enabled;
3382 copy.palette = pal2;
3384 if (sb->activeSubControls == SC_SpinBoxUp && (sb->state & State_Sunken)) {
3385 copy.state |= State_On;
3386 copy.state |= State_Sunken;
3388 copy.state |= State_Raised;
3389 copy.state &= ~State_Sunken;
3391 pe = (sb->buttonSymbols == QAbstractSpinBox::PlusMinus ? PE_IndicatorSpinPlus
3392 : PE_IndicatorSpinUp);
3394 copy.rect = proxy()->subControlRect(CC_SpinBox, sb, SC_SpinBoxUp, widget);
3395 proxy()->drawPrimitive(PE_PanelButtonBevel, ©, p, widget);
3396 copy.rect.adjust(3, 0, -4, 0);
3397 proxy()->drawPrimitive(pe, ©, p, widget);
3400 if (sb->subControls & SC_SpinBoxDown) {
3401 copy.subControls = SC_SpinBoxDown;
3402 copy.state = sb->state;
3403 QPalette pal2 = sb->palette;
3404 if (!(sb->stepEnabled & QAbstractSpinBox::StepDownEnabled)) {
3405 pal2.setCurrentColorGroup(QPalette::Disabled);
3406 copy.state &= ~State_Enabled;
3408 copy.palette = pal2;
3410 if (sb->activeSubControls == SC_SpinBoxDown && (sb->state & State_Sunken)) {
3411 copy.state |= State_On;
3412 copy.state |= State_Sunken;
3414 copy.state |= State_Raised;
3415 copy.state &= ~State_Sunken;
3417 pe = (sb->buttonSymbols == QAbstractSpinBox::PlusMinus ? PE_IndicatorSpinMinus
3418 : PE_IndicatorSpinDown);
3420 copy.rect = proxy()->subControlRect(CC_SpinBox, sb, SC_SpinBoxDown, widget);
3421 proxy()->drawPrimitive(PE_PanelButtonBevel, ©, p, widget);
3422 copy.rect.adjust(3, 0, -4, 0);
3423 proxy()->drawPrimitive(pe, ©, p, widget);
3428#if QT_CONFIG(toolbutton)
3430 if (
const QStyleOptionToolButton *toolbutton
3431 = qstyleoption_cast<
const QStyleOptionToolButton *>(opt)) {
3432 QRect button, menuarea;
3433 button = proxy()->subControlRect(cc, toolbutton, SC_ToolButton, widget);
3434 menuarea = proxy()->subControlRect(cc, toolbutton, SC_ToolButtonMenu, widget);
3436 State bflags = toolbutton->state & ~State_Sunken;
3438 if (bflags & State_AutoRaise) {
3439 if (!(bflags & State_MouseOver) || !(bflags & State_Enabled)) {
3440 bflags &= ~State_Raised;
3443 State mflags = bflags;
3444 if (toolbutton->state & State_Sunken) {
3445 if (toolbutton->activeSubControls & SC_ToolButton)
3446 bflags |= State_Sunken;
3447 mflags |= State_Sunken;
3450 QStyleOption tool = *toolbutton;
3451 if (toolbutton->subControls & SC_ToolButton) {
3452 if (bflags & (State_Sunken | State_On | State_Raised)) {
3454 tool.state = bflags;
3455 proxy()->drawPrimitive(PE_PanelButtonTool, &tool, p, widget);
3459 if (toolbutton->state & State_HasFocus) {
3460 QStyleOptionFocusRect fr;
3461 fr.QStyleOption::operator=(*toolbutton);
3462 fr.rect.adjust(3, 3, -3, -3);
3463 if (toolbutton->features & QStyleOptionToolButton::MenuButtonPopup)
3464 fr.rect.adjust(0, 0, -proxy()->pixelMetric(QStyle::PM_MenuButtonIndicator,
3465 toolbutton, widget), 0);
3466 proxy()->drawPrimitive(PE_FrameFocusRect, &fr, p, widget);
3468 QStyleOptionToolButton label = *toolbutton;
3469 label.state = bflags;
3470 int fw = proxy()->pixelMetric(PM_DefaultFrameWidth, opt, widget);
3471 label.rect = button.adjusted(fw, fw, -fw, -fw);
3472 proxy()->drawControl(CE_ToolButtonLabel, &label, p, widget);
3474 if (toolbutton->subControls & SC_ToolButtonMenu) {
3475 tool.rect = menuarea;
3476 tool.state = mflags;
3477 if (mflags & (State_Sunken | State_On | State_Raised))
3478 proxy()->drawPrimitive(PE_IndicatorButtonDropDown, &tool, p, widget);
3479 proxy()->drawPrimitive(PE_IndicatorArrowDown, &tool, p, widget);
3480 }
else if (toolbutton->features & QStyleOptionToolButton::HasMenu) {
3481 int mbi = proxy()->pixelMetric(PM_MenuButtonIndicator, toolbutton, widget);
3482 QRect ir = toolbutton->rect;
3483 QStyleOptionToolButton newBtn = *toolbutton;
3484 newBtn.rect = QRect(ir.right() + 5 - mbi, ir.y() + ir.height() - mbi + 4, mbi - 6, mbi - 6);
3485 newBtn.rect = visualRect(toolbutton->direction, button, newBtn.rect);
3486 proxy()->drawPrimitive(PE_IndicatorArrowDown, &newBtn, p, widget);
3492 if (
const QStyleOptionTitleBar *tb = qstyleoption_cast<
const QStyleOptionTitleBar *>(opt)) {
3494 if (opt->subControls & SC_TitleBarLabel) {
3495 QColor left = tb->palette.highlight().color();
3496 QColor right = tb->palette.base().color();
3498 QBrush fillBrush(left);
3499 if (left != right) {
3500 QPoint p1(tb->rect.x(), tb->rect.top() + tb->rect.height()/2);
3501 QPoint p2(tb->rect.right(), tb->rect.top() + tb->rect.height()/2);
3502 QLinearGradient lg(p1, p2);
3503 lg.setColorAt(0, left);
3504 lg.setColorAt(1, right);
3508 p->fillRect(opt->rect, fillBrush);
3510 ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarLabel, widget);
3512 p->setPen(tb->palette.highlightedText().color());
3513 p->drawText(ir.x() + 2, ir.y(), ir.width() - 2, ir.height(),
3514 Qt::AlignLeft | Qt::AlignVCenter | Qt::TextSingleLine, tb->text);
3520 QStyleOption tool = *tb;
3521 if (tb->subControls & SC_TitleBarCloseButton && tb->titleBarFlags & Qt::WindowSystemMenuHint) {
3522 ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarCloseButton, widget);
3523 down = tb->activeSubControls & SC_TitleBarCloseButton && (opt->state & State_Sunken);
3524 if ((tb->titleBarFlags & Qt::WindowType_Mask) == Qt::Tool
3525#if QT_CONFIG(dockwidget)
3526 || qobject_cast<
const QDockWidget *>(widget)
3529 pm = proxy()->standardIcon(SP_DockWidgetCloseButton, &tool, widget).pixmap(QSize(10, 10), QStyleHelper::getDpr(p));
3531 pm = proxy()->standardIcon(SP_TitleBarCloseButton, &tool, widget).pixmap(QSize(10, 10), QStyleHelper::getDpr(p));
3533 tool.state = down ? State_Sunken : State_Raised;
3534 proxy()->drawPrimitive(PE_PanelButtonTool, &tool, p, widget);
3536 QPainterStateGuard psg(p, down ? QPainterStateGuard::InitialState::Save
3537 : QPainterStateGuard::InitialState::NoSave);
3539 p->translate(proxy()->pixelMetric(PM_ButtonShiftHorizontal, tb, widget),
3540 proxy()->pixelMetric(PM_ButtonShiftVertical, tb, widget));
3541 proxy()->drawItemPixmap(p, ir, Qt::AlignCenter, pm);
3544 if (tb->subControls & SC_TitleBarMaxButton
3545 && tb->titleBarFlags & Qt::WindowMaximizeButtonHint
3546 && !(tb->titleBarState & Qt::WindowMaximized)) {
3547 ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarMaxButton, widget);
3549 down = tb->activeSubControls & SC_TitleBarMaxButton && (opt->state & State_Sunken);
3550 pm = proxy()->standardIcon(SP_TitleBarMaxButton, &tool, widget).pixmap(QSize(10, 10), QStyleHelper::getDpr(p));
3552 tool.state = down ? State_Sunken : State_Raised;
3553 proxy()->drawPrimitive(PE_PanelButtonTool, &tool, p, widget);
3555 QPainterStateGuard psg(p, down ? QPainterStateGuard::InitialState::Save
3556 : QPainterStateGuard::InitialState::NoSave);
3558 p->translate(proxy()->pixelMetric(PM_ButtonShiftHorizontal, tb, widget),
3559 proxy()->pixelMetric(PM_ButtonShiftVertical, tb, widget));
3560 proxy()->drawItemPixmap(p, ir, Qt::AlignCenter, pm);
3563 if (tb->subControls & SC_TitleBarMinButton
3564 && tb->titleBarFlags & Qt::WindowMinimizeButtonHint
3565 && !(tb->titleBarState & Qt::WindowMinimized)) {
3566 ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarMinButton, widget);
3567 down = tb->activeSubControls & SC_TitleBarMinButton && (opt->state & State_Sunken);
3568 pm = proxy()->standardIcon(SP_TitleBarMinButton, &tool, widget).pixmap(QSize(10, 10), QStyleHelper::getDpr(p));
3570 tool.state = down ? State_Sunken : State_Raised;
3571 proxy()->drawPrimitive(PE_PanelButtonTool, &tool, p, widget);
3573 QPainterStateGuard psg(p, down ? QPainterStateGuard::InitialState::Save
3574 : QPainterStateGuard::InitialState::NoSave);
3576 p->translate(proxy()->pixelMetric(PM_ButtonShiftHorizontal, tb, widget),
3577 proxy()->pixelMetric(PM_ButtonShiftVertical, tb, widget));
3578 proxy()->drawItemPixmap(p, ir, Qt::AlignCenter, pm);
3581 bool drawNormalButton = (tb->subControls & SC_TitleBarNormalButton)
3582 && (((tb->titleBarFlags & Qt::WindowMinimizeButtonHint)
3583 && (tb->titleBarState & Qt::WindowMinimized))
3584 || ((tb->titleBarFlags & Qt::WindowMaximizeButtonHint)
3585 && (tb->titleBarState & Qt::WindowMaximized)));
3587 if (drawNormalButton) {
3588 ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarNormalButton, widget);
3589 down = tb->activeSubControls & SC_TitleBarNormalButton && (opt->state & State_Sunken);
3590 pm = proxy()->standardIcon(SP_TitleBarNormalButton, &tool, widget).pixmap(QSize(10, 10), QStyleHelper::getDpr(p));
3592 tool.state = down ? State_Sunken : State_Raised;
3593 proxy()->drawPrimitive(PE_PanelButtonTool, &tool, p, widget);
3595 QPainterStateGuard psg(p, down ? QPainterStateGuard::InitialState::Save
3596 : QPainterStateGuard::InitialState::NoSave);
3598 p->translate(proxy()->pixelMetric(PM_ButtonShiftHorizontal, tb, widget),
3599 proxy()->pixelMetric(PM_ButtonShiftVertical, tb, widget));
3600 proxy()->drawItemPixmap(p, ir, Qt::AlignCenter, pm);
3603 if (tb->subControls & SC_TitleBarShadeButton
3604 && tb->titleBarFlags & Qt::WindowShadeButtonHint
3605 && !(tb->titleBarState & Qt::WindowMinimized)) {
3606 ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarShadeButton, widget);
3607 down = (tb->activeSubControls & SC_TitleBarShadeButton && (opt->state & State_Sunken));
3608 pm = proxy()->standardIcon(SP_TitleBarShadeButton, &tool, widget).pixmap(QSize(10, 10), QStyleHelper::getDpr(p));
3610 tool.state = down ? State_Sunken : State_Raised;
3611 proxy()->drawPrimitive(PE_PanelButtonTool, &tool, p, widget);
3613 QPainterStateGuard psg(p, down ? QPainterStateGuard::InitialState::Save
3614 : QPainterStateGuard::InitialState::NoSave);
3616 p->translate(proxy()->pixelMetric(PM_ButtonShiftHorizontal, tb, widget),
3617 proxy()->pixelMetric(PM_ButtonShiftVertical, tb, widget));
3618 proxy()->drawItemPixmap(p, ir, Qt::AlignCenter, pm);
3621 if (tb->subControls & SC_TitleBarUnshadeButton
3622 && tb->titleBarFlags & Qt::WindowShadeButtonHint
3623 && tb->titleBarState & Qt::WindowMinimized) {
3624 ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarUnshadeButton, widget);
3626 down = tb->activeSubControls & SC_TitleBarUnshadeButton && (opt->state & State_Sunken);
3627 pm = proxy()->standardIcon(SP_TitleBarUnshadeButton, &tool, widget).pixmap(QSize(10, 10), QStyleHelper::getDpr(p));
3629 tool.state = down ? State_Sunken : State_Raised;
3630 proxy()->drawPrimitive(PE_PanelButtonTool, &tool, p, widget);
3632 QPainterStateGuard psg(p, down ? QPainterStateGuard::InitialState::Save
3633 : QPainterStateGuard::InitialState::NoSave);
3635 p->translate(proxy()->pixelMetric(PM_ButtonShiftHorizontal, tb, widget),
3636 proxy()->pixelMetric(PM_ButtonShiftVertical, tb, widget));
3637 proxy()->drawItemPixmap(p, ir, Qt::AlignCenter, pm);
3639 if (tb->subControls & SC_TitleBarContextHelpButton
3640 && tb->titleBarFlags & Qt::WindowContextHelpButtonHint) {
3641 ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarContextHelpButton, widget);
3643 down = tb->activeSubControls & SC_TitleBarContextHelpButton && (opt->state & State_Sunken);
3644 pm = proxy()->standardIcon(SP_TitleBarContextHelpButton, &tool, widget).pixmap(QSize(10, 10), QStyleHelper::getDpr(p));
3646 tool.state = down ? State_Sunken : State_Raised;
3647 proxy()->drawPrimitive(PE_PanelButtonTool, &tool, p, widget);
3649 QPainterStateGuard psg(p, down ? QPainterStateGuard::InitialState::Save
3650 : QPainterStateGuard::InitialState::NoSave);
3652 p->translate(proxy()->pixelMetric(PM_ButtonShiftHorizontal, tb, widget),
3653 proxy()->pixelMetric(PM_ButtonShiftVertical, tb, widget));
3654 proxy()->drawItemPixmap(p, ir, Qt::AlignCenter, pm);
3656 if (tb->subControls & SC_TitleBarSysMenu && tb->titleBarFlags & Qt::WindowSystemMenuHint) {
3657 ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarSysMenu, widget);
3658 if (!tb->icon.isNull()) {
3659 tb->icon.paint(p, ir);
3661 int iconSize = proxy()->pixelMetric(PM_SmallIconSize, tb, widget);
3662 pm = proxy()->standardIcon(SP_TitleBarMenuButton, &tool, widget).pixmap(QSize(iconSize, iconSize), QStyleHelper::getDpr(p));
3664 proxy()->drawItemPixmap(p, ir, Qt::AlignCenter, pm);
3671 if (
const QStyleOptionSlider *dial = qstyleoption_cast<
const QStyleOptionSlider *>(opt)) {
3673 QPainterStateGuard psg(p);
3676 if (p->paintEngine()->hasFeature(QPaintEngine::Antialiasing))
3677 p->setRenderHint(QPainter::Antialiasing);
3679 int width = dial->rect.width();
3680 int height = dial->rect.height();
3681 qreal r = qMin(width, height) / 2;
3683 qreal dx = dial->rect.x() + d_ + (width - 2 * r) / 2 + 1;
3684 qreal dy = dial->rect.y() + d_ + (height - 2 * r) / 2 + 1;
3685 QRect br = QRect(
int(dx),
int(dy),
int(r * 2 - 2 * d_ - 2),
int(r * 2 - 2 * d_ - 2));
3687 QPalette pal = opt->palette;
3689 if (dial->subControls & QStyle::SC_DialTickmarks) {
3690 p->setPen(pal.windowText().color());
3691 p->drawLines(QStyleHelper::calcLines(dial));
3694 if (dial->state & State_Enabled) {
3695 p->setBrush(pal.brush(QPalette::ColorRole(proxy()->styleHint(SH_Dial_BackgroundRole,
3697 p->setPen(Qt::NoPen);
3699 p->setBrush(Qt::NoBrush);
3701 p->setPen(pal.dark().color());
3702 p->drawArc(br, 60 * 16, 180 * 16);
3703 p->setPen(pal.light().color());
3704 p->drawArc(br, 240 * 16, 180 * 16);
3707 const auto arrow = calcArrow(dial, a);
3709 p->setPen(Qt::NoPen);
3710 p->setBrush(pal.button());
3711 p->drawPolygon(arrow.data(),
int(arrow.size()));
3713 a = QStyleHelper::angle(QPointF(width / 2, height / 2), arrow[0]);
3714 p->setBrush(Qt::NoBrush);
3716 if (a <= 0 || a > 200) {
3717 p->setPen(pal.light().color());
3718 p->drawLine(arrow[2], arrow[0]);
3719 p->drawLine(arrow[1], arrow[2]);
3720 p->setPen(pal.dark().color());
3721 p->drawLine(arrow[0], arrow[1]);
3722 }
else if (a > 0 && a < 45) {
3723 p->setPen(pal.light().color());
3724 p->drawLine(arrow[2], arrow[0]);
3725 p->setPen(pal.dark().color());
3726 p->drawLine(arrow[1], arrow[2]);
3727 p->drawLine(arrow[0], arrow[1]);
3728 }
else if (a >= 45 && a < 135) {
3729 p->setPen(pal.dark().color());
3730 p->drawLine(arrow[2], arrow[0]);
3731 p->drawLine(arrow[1], arrow[2]);
3732 p->setPen(pal.light().color());
3733 p->drawLine(arrow[0], arrow[1]);
3734 }
else if (a >= 135 && a < 200) {
3735 p->setPen(pal.dark().color());
3736 p->drawLine(arrow[2], arrow[0]);
3737 p->setPen(pal.light().color());
3738 p->drawLine(arrow[0], arrow[1]);
3739 p->drawLine(arrow[1], arrow[2]);
3743 QStyleOptionFocusRect fropt;
3744 fropt.rect = dial->rect;
3745 fropt.state = dial->state;
3746 fropt.palette = dial->palette;
3747 if (fropt.state & QStyle::State_HasFocus) {
3748 br.adjust(0, 0, 2, 2);
3749 if (dial->subControls & SC_DialTickmarks) {
3750 int r = qMin(width, height) / 2;
3751 br.translate(-r / 6, - r / 6);
3752 br.setWidth(br.width() + r / 3);
3753 br.setHeight(br.height() + r / 3);
3755 fropt.rect = br.adjusted(-2, -2, 2, 2);
3756 proxy()->drawPrimitive(QStyle::PE_FrameFocusRect, &fropt, p, widget);
3761#if QT_CONFIG(groupbox)
3763 if (
const QStyleOptionGroupBox *groupBox = qstyleoption_cast<
const QStyleOptionGroupBox *>(opt)) {
3765 QRect textRect = proxy()->subControlRect(CC_GroupBox, opt, SC_GroupBoxLabel, widget);
3766 QRect checkBoxRect = proxy()->subControlRect(CC_GroupBox, opt, SC_GroupBoxCheckBox, widget);
3767 if (groupBox->subControls & QStyle::SC_GroupBoxFrame) {
3768 QStyleOptionFrame frame;
3769 frame.QStyleOption::operator=(*groupBox);
3770 frame.features = groupBox->features;
3771 frame.lineWidth = groupBox->lineWidth;
3772 frame.midLineWidth = groupBox->midLineWidth;
3773 frame.rect = proxy()->subControlRect(CC_GroupBox, opt, SC_GroupBoxFrame, widget);
3774 QPainterStateGuard psg(p);
3775 QRegion region(groupBox->rect);
3776 if (!groupBox->text.isEmpty()) {
3777 bool ltr = groupBox->direction == Qt::LeftToRight;
3779 if (groupBox->subControls & QStyle::SC_GroupBoxCheckBox) {
3780 finalRect = checkBoxRect.united(textRect);
3781 finalRect.adjust(ltr ? -4 : 0, 0, ltr ? 0 : 4, 0);
3783 finalRect = textRect;
3785 region -= finalRect;
3787 p->setClipRegion(region);
3788 proxy()->drawPrimitive(PE_FrameGroupBox, &frame, p, widget);
3792 if ((groupBox->subControls & QStyle::SC_GroupBoxLabel) && !groupBox->text.isEmpty()) {
3793 QColor textColor = groupBox->textColor;
3794 if (textColor.isValid())
3795 p->setPen(textColor);
3796 int alignment =
int(groupBox->textAlignment);
3797 if (!proxy()->styleHint(QStyle::SH_UnderlineShortcut, opt, widget))
3798 alignment |= Qt::TextHideMnemonic;
3800 proxy()->drawItemText(p, textRect, Qt::TextShowMnemonic | Qt::AlignHCenter | alignment,
3801 groupBox->palette, groupBox->state & State_Enabled, groupBox->text,
3802 textColor.isValid() ? QPalette::NoRole : QPalette::WindowText);
3804 if (groupBox->state & State_HasFocus) {
3805 QStyleOptionFocusRect fropt;
3806 fropt.QStyleOption::operator=(*groupBox);
3807 fropt.rect = textRect;
3808 proxy()->drawPrimitive(PE_FrameFocusRect, &fropt, p, widget);
3813 if (groupBox->subControls & SC_GroupBoxCheckBox) {
3814 QStyleOptionButton box;
3815 box.QStyleOption::operator=(*groupBox);
3816 box.rect = checkBoxRect;
3817 proxy()->drawPrimitive(PE_IndicatorCheckBox, &box, p, widget);
3822#if QT_CONFIG(mdiarea)
3823 case CC_MdiControls:
3825 QStyleOptionButton btnOpt;
3826 btnOpt.QStyleOption::operator=(*opt);
3827 btnOpt.state &= ~State_MouseOver;
3830 const int buttonIconMetric = proxy()->pixelMetric(PM_TitleBarButtonIconSize, &btnOpt, widget);
3831 const QSize buttonIconSize(buttonIconMetric, buttonIconMetric);
3832 if (opt->subControls & QStyle::SC_MdiCloseButton) {
3833 if (opt->activeSubControls & QStyle::SC_MdiCloseButton && (opt->state & State_Sunken)) {
3834 btnOpt.state |= State_Sunken;
3835 btnOpt.state &= ~State_Raised;
3836 bsx = proxy()->pixelMetric(PM_ButtonShiftHorizontal, opt, widget);
3837 bsy = proxy()->pixelMetric(PM_ButtonShiftVertical, opt, widget);
3839 btnOpt.state |= State_Raised;
3840 btnOpt.state &= ~State_Sunken;
3844 btnOpt.rect = proxy()->subControlRect(CC_MdiControls, opt, SC_MdiCloseButton, widget);
3845 proxy()->drawPrimitive(PE_PanelButtonCommand, &btnOpt, p, widget);
3846 QPixmap pm = proxy()->standardIcon(SP_TitleBarCloseButton).pixmap(buttonIconSize, QStyleHelper::getDpr(p));
3847 proxy()->drawItemPixmap(p, btnOpt.rect.translated(bsx, bsy), Qt::AlignCenter, pm);
3849 if (opt->subControls & QStyle::SC_MdiNormalButton) {
3850 if (opt->activeSubControls & QStyle::SC_MdiNormalButton && (opt->state & State_Sunken)) {
3851 btnOpt.state |= State_Sunken;
3852 btnOpt.state &= ~State_Raised;
3853 bsx = proxy()->pixelMetric(PM_ButtonShiftHorizontal, opt, widget);
3854 bsy = proxy()->pixelMetric(PM_ButtonShiftVertical, opt, widget);
3856 btnOpt.state |= State_Raised;
3857 btnOpt.state &= ~State_Sunken;
3861 btnOpt.rect = proxy()->subControlRect(CC_MdiControls, opt, SC_MdiNormalButton, widget);
3862 proxy()->drawPrimitive(PE_PanelButtonCommand, &btnOpt, p, widget);
3863 QPixmap pm = proxy()->standardIcon(SP_TitleBarNormalButton).pixmap(buttonIconSize, QStyleHelper::getDpr(p));
3864 proxy()->drawItemPixmap(p, btnOpt.rect.translated(bsx, bsy), Qt::AlignCenter, pm);
3866 if (opt->subControls & QStyle::SC_MdiMinButton) {
3867 if (opt->activeSubControls & QStyle::SC_MdiMinButton && (opt->state & State_Sunken)) {
3868 btnOpt.state |= State_Sunken;
3869 btnOpt.state &= ~State_Raised;
3870 bsx = proxy()->pixelMetric(PM_ButtonShiftHorizontal, opt, widget);
3871 bsy = proxy()->pixelMetric(PM_ButtonShiftVertical, opt, widget);
3873 btnOpt.state |= State_Raised;
3874 btnOpt.state &= ~State_Sunken;
3878 btnOpt.rect = proxy()->subControlRect(CC_MdiControls, opt, SC_MdiMinButton, widget);
3879 proxy()->drawPrimitive(PE_PanelButtonCommand, &btnOpt, p, widget);
3880 QPixmap pm = proxy()->standardIcon(SP_TitleBarMinButton).pixmap(buttonIconSize, QStyleHelper::getDpr(p));
3881 proxy()->drawItemPixmap(p, btnOpt.rect.translated(bsx, bsy), Qt::AlignCenter, pm);
3887 qCWarning(lcCommonStyle,
"QCommonStyle::drawComplexControl: Control %d not handled", cc);
4031QRect QCommonStyle::subControlRect(ComplexControl cc,
const QStyleOptionComplex *opt,
4032 SubControl sc,
const QWidget *widget)
const
4036#if QT_CONFIG(slider)
4038 if (
const QStyleOptionSlider *slider = qstyleoption_cast<
const QStyleOptionSlider *>(opt)) {
4039 int tickOffset = proxy()->pixelMetric(PM_SliderTickmarkOffset, slider, widget);
4040 int thickness = proxy()->pixelMetric(PM_SliderControlThickness, slider, widget);
4043 case SC_SliderHandle: {
4045 int len = proxy()->pixelMetric(PM_SliderLength, slider, widget);
4046 bool horizontal = slider->orientation == Qt::Horizontal;
4047 sliderPos = sliderPositionFromValue(slider->minimum, slider->maximum,
4048 slider->sliderPosition,
4049 (horizontal ? slider->rect.width()
4050 : slider->rect.height()) - len,
4051 slider->upsideDown);
4053 ret.setRect(slider->rect.x() + sliderPos, slider->rect.y() + tickOffset, len, thickness);
4055 ret.setRect(slider->rect.x() + tickOffset, slider->rect.y() + sliderPos, thickness, len);
4057 case SC_SliderGroove:
4058 if (slider->orientation == Qt::Horizontal)
4059 ret.setRect(slider->rect.x(), slider->rect.y() + tickOffset,
4060 slider->rect.width(), thickness);
4062 ret.setRect(slider->rect.x() + tickOffset, slider->rect.y(),
4063 thickness, slider->rect.height());
4068 ret = visualRect(slider->direction, slider->rect, ret);
4072#if QT_CONFIG(scrollbar)
4074 if (
const QStyleOptionSlider *scrollbar = qstyleoption_cast<
const QStyleOptionSlider *>(opt)) {
4075 const QRect scrollBarRect = scrollbar->rect;
4077 if (!proxy()->styleHint(SH_ScrollBar_Transient, scrollbar, widget))
4078 sbextent = proxy()->pixelMetric(PM_ScrollBarExtent, scrollbar, widget);
4079 int maxlen = ((scrollbar->orientation == Qt::Horizontal) ?
4080 scrollBarRect.width() : scrollBarRect.height()) - (sbextent * 2);
4084 if (scrollbar->maximum != scrollbar->minimum) {
4085 uint range = scrollbar->maximum - scrollbar->minimum;
4086 sliderlen = (qint64(scrollbar->pageStep) * maxlen) / (range + scrollbar->pageStep);
4088 int slidermin = proxy()->pixelMetric(PM_ScrollBarSliderMin, scrollbar, widget);
4089 if (sliderlen < slidermin || range > INT_MAX / 2)
4090 sliderlen = slidermin;
4091 if (sliderlen > maxlen)
4097 int sliderstart = sbextent + sliderPositionFromValue(scrollbar->minimum,
4099 scrollbar->sliderPosition,
4101 scrollbar->upsideDown);
4104 case SC_ScrollBarSubLine:
4105 if (scrollbar->orientation == Qt::Horizontal) {
4106 int buttonWidth = qMin(scrollBarRect.width() / 2, sbextent);
4107 ret.setRect(0, 0, buttonWidth, scrollBarRect.height());
4109 int buttonHeight = qMin(scrollBarRect.height() / 2, sbextent);
4110 ret.setRect(0, 0, scrollBarRect.width(), buttonHeight);
4113 case SC_ScrollBarAddLine:
4114 if (scrollbar->orientation == Qt::Horizontal) {
4115 int buttonWidth = qMin(scrollBarRect.width()/2, sbextent);
4116 ret.setRect(scrollBarRect.width() - buttonWidth, 0, buttonWidth, scrollBarRect.height());
4118 int buttonHeight = qMin(scrollBarRect.height()/2, sbextent);
4119 ret.setRect(0, scrollBarRect.height() - buttonHeight, scrollBarRect.width(), buttonHeight);
4122 case SC_ScrollBarSubPage:
4123 if (scrollbar->orientation == Qt::Horizontal)
4124 ret.setRect(sbextent, 0, sliderstart - sbextent, scrollBarRect.height());
4126 ret.setRect(0, sbextent, scrollBarRect.width(), sliderstart - sbextent);
4128 case SC_ScrollBarAddPage:
4129 if (scrollbar->orientation == Qt::Horizontal)
4130 ret.setRect(sliderstart + sliderlen, 0,
4131 maxlen - sliderstart - sliderlen + sbextent, scrollBarRect.height());
4133 ret.setRect(0, sliderstart + sliderlen, scrollBarRect.width(),
4134 maxlen - sliderstart - sliderlen + sbextent);
4136 case SC_ScrollBarGroove:
4137 if (scrollbar->orientation == Qt::Horizontal)
4138 ret.setRect(sbextent, 0, scrollBarRect.width() - sbextent * 2,
4139 scrollBarRect.height());
4141 ret.setRect(0, sbextent, scrollBarRect.width(),
4142 scrollBarRect.height() - sbextent * 2);
4144 case SC_ScrollBarSlider:
4145 if (scrollbar->orientation == Qt::Horizontal)
4146 ret.setRect(sliderstart, 0, sliderlen, scrollBarRect.height());
4148 ret.setRect(0, sliderstart, scrollBarRect.width(), sliderlen);
4153 ret = visualRect(scrollbar->direction, scrollBarRect, ret);
4157#if QT_CONFIG(spinbox)
4159 if (
const QStyleOptionSpinBox *spinbox = qstyleoption_cast<
const QStyleOptionSpinBox *>(opt)) {
4161 int fw = spinbox->frame ? proxy()->pixelMetric(PM_SpinBoxFrameWidth, spinbox, widget) : 0;
4162 bs.setHeight(qMax(8, spinbox->rect.height()/2 - fw));
4164 bs.setWidth(qMax(16, qMin(bs.height() * 8 / 5, spinbox->rect.width() / 4)));
4165 int y = fw + spinbox->rect.y();
4167 x = spinbox->rect.x() + spinbox->rect.width() - fw - bs.width();
4172 if (spinbox->buttonSymbols == QAbstractSpinBox::NoButtons)
4174 ret = QRect(x, y, bs.width(), bs.height());
4176 case SC_SpinBoxDown:
4177 if (spinbox->buttonSymbols == QAbstractSpinBox::NoButtons)
4180 ret = QRect(x, y + bs.height(), bs.width(), bs.height());
4182 case SC_SpinBoxEditField:
4183 if (spinbox->buttonSymbols == QAbstractSpinBox::NoButtons) {
4184 ret = QRect(lx, fw, spinbox->rect.width() - 2*fw, spinbox->rect.height() - 2*fw);
4186 ret = QRect(lx, fw, rx, spinbox->rect.height() - 2*fw);
4189 case SC_SpinBoxFrame:
4190 ret = spinbox->rect;
4195 ret = visualRect(spinbox->direction, spinbox->rect, ret);
4199#if QT_CONFIG(toolbutton)
4201 if (
const QStyleOptionToolButton *tb = qstyleoption_cast<
const QStyleOptionToolButton *>(opt)) {
4205 if (tb->features.testFlag(QStyleOptionToolButton::MenuButtonPopup)) {
4206 const int mbi = proxy()->pixelMetric(PM_MenuButtonIndicator, tb, widget);
4207 ret.adjust(0, 0, -mbi, 0);
4210 case SC_ToolButtonMenu:
4211 if (tb->features.testFlag(QStyleOptionToolButton::MenuButtonPopup)) {
4212 const int mbi = proxy()->pixelMetric(PM_MenuButtonIndicator, tb, widget);
4213 ret.adjust(ret.width() - mbi, 0, 0, 0);
4219 ret = visualRect(tb->direction, tb->rect, ret);
4223#if QT_CONFIG(combobox)
4225 if (
const QStyleOptionComboBox *cb = qstyleoption_cast<
const QStyleOptionComboBox *>(opt)) {
4226 const qreal dpi = QStyleHelper::dpi(opt);
4227 const int x = cb->rect.x(), y = cb->rect.y(), wi = cb->rect.width(), he = cb->rect.height();
4228 const int margin = cb->frame ? qRound(QStyleHelper::dpiScaled(3, dpi)) : 0;
4229 const int bmarg = cb->frame ? qRound(QStyleHelper::dpiScaled(2, dpi)) : 0;
4230 const int xpos = x + wi - bmarg - qRound(QStyleHelper::dpiScaled(16, dpi));
4234 case SC_ComboBoxFrame:
4237 case SC_ComboBoxArrow:
4238 ret.setRect(xpos, y + bmarg, qRound(QStyleHelper::dpiScaled(16, opt)), he - 2*bmarg);
4240 case SC_ComboBoxEditField:
4241 ret.setRect(x + margin, y + margin, wi - 2 * margin - qRound(QStyleHelper::dpiScaled(16, dpi)), he - 2 * margin);
4243 case SC_ComboBoxListBoxPopup:
4249 ret = visualRect(cb->direction, cb->rect, ret);
4254 if (
const QStyleOptionTitleBar *tb = qstyleoption_cast<
const QStyleOptionTitleBar *>(opt)) {
4255 const int controlMargin = 2;
4256 const int controlHeight = tb->rect.height() - controlMargin *2;
4257 const int delta = controlHeight + controlMargin;
4260 bool isMinimized = tb->titleBarState & Qt::WindowMinimized;
4261 bool isMaximized = tb->titleBarState & Qt::WindowMaximized;
4264 case SC_TitleBarLabel:
4265 if (tb->titleBarFlags & (Qt::WindowTitleHint | Qt::WindowSystemMenuHint)) {
4267 if (tb->titleBarFlags & Qt::WindowSystemMenuHint)
4268 ret.adjust(delta, 0, -delta, 0);
4269 if (tb->titleBarFlags & Qt::WindowMinimizeButtonHint)
4270 ret.adjust(0, 0, -delta, 0);
4271 if (tb->titleBarFlags & Qt::WindowMaximizeButtonHint)
4272 ret.adjust(0, 0, -delta, 0);
4273 if (tb->titleBarFlags & Qt::WindowShadeButtonHint)
4274 ret.adjust(0, 0, -delta, 0);
4275 if (tb->titleBarFlags & Qt::WindowContextHelpButtonHint)
4276 ret.adjust(0, 0, -delta, 0);
4279 case SC_TitleBarContextHelpButton:
4280 if (tb->titleBarFlags & Qt::WindowContextHelpButtonHint)
4283 case SC_TitleBarMinButton:
4284 if (!isMinimized && (tb->titleBarFlags & Qt::WindowMinimizeButtonHint))
4286 else if (sc == SC_TitleBarMinButton)
4289 case SC_TitleBarNormalButton:
4290 if (isMinimized && (tb->titleBarFlags & Qt::WindowMinimizeButtonHint))
4292 else if (isMaximized && (tb->titleBarFlags & Qt::WindowMaximizeButtonHint))
4294 else if (sc == SC_TitleBarNormalButton)
4297 case SC_TitleBarMaxButton:
4298 if (!isMaximized && (tb->titleBarFlags & Qt::WindowMaximizeButtonHint))
4300 else if (sc == SC_TitleBarMaxButton)
4303 case SC_TitleBarShadeButton:
4304 if (!isMinimized && (tb->titleBarFlags & Qt::WindowShadeButtonHint))
4306 else if (sc == SC_TitleBarShadeButton)
4309 case SC_TitleBarUnshadeButton:
4310 if (isMinimized && (tb->titleBarFlags & Qt::WindowShadeButtonHint))
4312 else if (sc == SC_TitleBarUnshadeButton)
4315 case SC_TitleBarCloseButton:
4316 if (tb->titleBarFlags & Qt::WindowSystemMenuHint)
4318 else if (sc == SC_TitleBarCloseButton)
4320 ret.setRect(tb->rect.right() - offset, tb->rect.top() + controlMargin,
4321 controlHeight, controlHeight);
4323 case SC_TitleBarSysMenu:
4324 if (tb->titleBarFlags & Qt::WindowSystemMenuHint) {
4325 ret.setRect(tb->rect.left() + controlMargin, tb->rect.top() + controlMargin,
4326 controlHeight, controlHeight);
4332 ret = visualRect(tb->direction, tb->rect, ret);
4335#if QT_CONFIG(groupbox)
4337 if (
const QStyleOptionGroupBox *groupBox = qstyleoption_cast<
const QStyleOptionGroupBox *>(opt)) {
4339 case SC_GroupBoxFrame:
4340 case SC_GroupBoxContents: {
4343 int verticalAlignment = proxy()->styleHint(SH_GroupBox_TextLabelVerticalAlignment, groupBox, widget);
4344 bool hasCheckBox = groupBox->subControls & QStyle::SC_GroupBoxCheckBox;
4345 if (groupBox->text.size() || hasCheckBox) {
4346 int checkBoxHeight = hasCheckBox ? proxy()->pixelMetric(PM_IndicatorHeight, groupBox, widget) : 0;
4347 topHeight = qMax(groupBox->fontMetrics.height(), checkBoxHeight);
4348 if (verticalAlignment & Qt::AlignVCenter)
4349 topMargin = topHeight / 2;
4350 else if (verticalAlignment & Qt::AlignTop)
4351 topMargin = topHeight + proxy()->pixelMetric(PM_FocusFrameVMargin, groupBox, widget);
4354 QRect frameRect = groupBox->rect;
4355 frameRect.setTop(frameRect.top() + topMargin);
4357 if (sc == SC_GroupBoxFrame) {
4363 if ((groupBox->features & QStyleOptionFrame::Flat) == 0)
4364 frameWidth = proxy()->pixelMetric(PM_DefaultFrameWidth, groupBox, widget);
4365 ret = frameRect.adjusted(frameWidth, frameWidth + topHeight - topMargin,
4366 -frameWidth, -frameWidth);
4369 case SC_GroupBoxCheckBox:
4370 case SC_GroupBoxLabel: {
4371 QFontMetrics fontMetrics = groupBox->fontMetrics;
4372 int th = fontMetrics.height();
4373 int tw = fontMetrics.size(Qt::TextShowMnemonic, groupBox->text + u' ').width();
4374 int marg = (groupBox->features & QStyleOptionFrame::Flat) ? 0 : 8;
4375 ret = groupBox->rect.adjusted(marg, 0, -marg, 0);
4377 int indicatorWidth = proxy()->pixelMetric(PM_IndicatorWidth, opt, widget);
4378 int indicatorHeight = proxy()->pixelMetric(PM_IndicatorHeight, opt, widget);
4379 int indicatorSpace = proxy()->pixelMetric(PM_CheckBoxLabelSpacing, opt, widget) - 1;
4380 bool hasCheckBox = groupBox->subControls & QStyle::SC_GroupBoxCheckBox;
4381 int checkBoxWidth = hasCheckBox ? (indicatorWidth + indicatorSpace) : 0;
4382 int checkBoxHeight = hasCheckBox ? indicatorHeight : 0;
4384 int h = qMax(th, checkBoxHeight);
4388 QRect totalRect = alignedRect(groupBox->direction, groupBox->textAlignment,
4389 QSize(tw + checkBoxWidth, h), ret);
4393 bool ltr = groupBox->direction == Qt::LeftToRight;
4396 if (sc == SC_GroupBoxCheckBox) {
4397 left = ltr ? totalRect.left() : (totalRect.right() - indicatorWidth);
4398 int top = totalRect.top() + (h - checkBoxHeight) / 2;
4399 totalRect.setRect(left, top, indicatorWidth, indicatorHeight);
4402 left = ltr ? (totalRect.left() + checkBoxWidth - 2) : totalRect.left();
4403 int top = totalRect.top() + (h - th) / 2;
4404 totalRect.setRect(left, top, totalRect.width() - checkBoxWidth, th);
4417#if QT_CONFIG(mdiarea)
4418 case CC_MdiControls:
4420 int numSubControls = 0;
4421 if (opt->subControls & SC_MdiCloseButton)
4423 if (opt->subControls & SC_MdiMinButton)
4425 if (opt->subControls & SC_MdiNormalButton)
4427 if (numSubControls == 0)
4430 int buttonWidth = opt->rect.width() / numSubControls - 1;
4433 case SC_MdiCloseButton:
4435 if (numSubControls == 1)
4437 offset += buttonWidth + 2;
4439 case SC_MdiNormalButton:
4443 if (numSubControls == 1 || (numSubControls == 2 && !(opt->subControls & SC_MdiMinButton)))
4445 if (opt->subControls & SC_MdiNormalButton)
4446 offset += buttonWidth;
4455 if (numSubControls == 1)
4457 ret = QRect(offset, 0, buttonWidth, opt->rect.height());
4462 qCWarning(lcCommonStyle,
"QCommonStyle::subControlRect: Case %d not handled", cc);
4464#if !QT_CONFIG(slider) && !QT_CONFIG(spinbox) && !QT_CONFIG(toolbutton) && !QT_CONFIG(groupbox)
5845QIcon QCommonStylePrivate::iconFromResourceTheme(QCommonStyle::StandardPixmap standardIcon,
5846 const QStyleOption *option,
5847 const QWidget *widget)
const
5849 Q_Q(
const QCommonStyle);
5851#ifndef QT_NO_IMAGEFORMAT_PNG
5852 switch (standardIcon) {
5853 case QStyle::SP_MessageBoxInformation:
5854 addIconFiles(u"information-", pngIconSizes, icon);
5856 case QStyle::SP_MessageBoxWarning:
5857 addIconFiles(u"warning-", pngIconSizes, icon);
5859 case QStyle::SP_MessageBoxCritical:
5860 addIconFiles(u"critical-", pngIconSizes, icon);
5862 case QStyle::SP_MessageBoxQuestion:
5863 addIconFiles(u"question-", pngIconSizes, icon);
5865 case QStyle::SP_FileDialogStart:
5866 addIconFiles(u"filedialog_start-", pngIconSizes, icon);
5868 case QStyle::SP_FileDialogEnd:
5869 addIconFiles(u"filedialog_end-", pngIconSizes, icon);
5871 case QStyle::SP_TitleBarMinButton:
5872 addIconFiles(u"titlebar-min-", titleBarSizes, icon);
5874 case QStyle::SP_TitleBarMaxButton:
5875 addIconFiles(u"titlebar-max-", titleBarSizes, icon);
5877 case QStyle::SP_TitleBarShadeButton:
5878 addIconFiles(u"titlebar-shade-", titleBarSizes, icon);
5880 case QStyle::SP_TitleBarUnshadeButton:
5881 addIconFiles(u"titlebar-unshade-", titleBarSizes, icon);
5883 case QStyle::SP_TitleBarContextHelpButton:
5884 addIconFiles(u"titlebar-contexthelp-", titleBarSizes, icon);
5886 case QStyle::SP_FileDialogNewFolder:
5887 addIconFiles(u"newdirectory-", pngIconSizes, icon);
5889 case QStyle::SP_FileDialogBack:
5890 return q->proxy()->standardIcon(QStyle::SP_ArrowBack, option, widget);
5891 case QStyle::SP_FileDialogToParent:
5892 return q->proxy()->standardIcon(QStyle::SP_ArrowUp, option, widget);
5893 case QStyle::SP_FileDialogDetailedView:
5894 addIconFiles(u"viewdetailed-", pngIconSizes, icon);
5896 case QStyle::SP_FileDialogInfoView:
5897 addIconFiles(u"fileinfo-", pngIconSizes, icon);
5899 case QStyle::SP_FileDialogContentsView:
5900 addIconFiles(u"filecontents-", pngIconSizes, icon);
5902 case QStyle::SP_FileDialogListView:
5903 addIconFiles(u"viewlist-", pngIconSizes, icon);
5905 case QStyle::SP_DialogOkButton:
5906 addIconFiles(u"standardbutton-ok-", pngIconSizes, icon);
5908 case QStyle::SP_DialogCancelButton:
5909 addIconFiles(u"standardbutton-cancel-", pngIconSizes, icon);
5911 case QStyle::SP_DialogHelpButton:
5912 addIconFiles(u"standardbutton-help-", pngIconSizes, icon);
5914 case QStyle::SP_DialogOpenButton:
5915 addIconFiles(u"standardbutton-open-", pngIconSizes, icon);
5917 case QStyle::SP_DialogSaveButton:
5918 addIconFiles(u"standardbutton-save-", pngIconSizes, icon);
5920 case QStyle::SP_DialogCloseButton:
5921 addIconFiles(u"standardbutton-close-", pngIconSizes, icon);
5923 case QStyle::SP_DialogApplyButton:
5924 addIconFiles(u"standardbutton-apply-", pngIconSizes, icon);
5926 case QStyle::SP_DialogResetButton:
5927 addIconFiles(u"standardbutton-clear-", pngIconSizes, icon);
5929 case QStyle::SP_DialogDiscardButton:
5930 addIconFiles(u"standardbutton-delete-", pngIconSizes, icon);
5932 case QStyle::SP_DialogYesButton:
5933 addIconFiles(u"standardbutton-yes-", pngIconSizes, icon);
5935 case QStyle::SP_DialogNoButton:
5936 addIconFiles(u"standardbutton-no-", pngIconSizes, icon);
5938 case QStyle::SP_CommandLink:
5939 case QStyle::SP_ArrowForward:
5940 return q->proxy()->standardIcon(rtl(option) ? QStyle::SP_ArrowLeft
5941 : QStyle::SP_ArrowRight,
5943 case QStyle::SP_ArrowBack:
5944 return q->proxy()->standardIcon(rtl(option) ? QStyle::SP_ArrowRight
5945 : QStyle::SP_ArrowLeft,
5947 case QStyle::SP_ArrowLeft:
5948 addIconFiles(u"arrow-left-", pngIconSizes, icon);
5950 case QStyle::SP_ArrowRight:
5951 addIconFiles(u"arrow-right-", pngIconSizes, icon);
5953 case QStyle::SP_ArrowUp:
5954 addIconFiles(u"arrow-up-", pngIconSizes, icon);
5956 case QStyle::SP_ArrowDown:
5957 addIconFiles(u"arrow-down-", pngIconSizes, icon);
5959 case QStyle::SP_DirHomeIcon:
5960 case QStyle::SP_DirIcon:
5961 addIconFiles(u"dirclosed-", pngIconSizes, icon, QIcon::Normal, QIcon::Off);
5962 addIconFiles(u"diropen-", pngIconSizes, icon, QIcon::Normal, QIcon::On);
5964 case QStyle::SP_DirOpenIcon:
5965 addIconFiles(u"diropen-", pngIconSizes, icon);
5967 case QStyle::SP_DirClosedIcon:
5968 addIconFiles(u"dirclosed-", pngIconSizes, icon);
5970 case QStyle::SP_DirLinkIcon:
5971 addIconFiles(u"dirlink-", pngIconSizes, icon);
5973 case QStyle::SP_DriveCDIcon:
5974 addIconFiles(u"cdr-", pngIconSizes, icon);
5976 case QStyle::SP_DriveFDIcon:
5977 addIconFiles(u"floppy-", pngIconSizes, icon);
5979 case QStyle::SP_DriveHDIcon:
5980 addIconFiles(u"harddrive-", pngIconSizes, icon);
5982 case QStyle::SP_DriveDVDIcon:
5983 addIconFiles(u"dvd-", pngIconSizes, icon);
5985 case QStyle::SP_DriveNetIcon:
5986 addIconFiles(u"networkdrive-", pngIconSizes, icon);
5988 case QStyle::SP_FileIcon:
5989 addIconFiles(u"file-", pngIconSizes, icon);
5991 case QStyle::SP_FileLinkIcon:
5992 addIconFiles(u"filelink-", pngIconSizes, icon);
5994 case QStyle::SP_DesktopIcon:
5995 addIconFiles(u"desktop-", {16, 32}, icon);
5997 case QStyle::SP_TrashIcon:
5998 addIconFiles(u"trash-", pngIconSizes, icon);
6000 case QStyle::SP_ComputerIcon:
6001 addIconFiles(u"computer-", {16, 32}, icon);
6003 case QStyle::SP_BrowserReload:
6004 addIconFiles(u"refresh-", {24, 32}, icon);
6006 case QStyle::SP_BrowserStop:
6007 addIconFiles(u"stop-", {24, 32}, icon);
6009 case QStyle::SP_MediaPlay:
6010 addIconFiles(u"media-play-", pngIconSizes, icon);
6012 case QStyle::SP_MediaPause:
6013 addIconFiles(u"media-pause-", pngIconSizes, icon);
6015 case QStyle::SP_MediaStop:
6016 addIconFiles(u"media-stop-", pngIconSizes, icon);
6018 case QStyle::SP_MediaSeekForward:
6019 addIconFiles(u"media-seek-forward-", pngIconSizes, icon);
6021 case QStyle::SP_MediaSeekBackward:
6022 addIconFiles(u"media-seek-backward-", pngIconSizes, icon);
6024 case QStyle::SP_MediaSkipForward:
6025 addIconFiles(u"media-skip-forward-", pngIconSizes, icon);
6027 case QStyle::SP_MediaSkipBackward:
6028 addIconFiles(u"media-skip-backward-", pngIconSizes, icon);
6030 case QStyle::SP_MediaVolume:
6031 addIconFiles(u"media-volume-", pngIconSizes, icon);
6033 case QStyle::SP_MediaVolumeMuted:
6034 addIconFiles(u"media-volume-muted-", pngIconSizes, icon);
6036 case QStyle::SP_TitleBarCloseButton:
6037 case QStyle::SP_DockWidgetCloseButton:
6038 addIconFiles(u"closedock-", dockTitleIconSizes, icon);
6040 case QStyle::SP_TitleBarMenuButton:
6041# ifndef QT_NO_IMAGEFORMAT_XPM
6042 icon.addPixmap(titleBarMenuCachedPixmapFromXPM());
6044 icon.addFile(
":/qt-project.org/qmessagebox/images/qtlogo-64.png"_L1);
6046 case QStyle::SP_TitleBarNormalButton:
6047 addIconFiles(u"normalizedockup-", dockTitleIconSizes, icon);
6049 case QStyle::SP_ToolBarHorizontalExtensionButton:
6050 addIconFiles(rtl(option) ? u"toolbar-ext-h-rtl-"_sv : u"toolbar-ext-h-"_sv, toolBarExtHSizes, icon);
6052 case QStyle::SP_ToolBarVerticalExtensionButton:
6053 addIconFiles(u"toolbar-ext-v-", toolBarExtVSizes, icon);
6055 case QStyle::SP_TabCloseButton:
6056 addIconFiles(u"standardbutton-closetab-", pngIconSizes, icon, QIcon::Normal, QIcon::Off);
6057 addIconFiles(u"standardbutton-closetab-down-", pngIconSizes, icon, QIcon::Normal, QIcon::On);
6058 addIconFiles(u"standardbutton-closetab-hover-", pngIconSizes, icon, QIcon::Active, QIcon::Off);
6060 case QStyle::SP_LineEditClearButton:
6061 addIconFiles(u"cleartext-", pngIconSizes, icon);
6067 Q_UNUSED(standardIcon);