700 qreal additionalDevicePixelRatio,
701 qreal correctionFactor)
704 QRectF rectF = scaleRect(QRectF(themeData.rect), additionalDevicePixelRatio);
706 if ((themeData.rotate + 90) % 180 == 0) {
707 rectF = QRectF(0, 0, rectF.height(), rectF.width());
711 const bool hasCorrectionFactor = !qFuzzyCompare(correctionFactor, qreal(1));
712 QRect rect = rectF.toRect();
713 QRect drawRect = hasCorrectionFactor
714 ? QRectF(rectF.topLeft() / correctionFactor, rectF.size() / correctionFactor).toRect() : rect;
717 int w = rect.width();
718 int h = rect.height();
722 bool stateHasData =
true;
723 bool hasAlpha =
false;
724 bool partIsTransparent;
725 bool potentialInvalidAlpha;
727 QString pixmapCacheKey = QStringLiteral(
"$qt_xp_");
728 pixmapCacheKey.append(themeName(themeData.theme));
729 pixmapCacheKey.append(QLatin1Char(
'p'));
730 pixmapCacheKey.append(QString::number(partId));
731 pixmapCacheKey.append(QLatin1Char(
's'));
732 pixmapCacheKey.append(QString::number(stateId));
733 pixmapCacheKey.append(QLatin1Char(
's'));
734 pixmapCacheKey.append(themeData.noBorder ? QLatin1Char(
'0') : QLatin1Char(
'1'));
735 pixmapCacheKey.append(QLatin1Char(
'b'));
736 pixmapCacheKey.append(themeData.noContent ? QLatin1Char(
'0') : QLatin1Char(
'1'));
737 pixmapCacheKey.append(QString::number(w));
738 pixmapCacheKey.append(QLatin1Char(
'w'));
739 pixmapCacheKey.append(QString::number(h));
740 pixmapCacheKey.append(QLatin1Char(
'h'));
741 pixmapCacheKey.append(QString::number(additionalDevicePixelRatio));
742 pixmapCacheKey.append(QLatin1Char(
'd'));
743 if (hasCorrectionFactor) {
744 pixmapCacheKey.append(QLatin1Char(
'c'));
745 pixmapCacheKey.append(QString::number(correctionFactor));
748 QPixmap cachedPixmap;
752 bool haveCachedPixmap =
false;
760 haveCachedPixmap = QPixmapCache::find(pixmapCacheKey, &cachedPixmap);
764 ::snprintf(buf,
sizeof(buf),
"+ Pixmap(%3d, %3d) ]", w, h);
765 printf(
"---[ CACHED %s--------> Name(%-10s) Part(%d) State(%d)\n",
766 haveCachedPixmap ? buf :
"]-------------------",
767 qPrintable(themeData.name), themeData.partId, themeData.stateId);
771 BOOL tmt_borderonly =
false;
772 COLORREF tmt_transparentcolor = 0x0;
773 PROPERTYORIGIN proporigin = PO_NOTFOUND;
774 GetThemeBool(themeData.handle(), themeData.partId, themeData.stateId, TMT_BORDERONLY, &tmt_borderonly);
775 GetThemeColor(themeData.handle(), themeData.partId, themeData.stateId, TMT_TRANSPARENTCOLOR, &tmt_transparentcolor);
776 GetThemePropertyOrigin(themeData.handle(), themeData.partId, themeData.stateId, TMT_CAPTIONMARGINS, &proporigin);
780 potentialInvalidAlpha =
false;
781 GetThemePropertyOrigin(themeData.handle(), themeData.partId, themeData.stateId, TMT_GLYPHTYPE, &proporigin);
782 if (proporigin == PO_PART || proporigin == PO_STATE) {
783 int tmt_glyphtype = GT_NONE;
784 GetThemeEnumValue(themeData.handle(), themeData.partId, themeData.stateId, TMT_GLYPHTYPE, &tmt_glyphtype);
785 potentialInvalidAlpha = partIsTransparent && tmt_glyphtype == GT_IMAGEGLYPH;
789 printf(
"---[ NOT CACHED ]-----------------------> Name(%-10s) Part(%d) State(%d)\n",
790 qPrintable(themeData.name), themeData.partId, themeData.stateId);
791 printf(
"-->partIsTransparen = %d\n", partIsTransparent);
792 printf(
"-->potentialInvalidAlpha = %d\n", potentialInvalidAlpha);
793 showProperties(themeData);
796 bool wasAlphaSwapped =
false;
797 bool wasAlphaFixed =
false;
803 bool addBorderContentClipping =
false;
805 QRect area = drawRect;
806 if (themeData.noBorder || themeData.noContent) {
813 PROPERTYORIGIN origin = PO_NOTFOUND;
814 GetThemePropertyOrigin(themeData.handle(), themeData.partId, themeData.stateId, TMT_BORDERSIZE, &origin);
815 GetThemeInt(themeData.handle(), themeData.partId, themeData.stateId, TMT_BORDERSIZE, &borderSize);
816 borderSize *= additionalDevicePixelRatio;
819 if ((origin == PO_CLASS || origin == PO_PART || origin == PO_STATE) && borderSize > 0) {
820 if (themeData.noBorder) {
822 area = area.adjusted(-borderSize, -borderSize, borderSize, borderSize);
826 if (themeData.noContent) {
827 QRegion content = area.adjusted(borderSize, borderSize, -borderSize, -borderSize);
828 extraClip ^= content;
831 addBorderContentClipping = (themeData.noBorder | themeData.noContent);
835 if (!haveCachedPixmap) {
836 if (!buffer(drawRect.width(), drawRect.height()))
838 HDC dc = bufferHDC();
843 memset(bufferPixels, 0x00, bufferW * drawRect.height() * 4);
847 int dx = area.x() - drawRect.x();
848 int dy = area.y() - drawRect.y();
853 DTBGOPTS drawOptions;
854 drawOptions.dwSize =
sizeof(drawOptions);
855 drawOptions.rcClip = themeData.toRECT(rect);
856 drawOptions.dwFlags = DTBG_CLIPRECT
857 | (themeData.noBorder ? DTBG_OMITBORDER : 0)
858 | (themeData.noContent ? DTBG_OMITCONTENT : 0);
861 RECT wRect(themeData.toRECT(area));
862 DrawThemeBackgroundEx(themeData.handle(), dc, themeData
.partId, themeData
.stateId, &wRect, &drawOptions);
869 memset(
static_cast<
void *>(&data), 0,
sizeof(data));
871 alphaCache.insert(key, data);
874 hasAlpha = hasAlphaChannel(rect);
875 if (!hasAlpha && partIsTransparent)
876 potentialInvalidAlpha =
true;
877#if defined(DEBUG_XP_STYLE) && 1
878 dumpNativeDIB(drawRect.width(), drawRect.height());
883 if (potentialInvalidAlpha)
884 wasAlphaFixed = fixAlphaChannel(drawRect);
886 QImage::Format format;
887 if ((partIsTransparent && !wasAlphaSwapped) || (!partIsTransparent && hasAlpha)) {
888 format = QImage::Format_ARGB32_Premultiplied;
890 }
else if (wasAlphaSwapped) {
891 format = QImage::Format_ARGB32_Premultiplied;
894 format = QImage::Format_RGB32;
899 swapAlphaChannel(rect,
true);
902#if defined(DEBUG_XP_STYLE) && 1
903 printf(
"Image format is: %s\n", alphaType == RealAlpha ?
"Real Alpha" : alphaType == MaskAlpha ?
"Masked Alpha" :
"No Alpha");
905 img = QImage(bufferPixels, bufferW, bufferH, format);
906 if (hasCorrectionFactor)
907 img = img.scaled(w, h, Qt::KeepAspectRatio, Qt::SmoothTransformation);
908 img.setDevicePixelRatio(additionalDevicePixelRatio);
912 bool useRegion = partIsTransparent && !hasAlpha && !wasAlphaSwapped;
917 newRegion = region(themeData);
918 oldRegion = painter->clipRegion();
919 painter->setClipRegion(newRegion);
920#if defined(DEBUG_XP_STYLE) && 0
921 printf(
"Using region:\n");
922 for (
const QRect &r : newRegion)
923 printf(
" (%d, %d, %d, %d)\n", r.x(), r.y(), r.right(), r.bottom());
927 if (addBorderContentClipping)
928 painter->setClipRegion(scaleRegion(extraClip, 1.0 / additionalDevicePixelRatio), Qt::IntersectClip);
930 if (!themeData.mirrorHorizontally && !themeData.mirrorVertically && !themeData.rotate) {
931 if (!haveCachedPixmap)
932 painter->drawImage(themeData.rect, img, rect);
934 painter->drawPixmap(themeData.rect, cachedPixmap);
942 if (!haveCachedPixmap)
943 imgCopy = img.copy(rect);
945 imgCopy = cachedPixmap.toImage();
947 if (themeData.rotate) {
948 QTransform rotMatrix;
949 rotMatrix.rotate(themeData.rotate);
950 imgCopy = imgCopy.transformed(rotMatrix);
952 static constexpr Qt::Orientation none = Qt::Orientation(0);
953 const auto orientation = (themeData.mirrorHorizontally ? Qt::Horizontal : none)
954 | (themeData.mirrorVertically ? Qt::Vertical : none);
956 imgCopy.flip(orientation);
957 painter->drawImage(themeData.rect, imgCopy);
960 if (useRegion || addBorderContentClipping) {
961 if (oldRegion.isEmpty())
962 painter->setClipping(
false);
964 painter->setClipRegion(oldRegion);
968 if (!haveCachedPixmap && w && h) {
969 QPixmap pix = QPixmap::fromImage(img).copy(rect);
970 QPixmapCache::insert(pixmapCacheKey, pix);
972 printf(
"+++Adding pixmap to cache, size(%d, %d), wasAlphaSwapped(%d), wasAlphaFixed(%d), name(%s)\n",
973 w, h, wasAlphaSwapped, wasAlphaFixed, qPrintable(pixmapCacheKey));
979 memset(
static_cast<
void *>(&data), 0,
sizeof(data));
986 alphaCache.insert(key, data);
1126 QWindowsStyle::drawPrimitive(pe, option, p);
1130 int themeNumber = -1;
1133 QRect rect = option->rect;
1134 State flags = option->state;
1135 bool hMirrored =
false;
1136 bool vMirrored =
false;
1137 bool noBorder =
false;
1138 bool noContent =
false;
1143 case PE_FrameTabBarBase:
1144 if (
const QStyleOptionTabBarBase *tbb
1145 = qstyleoption_cast<
const QStyleOptionTabBarBase *>(option)) {
1147 switch (tbb->shape) {
1148 case QTabBar::RoundedNorth:
1149 p->setPen(QPen(tbb->palette.dark(), 0));
1150 p->drawLine(tbb->rect.topLeft(), tbb->rect.topRight());
1152 case QTabBar::RoundedWest:
1153 p->setPen(QPen(tbb->palette.dark(), 0));
1154 p->drawLine(tbb->rect.left(), tbb->rect.top(), tbb->rect.left(), tbb->rect.bottom());
1156 case QTabBar::RoundedSouth:
1157 p->setPen(QPen(tbb->palette.dark(), 0));
1158 p->drawLine(tbb->rect.left(), tbb->rect.top(),
1159 tbb->rect.right(), tbb->rect.top());
1161 case QTabBar::RoundedEast:
1162 p->setPen(QPen(tbb->palette.dark(), 0));
1163 p->drawLine(tbb->rect.topLeft(), tbb->rect.bottomLeft());
1165 case QTabBar::TriangularNorth:
1166 case QTabBar::TriangularEast:
1167 case QTabBar::TriangularWest:
1168 case QTabBar::TriangularSouth:
1170 QWindowsStyle::drawPrimitive(pe, option, p);
1177 case PE_PanelButtonBevel:
1178 themeNumber = QWindowsXPStylePrivate::ButtonTheme;
1179 partId = BP_PUSHBUTTON;
1180 if (!(flags & State_Enabled))
1181 stateId = PBS_DISABLED;
1182 else if ((flags & State_Sunken) || (flags & State_On))
1183 stateId = PBS_PRESSED;
1184 else if (flags & State_MouseOver)
1189 stateId = PBS_NORMAL;
1192 case PE_PanelButtonTool:
1198 themeNumber = QWindowsXPStylePrivate::ToolBarTheme;
1200 if (!(flags & State_Enabled))
1201 stateId = TS_DISABLED;
1202 else if (flags & State_Sunken)
1203 stateId = TS_PRESSED;
1204 else if (flags & State_MouseOver)
1205 stateId = flags & State_On ? TS_HOTCHECKED : TS_HOT;
1206 else if (flags & State_On)
1207 stateId = TS_CHECKED;
1208 else if (!(flags & State_AutoRaise))
1211 stateId = TS_NORMAL;
1214 case PE_IndicatorButtonDropDown:
1215 themeNumber = QWindowsXPStylePrivate::ToolBarTheme;
1216 partId = TP_SPLITBUTTONDROPDOWN;
1217 if (!(flags & State_Enabled))
1218 stateId = TS_DISABLED;
1219 else if (flags & State_Sunken)
1220 stateId = TS_PRESSED;
1221 else if (flags & State_MouseOver)
1222 stateId = flags & State_On ? TS_HOTCHECKED : TS_HOT;
1223 else if (flags & State_On)
1224 stateId = TS_CHECKED;
1225 else if (!(flags & State_AutoRaise))
1228 stateId = TS_NORMAL;
1229 if (option->direction == Qt::RightToLeft)
1233 case PE_IndicatorCheckBox:
1234 themeNumber = QWindowsXPStylePrivate::ButtonTheme;
1235 partId = BP_CHECKBOX;
1236 if (!(flags & State_Enabled))
1237 stateId = CBS_UNCHECKEDDISABLED;
1238 else if (flags & State_Sunken)
1239 stateId = CBS_UNCHECKEDPRESSED;
1240 else if (flags & State_MouseOver)
1241 stateId = CBS_UNCHECKEDHOT;
1243 stateId = CBS_UNCHECKEDNORMAL;
1245 if (flags & State_On)
1246 stateId += CBS_CHECKEDNORMAL-1;
1247 else if (flags & State_NoChange)
1248 stateId += CBS_MIXEDNORMAL-1;
1252 case PE_IndicatorRadioButton:
1253 themeNumber = QWindowsXPStylePrivate::ButtonTheme;
1254 partId = BP_RADIOBUTTON;
1255 if (!(flags & State_Enabled))
1256 stateId = RBS_UNCHECKEDDISABLED;
1257 else if (flags & State_Sunken)
1258 stateId = RBS_UNCHECKEDPRESSED;
1259 else if (flags & State_MouseOver)
1260 stateId = RBS_UNCHECKEDHOT;
1262 stateId = RBS_UNCHECKEDNORMAL;
1264 if (flags & State_On)
1265 stateId += RBS_CHECKEDNORMAL-1;
1268 case PE_IndicatorDockWidgetResizeHandle:
1273 if (flags & State_Raised)
1275 themeNumber = QWindowsXPStylePrivate::ListViewTheme;
1276 partId = LVP_LISTGROUP;
1277 XPThemeData theme(option->window,
nullptr, themeNumber, partId);
1279 if (!(flags & State_Enabled))
1280 stateId = ETS_DISABLED;
1282 stateId = ETS_NORMAL;
1284 if (GetThemeEnumValue(theme.handle(), partId, stateId, TMT_BGTYPE, &fillType) == S_OK) {
1285 if (fillType == BT_BORDERFILL) {
1287 GetThemeColor(theme.handle(), partId, stateId, TMT_BORDERCOLOR, &bcRef);
1288 QColor bordercolor(qRgb(GetRValue(bcRef), GetGValue(bcRef), GetBValue(bcRef)));
1289 QPen oldPen = p->pen();
1294 p->setPen(QPen(option->palette.base().color(), 0));
1295 const qreal dpi = QStyleHelper::dpi(option);
1296 const auto topLevelAdjustment = QStyleHelper::dpiScaled(0.5, dpi);
1297 const auto bottomRightAdjustment = QStyleHelper::dpiScaled(-1, dpi);
1298 p->drawRect(QRectF(option->rect).adjusted(topLevelAdjustment, topLevelAdjustment,
1299 bottomRightAdjustment, bottomRightAdjustment));
1301 p->setPen(QPen(bordercolor, 0));
1302 p->drawRect(QRectF(option->rect).adjusted(0, 0, -topLevelAdjustment, -topLevelAdjustment));
1306 if (fillType == BT_NONE)
1311 case PE_FrameLineEdit: {
1314
1315
1316
1317
1318
1319
1320
1321
1322
1323
1324
1325
1326 if (qstyleoption_cast<
const QStyleOptionFrame *>(option)) {
1327 themeNumber = QWindowsXPStylePrivate::EditTheme;
1328 partId = EP_EDITTEXT;
1330 if (!(flags & State_Enabled))
1331 stateId = ETS_DISABLED;
1333 stateId = ETS_NORMAL;
1338 case PE_PanelLineEdit:
1339 if (
const QStyleOptionFrame *panel = qstyleoption_cast<
const QStyleOptionFrame *>(option)) {
1340 themeNumber = QWindowsXPStylePrivate::EditTheme;
1341 partId = EP_EDITTEXT;
1343 bool isEnabled = flags & State_Enabled;
1345 stateId = isEnabled ? ETS_NORMAL : ETS_DISABLED;
1348
1349{
1350 XPThemeData theme(
nullptr, p, themeNumber, partId, stateId, rect);
1352 QWindowsStyle::drawPrimitive(pe, option, p);
1356 GetThemeEnumValue(theme.handle(), partId, stateId, TMT_BGTYPE, &bgType);
1357 if ( bgType == BT_IMAGEFILE ) {
1358 theme.mirrorHorizontally = hMirrored;
1359 theme.mirrorVertically = vMirrored;
1360 theme.noBorder = noBorder;
1361 theme.noContent = noContent;
1362 theme.rotate = rotate;
1363 d->drawBackground(theme);
1365 QBrush fillColor = option->palette.brush(QPalette::Base);
1368 PROPERTYORIGIN origin = PO_NOTFOUND;
1369 GetThemePropertyOrigin(theme.handle(), theme.partId, theme.stateId, TMT_FILLCOLOR, &origin);
1371 if ((origin == PO_PART || origin == PO_STATE)) {
1373 GetThemeColor(theme.handle(), partId, stateId, TMT_FILLCOLOR, &bgRef);
1374 fillColor = QBrush(qRgb(GetRValue(bgRef), GetGValue(bgRef), GetBValue(bgRef)));
1377 p->fillRect(option->rect, fillColor);
1381 if (panel->lineWidth > 0)
1382 proxy()->drawPrimitive(PE_FrameLineEdit, panel, p);
1387 case PE_FrameTabWidget:
1388 if (
const QStyleOptionTabWidgetFrame *tab = qstyleoption_cast<
const QStyleOptionTabWidgetFrame *>(option))
1390 themeNumber = QWindowsXPStylePrivate::TabTheme;
1393 if (option->window) {
1394 bool useGradient =
true;
1395 const int maxlength = 256;
1396 wchar_t themeFileName[maxlength];
1397 wchar_t themeColor[maxlength];
1399 if (GetCurrentThemeName(themeFileName, maxlength, themeColor, maxlength,
nullptr, 0) == S_OK) {
1400 wchar_t *offset =
nullptr;
1401 if ((offset = wcsrchr(themeFileName, QChar(QLatin1Char(
'\\')).unicode())) !=
nullptr) {
1403 if (!lstrcmp(offset, L"Luna.msstyles") && !lstrcmp(offset, L"Metallic")) {
1404 useGradient =
false;
1411 QStyleOptionTabWidgetFrame frameOpt = *tab;
1414 QRect contentsRect = subElementRect(SE_TabWidgetTabContents, &frameOpt);
1415 QRegion reg = option->rect;
1416 reg -= contentsRect;
1417 p->setClipRegion(reg);
1418 XPThemeData theme(option->window, p, themeNumber, partId, stateId, rect);
1419 theme.mirrorHorizontally = hMirrored;
1420 theme.mirrorVertically = vMirrored;
1421 d->drawBackground(theme);
1422 p->setClipRect(contentsRect);
1426 switch (tab->shape) {
1427 case QTabBar::RoundedNorth:
1428 case QTabBar::TriangularNorth:
1430 case QTabBar::RoundedSouth:
1431 case QTabBar::TriangularSouth:
1434 case QTabBar::RoundedEast:
1435 case QTabBar::TriangularEast:
1438 case QTabBar::RoundedWest:
1439 case QTabBar::TriangularWest:
1451 p->setPen(option->palette.dark().color());
1452 p->drawRect(rect.adjusted(0, 0, -1, -1));
1456 case PE_PanelMenuBar:
1459 case PE_FrameDockWidget:
1460 if (
const QStyleOptionFrame *frm = qstyleoption_cast<
const QStyleOptionFrame *>(option))
1462 themeNumber = QWindowsXPStylePrivate::WindowTheme;
1463 if (flags & State_Active)
1464 stateId = FS_ACTIVE;
1466 stateId = FS_INACTIVE;
1468 int fwidth = proxy()->pixelMetric(PM_DockWidgetFrameWidth, frm);
1470 XPThemeData theme(option->window, p, themeNumber, 0, stateId);
1473 theme.rect = QRect(frm->rect.x(), frm->rect.y(), frm->rect.x()+fwidth, frm->rect.height()-fwidth); theme.partId = WP_SMALLFRAMELEFT;
1474 d->drawBackground(theme);
1475 theme.rect = QRect(frm->rect.width()-fwidth, frm->rect.y(), fwidth, frm->rect.height()-fwidth);
1476 theme.partId = WP_SMALLFRAMERIGHT;
1477 d->drawBackground(theme);
1478 theme.rect = QRect(frm->rect.x(), frm->rect.bottom()-fwidth+1, frm->rect.width(), fwidth);
1479 theme.partId = WP_SMALLFRAMEBOTTOM;
1480 d->drawBackground(theme);
1485 case PE_IndicatorHeaderArrow:
1488 name = QWindowsXPStylePrivate::HeaderTheme;
1489 partId = HP_HEADERSORTARROW;
1490 if (flags & State_Down)
1491 stateId = HSAS_SORTEDDOWN;
1493 stateId = HSAS_SORTEDUP;
1497 p->setPen(option->palette.dark().color());
1498 p->translate(0, option->rect.height()/2 - 4);
1500 p->drawLine(option->rect.x(), option->rect.y(), option->rect.x()+8, option->rect.y());
1501 p->drawLine(option->rect.x()+1, option->rect.y()+1, option->rect.x()+7, option->rect.y()+1);
1502 p->drawLine(option->rect.x()+2, option->rect.y()+2, option->rect.x()+6, option->rect.y()+2);
1503 p->drawLine(option->rect.x()+3, option->rect.y()+3, option->rect.x()+5, option->rect.y()+3);
1504 p->drawPoint(option->rect.x()+4, option->rect.y()+4);
1506 p->drawLine(option->rect.x(), option->rect.y()+4, option->rect.x()+8, option->rect.y()+4);
1507 p->drawLine(option->rect.x()+1, option->rect.y()+3, option->rect.x()+7, option->rect.y()+3);
1508 p->drawLine(option->rect.x()+2, option->rect.y()+2, option->rect.x()+6, option->rect.y()+2);
1509 p->drawLine(option->rect.x()+3, option->rect.y()+1, option->rect.x()+5, option->rect.y()+1);
1510 p->drawPoint(option->rect.x()+4, option->rect.y());
1519 case PE_FrameStatusBarItem:
1520 themeNumber = QWindowsXPStylePrivate::StatusTheme;
1524 case PE_FrameGroupBox:
1525 themeNumber = QWindowsXPStylePrivate::ButtonTheme;
1526 partId = BP_GROUPBOX;
1527 if (!(flags & State_Enabled))
1528 stateId = GBS_DISABLED;
1530 stateId = GBS_NORMAL;
1531 if (
const QStyleOptionFrame *frame = qstyleoption_cast<
const QStyleOptionFrame *>(option)) {
1532 if (frame->features & QStyleOptionFrame::Flat) {
1534 QRect fr = frame->rect;
1535 QPoint p1(fr.x(), fr.y() + 1);
1536 QPoint p2(fr.x() + fr.width(), p1.y() + 1);
1537 rect = QRect(p1, p2);
1543 case PE_IndicatorProgressChunk:
1545 Qt::Orientation orient = Qt::Horizontal;
1546 bool inverted =
false;
1548 orient = pb->state & QStyle::State_Horizontal ? Qt::Horizontal : Qt::Vertical;
1551 if (orient == Qt::Horizontal) {
1553 rect = QRect(option->rect.x(), option->rect.y(), option->rect.width(), option->rect.height() );
1554 if (inverted && option->direction == Qt::LeftToRight)
1557 partId = PP_CHUNKVERT;
1558 rect = QRect(option->rect.x(), option->rect.y(), option->rect.width(), option->rect.height());
1560 themeNumber = QWindowsXPStylePrivate::ProgressTheme;
1565 case PE_FrameWindow:
1566 if (
const QStyleOptionFrame *frm = qstyleoption_cast<
const QStyleOptionFrame *>(option))
1568 themeNumber = QWindowsXPStylePrivate::WindowTheme;
1569 if (flags & State_Active)
1570 stateId = FS_ACTIVE;
1572 stateId = FS_INACTIVE;
1574 int fwidth =
int((frm->lineWidth + frm->midLineWidth) / QWindowsStylePrivate::nativeMetricScaleFactor(option));
1576 XPThemeData theme(option->window, p, themeNumber, 0, stateId);
1581 theme.rect = QRect(option->rect.x(), option->rect.y()+fwidth, option->rect.x()+fwidth, option->rect.height()-fwidth);
1582 theme.partId = WP_FRAMELEFT;
1583 if (!d->drawBackground(theme)) {
1584 QWindowsStyle::drawPrimitive(pe, option, p);
1587 theme.rect = QRect(option->rect.width()-fwidth, option->rect.y()+fwidth, fwidth, option->rect.height()-fwidth);
1588 theme.partId = WP_FRAMERIGHT;
1589 if (!d->drawBackground(theme)) {
1590 QWindowsStyle::drawPrimitive(pe, option, p);
1593 theme.rect = QRect(option->rect.x(), option->rect.height()-fwidth, option->rect.width(), fwidth);
1594 theme.partId = WP_FRAMEBOTTOM;
1595 if (!d->drawBackground(theme)) {
1596 QWindowsStyle::drawPrimitive(pe, option, p);
1599 theme.rect = QRect(option->rect.x(), option->rect.y(), option->rect.width(), option->rect.y()+fwidth);
1600 theme.partId = WP_CAPTION;
1601 if (!d->drawBackground(theme))
1602 QWindowsStyle::drawPrimitive(pe, option, p);
1607 case PE_IndicatorBranch:
1609 static const int decoration_size = 9;
1610 int mid_h = option->rect.x() + option->rect.width() / 2;
1611 int mid_v = option->rect.y() + option->rect.height() / 2;
1616 QBrush brush(option->palette.dark().color(), Qt::Dense4Pattern);
1618 if (option->direction == Qt::RightToLeft)
1619 p->fillRect(option->rect.left(), mid_v, bef_h - option->rect.left(), 1, brush);
1621 p->fillRect(aft_h, mid_v, option->rect.right() - aft_h + 1, 1, brush);
1624 p->fillRect(mid_h, aft_v, 1, option->rect.bottom() - aft_v + 1, brush);
1626 p->fillRect(mid_h, option->rect.y(), 1, bef_v - option->rect.y(), brush);
1628 int delta = decoration_size / 2;
1633 XPThemeData theme(
nullptr, p, QWindowsXPStylePrivate::XpTreeViewTheme);
1634 theme.rect = QRect(bef_h, bef_v, decoration_size, decoration_size);
1635 theme.partId = TVP_GLYPH;
1636 theme.stateId = flags & QStyle::State_Open ? GLPS_OPENED : GLPS_CLOSED;
1637 d->drawBackground(theme);
1642 case PE_IndicatorToolBarSeparator:
1643 if (option->rect.height() < 3) {
1646 QWindowsStyle::drawPrimitive(pe, option, p);
1649 themeNumber = QWindowsXPStylePrivate::ToolBarTheme;
1650 partId = TP_SEPARATOR;
1652 if (option->state & State_Horizontal)
1653 partId = TP_SEPARATOR;
1655 partId = TP_SEPARATORVERT;
1659 case PE_IndicatorToolBarHandle:
1661 themeNumber = QWindowsXPStylePrivate::RebarTheme;
1662 partId = RP_GRIPPER;
1664 partId = RP_GRIPPER;
1665 rect.adjust(0, 0, -2, 0);
1668 partId = RP_GRIPPERVERT;
1669 rect.adjust(0, 0, 0, -2);
1673 case PE_IndicatorItemViewItemCheck: {
1677 proxy()->drawPrimitive(PE_IndicatorCheckBox, &button, p);
1685 XPThemeData theme(option->window, p, themeNumber, partId, stateId, rect);
1687 QWindowsStyle::drawPrimitive(pe, option, p);
1690 theme.mirrorHorizontally = hMirrored;
1691 theme.mirrorVertically = vMirrored;
1692 theme.noBorder = noBorder;
1693 theme.noContent = noContent;
1694 theme.rotate = rotate;
1695 d->drawBackground(theme);
1705 QWindowsStyle::drawControl(element, option, p);
1709 QRect rect(option->rect);
1710 State flags = option->state;
1713 bool hMirrored =
false;
1714 bool vMirrored =
false;
1716 int themeNumber = -1;
1722 themeNumber = QWindowsXPStylePrivate::StatusTheme;
1723 partId = SP_GRIPPER;
1724 XPThemeData theme(
nullptr, p, themeNumber, partId);
1725 QSize size = (theme.size() * QWindowsStylePrivate::nativeMetricScaleFactor(option)).toSize();
1728 switch (sg->corner) {
1729 case Qt::BottomRightCorner:
1730 rect = QRect(
QPoint(rect.right() - size.width(), rect.bottom() - size.height()), size);
1732 case Qt::BottomLeftCorner:
1733 rect = QRect(
QPoint(rect.left() + 1, rect.bottom() - size.height()), size);
1736 case Qt::TopRightCorner:
1737 rect = QRect(
QPoint(rect.right() - size.width(), rect.top() + 1), size);
1740 case Qt::TopLeftCorner:
1741 rect = QRect(rect.topLeft() + QPoint(1, 1), size);
1742 hMirrored = vMirrored =
true;
1748 case CE_HeaderSection:
1749 themeNumber = QWindowsXPStylePrivate::HeaderTheme;
1750 partId = HP_HEADERITEM;
1751 if (flags & State_Sunken)
1752 stateId = HIS_PRESSED;
1753 else if (flags & State_MouseOver)
1756 stateId = HIS_NORMAL;
1760 p->eraseRect(option->rect);
1763 case CE_PushButtonBevel:
1766 themeNumber = QWindowsXPStylePrivate::ButtonTheme;
1767 partId = BP_PUSHBUTTON;
1768 bool justFlat = ((btn->features & QStyleOptionButton::Flat) && !(flags & (State_On|State_Sunken)))
1769 || ((btn->features & QStyleOptionButton::CommandLinkButton)
1770 && !(flags & State_MouseOver)
1771 && !(btn->features & QStyleOptionButton::DefaultButton));
1772 if (!(flags & State_Enabled) && !(btn->features & QStyleOptionButton::Flat))
1773 stateId = PBS_DISABLED;
1776 else if (flags & (State_Sunken | State_On))
1777 stateId = PBS_PRESSED;
1778 else if (flags & State_MouseOver)
1780 else if (btn->features & QStyleOptionButton::DefaultButton)
1781 stateId = PBS_DEFAULTED;
1783 stateId = PBS_NORMAL;
1786 XPThemeData theme(option->window, p, themeNumber, partId, stateId, rect);
1787 d->drawBackground(theme);
1791 int mbiw = 0, mbih = 0;
1793 QWindowsXPStylePrivate::ToolBarTheme,
1794 TP_SPLITBUTTONDROPDOWN);
1796 const QSize size = (theme.size() * QWindowsStylePrivate::nativeMetricScaleFactor(option)).toSize();
1797 mbiw = size.width();
1798 mbih = size.height();
1801 QRect ir = btn->rect;
1803 newBtn.rect = QRect(ir.right() - mbiw - 1, 1 + (ir.height()/2) - (mbih/2), mbiw, mbih);
1804 proxy()->drawPrimitive(PE_IndicatorArrowDown, &newBtn, p);
1810 if (
const QStyleOptionTab *tab = qstyleoption_cast<
const QStyleOptionTab *>(option))
1812 stateId = tab->state & State_Enabled ? TIS_NORMAL : TIS_DISABLED;
1816 case CE_TabBarTabShape:
1817 if (
const QStyleOptionTab *tab = qstyleoption_cast<
const QStyleOptionTab *>(option))
1819 themeNumber = QWindowsXPStylePrivate::TabTheme;
1820 bool isDisabled = !(tab->state & State_Enabled);
1821 bool hasFocus = tab->state & State_HasFocus;
1822 bool isHot = tab->state & State_MouseOver;
1823 bool selected = tab->state & State_Selected;
1824 bool lastTab = tab->position == QStyleOptionTab::End;
1825 bool firstTab = tab->position == QStyleOptionTab::Beginning;
1826 bool onlyOne = tab->position == QStyleOptionTab::OnlyOneTab;
1827 bool leftAligned = proxy()->styleHint(SH_TabBar_Alignment, tab) == Qt::AlignLeft;
1828 bool centerAligned = proxy()->styleHint(SH_TabBar_Alignment, tab) == Qt::AlignCenter;
1829 int borderThickness = proxy()->pixelMetric(PM_DefaultFrameWidth, option);
1830 int tabOverlap = proxy()->pixelMetric(PM_TabBarTabOverlap, option);
1833 stateId = TIS_DISABLED;
1835 stateId = TIS_SELECTED;
1837 stateId = TIS_FOCUSED;
1841 stateId = TIS_NORMAL;
1844 if (firstTab || onlyOne) {
1846 partId = TABP_TABITEMLEFTEDGE;
1847 }
else if (centerAligned) {
1848 partId = TABP_TABITEM;
1850 partId = TABP_TABITEMRIGHTEDGE;
1853 partId = TABP_TABITEM;
1856 if (tab->direction == Qt::RightToLeft
1857 && (tab->shape == QTabBar::RoundedNorth
1858 || tab->shape == QTabBar::RoundedSouth)) {
1859 bool temp = firstTab;
1863 bool begin = firstTab || onlyOne;
1864 bool end = lastTab || onlyOne;
1865 switch (tab->shape) {
1866 case QTabBar::RoundedNorth:
1868 rect.adjust(begin ? 0 : -tabOverlap, 0, end ? 0 : tabOverlap, borderThickness);
1870 rect.adjust(begin? tabOverlap : 0, tabOverlap, end ? -tabOverlap : 0, 0);
1872 case QTabBar::RoundedSouth:
1876 rect.adjust(begin ? 0 : -tabOverlap , -borderThickness, end ? 0 : tabOverlap, 0);
1878 rect.adjust(begin ? tabOverlap : 0, 0, end ? -tabOverlap : 0 , -tabOverlap);
1880 case QTabBar::RoundedEast:
1883 rect.adjust(-borderThickness, begin ? 0 : -tabOverlap, 0, end ? 0 : tabOverlap);
1885 rect.adjust(0, begin ? tabOverlap : 0, -tabOverlap, end ? -tabOverlap : 0);
1888 case QTabBar::RoundedWest:
1892 rect.adjust(0, begin ? 0 : -tabOverlap, borderThickness, end ? 0 : tabOverlap);
1894 rect.adjust(tabOverlap, begin ? tabOverlap : 0, 0, end ? -tabOverlap : 0);
1903 switch (tab->shape) {
1904 case QTabBar::RoundedNorth:
1905 rect.adjust(0,0, 0,-1);
1907 case QTabBar::RoundedSouth:
1908 rect.adjust(0,1, 0,0);
1910 case QTabBar::RoundedEast:
1911 rect.adjust( 1,0, 0,0);
1913 case QTabBar::RoundedWest:
1914 rect.adjust(0,0, -1,0);
1923 case CE_ProgressBarGroove:
1925 Qt::Orientation orient = Qt::Horizontal;
1926 if (
const QStyleOptionProgressBar *pb = qstyleoption_cast<
const QStyleOptionProgressBar *>(option))
1927 orient = pb->state & QStyle::State_Horizontal ? Qt::Horizontal : Qt::Vertical;
1928 partId = (orient == Qt::Horizontal) ? PP_BAR : PP_BARVERT;
1929 themeNumber = QWindowsXPStylePrivate::ProgressTheme;
1934 case CE_MenuEmptyArea:
1942 bool checked = checkable ? menuitem
->checked :
false;
1948 rect.getRect(&x, &y, &w, &h);
1950 QBrush fill = menuitem->palette.brush(act ? QPalette::Highlight : QPalette::Button);
1951 p->fillRect(rect, fill);
1953 if (element == CE_MenuEmptyArea)
1958 int yoff = y-1 + h / 2;
1959 p->setPen(menuitem->palette.dark().color());
1960 p->drawLine(x, yoff, x+w, yoff);
1962 p->setPen(menuitem->palette.light().color());
1963 p->drawLine(x, yoff, x+w, yoff);
1970 if (!menuitem->icon.isNull()) {
1971 QIcon::Mode mode = dis ? QIcon::Disabled : QIcon::Normal;
1973 mode = QIcon::Active;
1974 QPixmap pixmap = checked ?
1975 menuitem->icon.pixmap(proxy()->pixelMetric(PM_SmallIconSize, option), mode, QIcon::On) :
1976 menuitem->icon.pixmap(proxy()->pixelMetric(PM_SmallIconSize, option), mode);
1977 const int pixw = pixmap.width() / pixmap.devicePixelRatio();
1978 const int pixh = pixmap.height() / pixmap.devicePixelRatio();
1979 QRect iconRect(0, 0, pixw, pixh);
1980 iconRect.moveCenter(QRect(xpos, y, checkcol, h).center());
1981 QRect vIconRect = visualRect(option->direction, option->rect, iconRect);
1982 p->setPen(menuitem->palette.text().color());
1983 p->setBrush(Qt::NoBrush);
1985 p->drawRect(vIconRect.adjusted(-1, -1, 0, 0));
1986 p->drawPixmap(vIconRect.topLeft(), pixmap);
1989 }
else if (checked) {
1997 QRect checkMarkRect = QRect(menuitem->rect.x() + windowsItemFrame,
1998 menuitem->rect.y() + windowsItemFrame,
1999 checkcol - 2 * windowsItemFrame,
2000 menuitem->rect.height() - 2*windowsItemFrame);
2001 newMi.rect = visualRect(option->direction, option->rect, checkMarkRect);
2002 proxy()->drawPrimitive(PE_IndicatorMenuCheckMark, &newMi, p);
2005 QColor textColor = dis ? menuitem->palette.text().color() :
2006 act ? menuitem->palette.highlightedText().color() : menuitem->palette.buttonText().color();
2007 p->setPen(textColor);
2011 xpos = menuitem->rect.x() + xm;
2012 QRect textRect(xpos, y + windowsItemVMargin, w - xm - windowsRightBorder - tab + 1, h - 2 * windowsItemVMargin);
2013 QRect vTextRect = visualRect(option->direction, option->rect, textRect);
2014 QString s = menuitem->text;
2017 int t = s.indexOf(QLatin1Char(
'\t'));
2018 int text_flags = Qt::AlignVCenter|Qt::TextShowMnemonic | Qt::TextDontClip | Qt::TextSingleLine | Qt::AlignLeft;
2019 if (!proxy()->styleHint(SH_UnderlineShortcut, menuitem))
2020 text_flags |= Qt::TextHideMnemonic;
2023 QRect vShortcutRect = visualRect(option->direction, option->rect, QRect(textRect.topRight(), menuitem->rect.bottomRight()));
2024 if (dis && !act && proxy()->styleHint(SH_EtchDisabledText, option)) {
2025 p->setPen(menuitem->palette.light().color());
2026 p->drawText(vShortcutRect.adjusted(1,1,1,1), text_flags, s.mid(t + 1));
2027 p->setPen(textColor);
2029 p->drawText(vShortcutRect, text_flags, s.mid(t + 1));
2032 QFont font = menuitem->font;
2036 if (dis && !act && proxy()->styleHint(SH_EtchDisabledText, option)) {
2037 p->setPen(menuitem->palette.light().color());
2038 p->drawText(vTextRect.adjusted(1,1,1,1), text_flags, s.left(t));
2039 p->setPen(textColor);
2041 p->drawText(vTextRect, text_flags, s);
2047 int dim = (h - 2) / 2;
2048 PrimitiveElement arrow;
2049 arrow = (option->direction == Qt::RightToLeft) ? PE_IndicatorArrowLeft : PE_IndicatorArrowRight;
2051 QRect vSubMenuRect = visualRect(option->direction, option->rect, QRect(xpos, y + h / 2 - dim / 2, dim, dim));
2053 newMI.rect = vSubMenuRect;
2056 newMI.palette.setColor(QPalette::ButtonText, newMI.palette.highlightedText().color());
2057 proxy()->drawPrimitive(arrow, &newMI, p);
2062 case CE_MenuBarItem:
2071 QBrush fill = mbi->palette.brush(act ? QPalette::Highlight : QPalette::Button);
2072 QPalette::ColorRole textRole = dis ? QPalette::Text:
2073 act ? QPalette::HighlightedText : QPalette::ButtonText;
2074 QPixmap pix = mbi->icon.pixmap(proxy()->pixelMetric(PM_SmallIconSize, option), QIcon::Normal);
2076 uint alignment = Qt::AlignCenter | Qt::TextShowMnemonic | Qt::TextDontClip | Qt::TextSingleLine;
2077 if (!proxy()->styleHint(SH_UnderlineShortcut, mbi))
2078 alignment |= Qt::TextHideMnemonic;
2080 p->fillRect(rect, fill);
2082 drawItemPixmap(p, mbi->rect, alignment, pix);
2084 drawItemText(p, mbi->rect, alignment, mbi->palette, mbi->state & State_Enabled, mbi->text, textRole);
2087#if 0
&& QT_CONFIG(dockwidget)
2088 case CE_DockWidgetTitle:
2089 if (
const QStyleOptionDockWidget *dwOpt = qstyleoption_cast<
const QStyleOptionDockWidget *>(option))
2091 int buttonMargin = 4;
2092 int mw = proxy()->pixelMetric(QStyle::PM_DockWidgetTitleMargin, dwOpt);
2093 int fw = proxy()->pixelMetric(PM_DockWidgetFrameWidth, dwOpt);
2094 bool isFloating =
false;
2095 bool isActive = dwOpt->state & State_Active;
2097 const bool verticalTitleBar = dwOpt->verticalTitleBar;
2099 if (verticalTitleBar) {
2100 rect = rect.transposed();
2102 p->translate(rect.left() - 1, rect.top() + rect.width());
2104 p->translate(-rect.left() + 1, -rect.top());
2106 QRect r = rect.adjusted(0, 2, -1, -3);
2107 QRect titleRect = r;
2109 if (dwOpt->closable) {
2110 QSize sz = proxy()->standardIcon(QStyle::SP_TitleBarCloseButton, dwOpt).actualSize(QSize(10, 10));
2111 titleRect.adjust(0, 0, -sz.width() - mw - buttonMargin, 0);
2114 if (dwOpt->floatable) {
2115 QSize sz = proxy()->standardIcon(QStyle::SP_TitleBarMaxButton, dwOpt).actualSize(QSize(10, 10));
2116 titleRect.adjust(0, 0, -sz.width() - mw - buttonMargin, 0);
2120 titleRect.adjust(0, -fw, 0, 0);
2121 if (option->window && option->window->icon().cacheKey() != QApplication::windowIcon().cacheKey())
2122 titleRect.adjust(titleRect.height() + mw, 0, 0, 0);
2124 titleRect.adjust(mw, 0, 0, 0);
2125 if (!dwOpt->floatable && !dwOpt->closable)
2126 titleRect.adjust(0, 0, -mw, 0);
2129 if (!verticalTitleBar)
2130 titleRect = visualRect(dwOpt->direction, r, titleRect);
2133 QPen oldPen = p->pen();
2134 QString titleText = p->fontMetrics().elidedText(dwOpt->title, Qt::ElideRight, titleRect.width());
2135 p->setPen(dwOpt->palette.color(QPalette::Dark));
2138 if (!titleText.isEmpty()) {
2139 drawItemText(p, titleRect,
2140 Qt::AlignLeft | Qt::AlignVCenter | Qt::TextShowMnemonic, dwOpt->palette,
2141 dwOpt->state & State_Enabled, titleText,
2142 QPalette::WindowText);
2147 themeNumber = QWindowsXPStylePrivate::WindowTheme;
2149 stateId = CS_ACTIVE;
2151 stateId = CS_INACTIVE;
2153 int titleHeight = rect.height() - 2;
2154 rect = rect.adjusted(-fw, -fw, fw, 0);
2156 XPThemeData theme(option->window, p, themeNumber, 0, stateId);
2157 if (!theme.isValid())
2162 theme.partId = WP_SMALLCAPTION;
2163 d->drawBackground(theme);
2167 QIcon ico = option->window->icon();
2168 bool hasIcon = (ico.cacheKey() != QApplication::windowIcon().cacheKey());
2170 QPixmap pxIco = ico.pixmap(titleHeight);
2171 if (!verticalTitleBar && dwOpt->direction == Qt::RightToLeft)
2172 p->drawPixmap(rect.width() - titleHeight - pxIco.width(), rect.bottom() - titleHeight - 2, pxIco);
2174 p->drawPixmap(fw, rect.bottom() - titleHeight - 2, pxIco);
2176 if (!dwOpt->title.isEmpty()) {
2177 QPen oldPen = p->pen();
2178 QFont oldFont = p->font();
2179 QFont titleFont = oldFont;
2180 titleFont.setBold(
true);
2181 p->setFont(titleFont);
2183 = p->fontMetrics().elidedText(dwOpt->title, Qt::ElideRight, titleRect.width());
2185 int result = TST_NONE;
2186 GetThemeEnumValue(theme.handle(), WP_SMALLCAPTION, isActive ? CS_ACTIVE : CS_INACTIVE, TMT_TEXTSHADOWTYPE, &result);
2187 if (result != TST_NONE) {
2188 COLORREF textShadowRef;
2189 GetThemeColor(theme.handle(), WP_SMALLCAPTION, isActive ? CS_ACTIVE : CS_INACTIVE, TMT_TEXTSHADOWCOLOR, &textShadowRef);
2190 QColor textShadow = qRgb(GetRValue(textShadowRef), GetGValue(textShadowRef), GetBValue(textShadowRef));
2191 p->setPen(textShadow);
2192 drawItemText(p, titleRect.adjusted(1, 1, 1, 1),
2193 Qt::AlignLeft | Qt::AlignBottom, dwOpt->palette,
2194 dwOpt->state & State_Enabled, titleText);
2197 COLORREF captionText = GetSysColor(isActive ? COLOR_CAPTIONTEXT : COLOR_INACTIVECAPTIONTEXT);
2198 QColor textColor = qRgb(GetRValue(captionText), GetGValue(captionText), GetBValue(captionText));
2199 p->setPen(textColor);
2200 drawItemText(p, titleRect,
2201 Qt::AlignLeft | Qt::AlignBottom, dwOpt->palette,
2202 dwOpt->state & State_Enabled, titleText);
2203 p->setFont(oldFont);
2213#if 0
&& QT_CONFIG(rubberband)
2215 if (qstyleoption_cast<
const QStyleOptionRubberBand *>(option)) {
2216 QColor highlight = option->palette.color(QPalette::Active, QPalette::Highlight).toRgb();
2218 p->setPen(highlight.darker(120));
2219 QColor dimHighlight(qMin(highlight.red()/2 + 110, 255),
2220 qMin(highlight.green()/2 + 110, 255),
2221 qMin(highlight.blue()/2 + 110, 255),
2224 p->setBrush(dimHighlight);
2225 p->drawRect(option->rect.adjusted(0, 0, -1, -1));
2231 case CE_HeaderEmptyArea:
2234 themeNumber = QWindowsXPStylePrivate::HeaderTheme;
2235 stateId = HIS_NORMAL;
2238 QWindowsStyle::drawControl(CE_HeaderEmptyArea, option, p);
2246 XPThemeData theme(option->window, p, themeNumber, partId, stateId, rect);
2248 QWindowsStyle::drawControl(element, option, p);
2252 theme.rotate = rotate;
2253 theme.mirrorHorizontally = hMirrored;
2254 theme.mirrorVertically = vMirrored;
2255 d->drawBackground(theme);
2338 QWindowsStyle::drawComplexControl(cc, option, p);
2342 State flags = option->state;
2343 SubControls sub = option->subControls;
2344 QRect r = option->rect;
2348 if (option->window && option->window->isActive())
2349 flags |= State_MouseOver;
2356 XPThemeData theme(option->window, p, QWindowsXPStylePrivate::SpinTheme);
2358 if (sb->frame && (sub & SC_SpinBoxFrame)) {
2359 partId = EP_EDITTEXT;
2360 if (!(flags & State_Enabled))
2361 stateId = ETS_DISABLED;
2362 else if (flags & State_HasFocus)
2363 stateId = ETS_FOCUSED;
2365 stateId = ETS_NORMAL;
2367 XPThemeData ftheme(option->window, p, QWindowsXPStylePrivate::EditTheme,
2368 partId, stateId, r);
2369 ftheme.noContent =
true;
2370 d->drawBackground(ftheme);
2372 if (sub & SC_SpinBoxUp) {
2373 theme.rect = proxy()->subControlRect(CC_SpinBox, option, SC_SpinBoxUp);
2375 if (!(sb->stepEnabled & QStyleOptionSpinBox::StepUpEnabled) || !(flags & State_Enabled))
2376 stateId = UPS_DISABLED;
2377 else if (sb->activeSubControls == SC_SpinBoxUp && (sb->state & State_Sunken))
2378 stateId = UPS_PRESSED;
2379 else if (sb->activeSubControls == SC_SpinBoxUp && (sb->state & State_MouseOver))
2382 stateId = UPS_NORMAL;
2385 d->drawBackground(theme);
2387 if (sub & SC_SpinBoxDown) {
2388 theme.rect = proxy()->subControlRect(CC_SpinBox, option, SC_SpinBoxDown);
2390 if (!(sb->stepEnabled & QStyleOptionSpinBox::StepDownEnabled) || !(flags & State_Enabled))
2391 stateId = DNS_DISABLED;
2392 else if (sb->activeSubControls == SC_SpinBoxDown && (sb->state & State_Sunken))
2393 stateId = DNS_PRESSED;
2394 else if (sb->activeSubControls == SC_SpinBoxDown && (sb->state & State_MouseOver))
2397 stateId = DNS_NORMAL;
2400 d->drawBackground(theme);
2406 case CC_SearchField:
2409 if (sf->frame && (sub & SC_SearchFieldFrame)) {
2410 partId = EP_EDITBORDER_NOSCROLL;
2411 if (!(flags & State_Enabled))
2412 stateId = ETS_DISABLED;
2413 else if (flags & State_MouseOver)
2415 else if (flags & State_HasFocus)
2416 stateId = ETS_FOCUSED;
2418 stateId = ETS_NORMAL;
2421 QWindowsXPStylePrivate::EditTheme,
2422 partId, stateId, r);
2424 d->drawBackground(theme);
2434 if (sub & SC_ComboBoxEditField) {
2435 partId = EP_EDITBORDER_NOSCROLL;
2436 if (!(flags & State_Enabled))
2437 stateId = ETS_DISABLED;
2438 else if (flags & State_MouseOver)
2440 else if (flags & State_HasFocus)
2441 stateId = ETS_FOCUSED;
2443 stateId = ETS_NORMAL;
2446 QWindowsXPStylePrivate::EditTheme,
2447 partId, stateId, r);
2449 d->drawBackground(theme);
2451 if (sub & SC_ComboBoxArrow) {
2452 QRect subRect = proxy()->subControlRect(CC_ComboBox, option, SC_ComboBoxArrow);
2453 XPThemeData theme(option->window, p, QWindowsXPStylePrivate::ComboboxTheme);
2454 theme.rect = subRect;
2455 partId = option->direction == Qt::RightToLeft ? CP_DROPDOWNBUTTONLEFT : CP_DROPDOWNBUTTONRIGHT;
2457 if (!(cmb->state & State_Enabled))
2458 stateId = CBXS_DISABLED;
2459 else if (cmb->state & State_Sunken || cmb->state & State_On)
2460 stateId = CBXS_PRESSED;
2461 else if (cmb->state & State_MouseOver && option->activeSubControls & SC_ComboBoxArrow)
2464 stateId = CBXS_NORMAL;
2468 d->drawBackground(theme);
2472 if (sub & SC_ComboBoxFrame) {
2473 XPThemeData theme(option->window, p, QWindowsXPStylePrivate::ComboboxTheme);
2474 theme.rect = option->rect;
2475 theme.partId = CP_READONLY;
2476 if (!(cmb->state & State_Enabled))
2477 theme.stateId = CBXS_DISABLED;
2478 else if (cmb->state & State_Sunken || cmb->state & State_On)
2479 theme.stateId = CBXS_PRESSED;
2480 else if (cmb->state & State_MouseOver)
2481 theme.stateId = CBXS_HOT;
2483 theme.stateId = CBXS_NORMAL;
2484 d->drawBackground(theme);
2486 if (sub & SC_ComboBoxArrow) {
2487 XPThemeData theme(option->window, p, QWindowsXPStylePrivate::ComboboxTheme);
2488 theme.rect = proxy()->subControlRect(CC_ComboBox, option, SC_ComboBoxArrow);
2489 theme.partId = option->direction == Qt::RightToLeft ? CP_DROPDOWNBUTTONLEFT : CP_DROPDOWNBUTTONRIGHT;
2490 if (!(cmb->state & State_Enabled))
2491 theme.stateId = CBXS_DISABLED;
2493 theme.stateId = CBXS_NORMAL;
2494 d->drawBackground(theme);
2496 if ((sub & SC_ComboBoxEditField) && (flags & State_HasFocus)) {
2499 fropt.rect = proxy()->subControlRect(CC_ComboBox, option, SC_ComboBoxEditField);
2500 proxy()->drawPrimitive(PE_FrameFocusRect, &fropt, p);
2509 XPThemeData theme(option->window, p, QWindowsXPStylePrivate::ScrollBarTheme);
2512 flags &= ~State_Enabled;
2514 bool isHorz = flags & State_Horizontal;
2515 bool isRTL = option->direction == Qt::RightToLeft;
2516 if (sub & SC_ScrollBarAddLine) {
2517 theme.rect = proxy()->subControlRect(CC_ScrollBar, option, SC_ScrollBarAddLine);
2518 partId = SBP_ARROWBTN;
2519 if (!(flags & State_Enabled))
2520 stateId = (isHorz ? (isRTL ? ABS_LEFTDISABLED : ABS_RIGHTDISABLED) : ABS_DOWNDISABLED);
2521 else if (scrollbar->activeSubControls & SC_ScrollBarAddLine && (scrollbar->state & State_Sunken))
2522 stateId = (isHorz ? (isRTL ? ABS_LEFTPRESSED : ABS_RIGHTPRESSED) : ABS_DOWNPRESSED);
2523 else if (scrollbar->activeSubControls & SC_ScrollBarAddLine && (scrollbar->state & State_MouseOver))
2524 stateId = (isHorz ? (isRTL ? ABS_LEFTHOT : ABS_RIGHTHOT) : ABS_DOWNHOT);
2526 stateId = (isHorz ? (isRTL ? ABS_LEFTNORMAL : ABS_RIGHTNORMAL) : ABS_DOWNNORMAL);
2529 d->drawBackground(theme);
2531 if (sub & SC_ScrollBarSubLine) {
2532 theme.rect = proxy()->subControlRect(CC_ScrollBar, option, SC_ScrollBarSubLine);
2533 partId = SBP_ARROWBTN;
2534 if (!(flags & State_Enabled))
2535 stateId = (isHorz ? (isRTL ? ABS_RIGHTDISABLED : ABS_LEFTDISABLED) : ABS_UPDISABLED);
2536 else if (scrollbar->activeSubControls & SC_ScrollBarSubLine && (scrollbar->state & State_Sunken))
2537 stateId = (isHorz ? (isRTL ? ABS_RIGHTPRESSED : ABS_LEFTPRESSED) : ABS_UPPRESSED);
2538 else if (scrollbar->activeSubControls & SC_ScrollBarSubLine && (scrollbar->state & State_MouseOver))
2539 stateId = (isHorz ? (isRTL ? ABS_RIGHTHOT : ABS_LEFTHOT) : ABS_UPHOT);
2541 stateId = (isHorz ? (isRTL ? ABS_RIGHTNORMAL : ABS_LEFTNORMAL) : ABS_UPNORMAL);
2544 d->drawBackground(theme);
2547 if (sub & SC_ScrollBarSlider) {
2548 theme.rect = proxy()->subControlRect(CC_ScrollBar, option, SC_ScrollBarSlider);
2549 theme.rect = theme.rect.united(proxy()->subControlRect(CC_ScrollBar, option, SC_ScrollBarSubPage));
2550 theme.rect = theme.rect.united(proxy()->subControlRect(CC_ScrollBar, option, SC_ScrollBarAddPage));
2551 partId = scrollbar->orientation == Qt::Horizontal ? SBP_LOWERTRACKHORZ : SBP_LOWERTRACKVERT;
2552 stateId = SCRBS_DISABLED;
2555 d->drawBackground(theme);
2558 if (sub & SC_ScrollBarSubPage) {
2559 theme.rect = proxy()->subControlRect(CC_ScrollBar, option, SC_ScrollBarSubPage);
2560 partId = flags & State_Horizontal ? SBP_UPPERTRACKHORZ : SBP_UPPERTRACKVERT;
2561 if (!(flags & State_Enabled))
2562 stateId = SCRBS_DISABLED;
2563 else if (scrollbar->activeSubControls & SC_ScrollBarSubPage && (scrollbar->state & State_Sunken))
2564 stateId = SCRBS_PRESSED;
2565 else if (scrollbar->activeSubControls & SC_ScrollBarSubPage && (scrollbar->state & State_MouseOver))
2566 stateId = SCRBS_HOT;
2568 stateId = SCRBS_NORMAL;
2571 d->drawBackground(theme);
2573 if (sub & SC_ScrollBarAddPage) {
2574 theme.rect = proxy()->subControlRect(CC_ScrollBar, option, SC_ScrollBarAddPage);
2575 partId = flags & State_Horizontal ? SBP_LOWERTRACKHORZ : SBP_LOWERTRACKVERT;
2576 if (!(flags & State_Enabled))
2577 stateId = SCRBS_DISABLED;
2578 else if (scrollbar->activeSubControls & SC_ScrollBarAddPage && (scrollbar->state & State_Sunken))
2579 stateId = SCRBS_PRESSED;
2580 else if (scrollbar->activeSubControls & SC_ScrollBarAddPage && (scrollbar->state & State_MouseOver))
2581 stateId = SCRBS_HOT;
2583 stateId = SCRBS_NORMAL;
2586 d->drawBackground(theme);
2588 if (sub & SC_ScrollBarSlider) {
2594 const int extentForButton = proxy()->pixelMetric(PM_ScrollBarExtent, scrollbar);
2595 QSize extend(extentForButton, 0);
2596 if (scrollbar->orientation == Qt::Vertical)
2600 rect.setSize(rect.size() + 2 * extend);
2602 p->translate(-extend.width(), -extend.height());
2605 if (!(flags & State_Enabled))
2606 stateId = SCRBS_DISABLED;
2607 else if (scrollbar->activeSubControls & SC_ScrollBarSlider && (scrollbar->state & State_Sunken))
2608 stateId = SCRBS_PRESSED;
2609 else if (scrollbar->activeSubControls & SC_ScrollBarSlider && (scrollbar->state & State_MouseOver))
2610 stateId = SCRBS_HOT;
2612 stateId = SCRBS_NORMAL;
2615 theme.partId = flags & State_Horizontal ? SBP_THUMBBTNHORZ : SBP_THUMBBTNVERT;
2617 d->drawBackground(theme);
2619 const QRect gripperBounds = QWindowsXPStylePrivate::scrollBarGripperBounds(flags, &theme);
2621 if (!gripperBounds.isEmpty()) {
2623 theme.rect = gripperBounds;
2624 p->setClipRegion(d->region(theme));
2625 d->drawBackground(theme);
2637 XPThemeData theme(option->window, p, QWindowsXPStylePrivate::TrackBarTheme);
2638 QRect slrect = slider->rect;
2639 QRegion tickreg = slrect;
2640 if (sub & SC_SliderGroove) {
2641 theme.rect = proxy()->subControlRect(CC_Slider, option, SC_SliderGroove);
2642 if (slider->orientation == Qt::Horizontal) {
2644 stateId = TRS_NORMAL;
2645 theme.rect = QRect(slrect.left(), theme.rect.center().y() - 2, slrect.width(), 4);
2647 partId = TKP_TRACKVERT;
2648 stateId = TRVS_NORMAL;
2649 theme.rect = QRect(theme.rect.center().x() - 2, slrect.top(), 4, slrect.height());
2653 d->drawBackground(theme);
2654 tickreg -= theme.rect;
2656 if (sub & SC_SliderTickmarks) {
2657 int tickOffset = proxy()->pixelMetric(PM_SliderTickmarkOffset, slider);
2659 int thickness = proxy()->pixelMetric(PM_SliderControlThickness, slider);
2660 int len = proxy()->pixelMetric(PM_SliderLength, slider);
2661 int available = proxy()->pixelMetric(PM_SliderSpaceAvailable, slider);
2663 if (interval <= 0) {
2673 int fudge = len / 2;
2676 p->setPen(d->sliderTickColor);
2677 QVarLengthArray<QLine, 32> lines;
2680 if (v == slider
->maximum + 1 && interval == 1)
2682 const int v_ = qMin(v, slider
->maximum);
2685 v_
, available
) + fudge;
2686 if (slider->orientation == Qt::Horizontal) {
2688 lines.append(QLine(pos, tickOffset - 1 - bothOffset,
2689 pos, tickOffset - 1 - bothOffset - tickLength));
2692 lines.append(QLine(pos, tickOffset + thickness + bothOffset,
2693 pos, tickOffset + thickness + bothOffset + tickLength));
2696 lines.append(QLine(tickOffset - 1 - bothOffset, pos,
2697 tickOffset - 1 - bothOffset - tickLength, pos));
2700 lines.append(QLine(tickOffset + thickness + bothOffset, pos,
2701 tickOffset + thickness + bothOffset + tickLength, pos));
2704 int nextInterval = v + interval;
2705 if (nextInterval < v)
2709 if (!lines.isEmpty()) {
2711 p->translate(slrect.topLeft());
2712 p->drawLines(lines.constData(), lines.size());
2716 if (sub & SC_SliderHandle) {
2717 theme.rect = proxy()->subControlRect(CC_Slider, option, SC_SliderHandle);
2718 if (slider->orientation == Qt::Horizontal) {
2719 if (slider->tickPosition == QStyleOptionSlider::TicksAbove)
2720 partId = TKP_THUMBTOP;
2721 else if (slider->tickPosition == QStyleOptionSlider::TicksBelow)
2722 partId = TKP_THUMBBOTTOM;
2726 if (!(slider->state & State_Enabled))
2727 stateId = TUS_DISABLED;
2728 else if (slider->activeSubControls & SC_SliderHandle && (slider->state & State_Sunken))
2729 stateId = TUS_PRESSED;
2730 else if (slider->activeSubControls & SC_SliderHandle && (slider->state & State_MouseOver))
2732 else if (flags & State_HasFocus)
2733 stateId = TUS_FOCUSED;
2735 stateId = TUS_NORMAL;
2737 if (slider->tickPosition == QStyleOptionSlider::TicksLeft)
2738 partId = TKP_THUMBLEFT;
2739 else if (slider->tickPosition == QStyleOptionSlider::TicksRight)
2740 partId = TKP_THUMBRIGHT;
2742 partId = TKP_THUMBVERT;
2744 if (!(slider->state & State_Enabled))
2745 stateId = TUVS_DISABLED;
2746 else if (slider->activeSubControls & SC_SliderHandle && (slider->state & State_Sunken))
2747 stateId = TUVS_PRESSED;
2748 else if (slider->activeSubControls & SC_SliderHandle && (slider->state & State_MouseOver))
2750 else if (flags & State_HasFocus)
2751 stateId = TUVS_FOCUSED;
2753 stateId = TUVS_NORMAL;
2757 d->drawBackground(theme);
2759 if (sub & SC_SliderGroove && slider->state & State_HasFocus) {
2762 fropt.rect = subElementRect(SE_SliderFocusRect, slider);
2763 proxy()->drawPrimitive(PE_FrameFocusRect, &fropt, p);
2768#if 0
&& QT_CONFIG(toolbutton)
2770 if (
const QStyleOptionToolButton *toolbutton
2771 = qstyleoption_cast<
const QStyleOptionToolButton *>(option)) {
2772 QRect button, menuarea;
2773 button = proxy()->subControlRect(cc, toolbutton, SC_ToolButton);
2774 menuarea = proxy()->subControlRect(cc, toolbutton, SC_ToolButtonMenu);
2776 State bflags = toolbutton->state & ~State_Sunken;
2777 State mflags = bflags;
2778 bool autoRaise = flags & State_AutoRaise;
2780 if (!(bflags & State_MouseOver) || !(bflags & State_Enabled)) {
2781 bflags &= ~State_Raised;
2785 if (toolbutton->state & State_Sunken) {
2786 if (toolbutton->activeSubControls & SC_ToolButton) {
2787 bflags |= State_Sunken;
2788 mflags |= State_MouseOver | State_Sunken;
2789 }
else if (toolbutton->activeSubControls & SC_ToolButtonMenu) {
2790 mflags |= State_Sunken;
2791 bflags |= State_MouseOver;
2795 QStyleOption tool = *toolbutton;
2796 if (toolbutton->subControls & SC_ToolButton) {
2797 if (flags & (State_Sunken | State_On | State_Raised) || !autoRaise) {
2798 if (toolbutton->features & QStyleOptionToolButton::MenuButtonPopup && autoRaise) {
2799 XPThemeData theme(option->window, p, QWindowsXPStylePrivate::ToolBarTheme);
2800 theme.partId = TP_SPLITBUTTON;
2801 theme.rect = button;
2802 if (!(bflags & State_Enabled))
2803 stateId = TS_DISABLED;
2804 else if (bflags & State_Sunken)
2805 stateId = TS_PRESSED;
2806 else if (bflags & State_MouseOver || !(flags & State_AutoRaise))
2807 stateId = flags & State_On ? TS_HOTCHECKED : TS_HOT;
2808 else if (bflags & State_On)
2809 stateId = TS_CHECKED;
2811 stateId = TS_NORMAL;
2812 if (option->direction == Qt::RightToLeft)
2813 theme.mirrorHorizontally =
true;
2814 theme.stateId = stateId;
2815 d->drawBackground(theme);
2817 tool.rect = option->rect;
2818 tool.state = bflags;
2820 proxy()->drawPrimitive(PE_PanelButtonTool, &tool, p);
2822 proxy()->drawPrimitive(PE_PanelButtonBevel, &tool, p);
2827 if (toolbutton->state & State_HasFocus) {
2828 QStyleOptionFocusRect fr;
2829 fr.QStyleOption::operator=(*toolbutton);
2830 fr.rect.adjust(3, 3, -3, -3);
2831 if (toolbutton->features & QStyleOptionToolButton::MenuButtonPopup)
2832 fr.rect.adjust(0, 0, -proxy()->pixelMetric(QStyle::PM_MenuButtonIndicator,
2834 proxy()->drawPrimitive(PE_FrameFocusRect, &fr, p);
2836 QStyleOptionToolButton label = *toolbutton;
2837 label.state = bflags;
2840 label.state &= ~State_Sunken;
2841 label.rect = button.adjusted(fw, fw, -fw, -fw);
2842 proxy()->drawControl(CE_ToolButtonLabel, &label, p);
2844 if (toolbutton->subControls & SC_ToolButtonMenu) {
2845 tool.rect = menuarea;
2846 tool.state = mflags;
2848 proxy()->drawPrimitive(PE_IndicatorButtonDropDown, &tool, p);
2850 tool.state = mflags;
2851 menuarea.adjust(-2, 0, 0, 0);
2853 if ((bflags & State_Sunken) != (mflags & State_Sunken)){
2855 p->setClipRect(menuarea);
2856 tool.rect = option->rect;
2857 proxy()->drawPrimitive(PE_PanelButtonBevel, &tool, p);
2862 p->setPen(option->palette.dark().color());
2863 p->drawLine(menuarea.left(), menuarea.top() + 3,
2864 menuarea.left(), menuarea.bottom() - 3);
2865 p->setPen(option->palette.light().color());
2866 p->drawLine(menuarea.left() - 1, menuarea.top() + 3,
2867 menuarea.left() - 1, menuarea.bottom() - 3);
2869 tool.rect = menuarea.adjusted(2, 3, -2, -1);
2870 proxy()->drawPrimitive(PE_IndicatorArrowDown, &tool, p);
2873 }
else if (toolbutton->features & QStyleOptionToolButton::HasMenu) {
2874 int mbi = proxy()->pixelMetric(PM_MenuButtonIndicator, toolbutton);
2875 QRect ir = toolbutton->rect;
2876 QStyleOptionToolButton newBtn = *toolbutton;
2877 newBtn.rect = QRect(ir.right() + 4 - mbi, ir.height() - mbi + 4, mbi - 5, mbi - 5);
2878 proxy()->drawPrimitive(PE_IndicatorArrowDown, &newBtn, p);
2888 const qreal factor = QWindowsStylePrivate::nativeMetricScaleFactor(option);
2890 XPThemeData theme(option->window, p, QWindowsXPStylePrivate::WindowTheme);
2891 if (sub & SC_TitleBarLabel) {
2893 partId = (tb->titleBarState & Qt::WindowMinimized) ? WP_MINCAPTION : WP_CAPTION;
2894 theme.rect = option->rect;
2895 if (!(option->state & QStyle::State_Enabled))
2896 stateId = CS_DISABLED;
2898 stateId = CS_ACTIVE;
2900 stateId = CS_INACTIVE;
2904 d->drawBackground(theme);
2906 QRect ir = proxy()->subControlRect(CC_TitleBar, tb, SC_TitleBarLabel);
2909 GetThemeEnumValue(theme.handle(), WP_CAPTION, isActive ? CS_ACTIVE : CS_INACTIVE, TMT_TEXTSHADOWTYPE, &result);
2911 COLORREF textShadowRef;
2912 GetThemeColor(theme.handle(), WP_CAPTION, isActive ? CS_ACTIVE : CS_INACTIVE,
TMT_TEXTSHADOWCOLOR, &textShadowRef);
2913 QColor textShadow = qRgb(GetRValue(textShadowRef), GetGValue(textShadowRef), GetBValue(textShadowRef));
2914 p->setPen(textShadow);
2915 p->drawText(
int(ir.x() + 3 * factor),
int(ir.y() + 2 * factor),
2916 int(ir.width() - 1 * factor), ir.height(),
2917 Qt::AlignLeft | Qt::AlignVCenter | Qt::TextSingleLine, tb->text);
2919 COLORREF captionText = GetSysColor(isActive ? COLOR_CAPTIONTEXT : COLOR_INACTIVECAPTIONTEXT);
2920 QColor textColor = qRgb(GetRValue(captionText), GetGValue(captionText), GetBValue(captionText));
2921 p->setPen(textColor);
2922 p->drawText(
int(ir.x() + 2 * factor),
int(ir.y() + 1 * factor),
2923 int(ir.width() - 2 * factor), ir.height(),
2924 Qt::AlignLeft | Qt::AlignVCenter | Qt::TextSingleLine, tb->text);
2926 if (sub & SC_TitleBarSysMenu && tb->titleBarFlags & Qt::WindowSystemMenuHint) {
2927 theme.rect = proxy()->subControlRect(CC_TitleBar, option, SC_TitleBarSysMenu);
2928 partId = WP_SYSBUTTON;
2929 if (!(option->state & QStyle::State_Enabled) || !isActive)
2930 stateId = SBS_DISABLED;
2931 else if (option->activeSubControls == SC_TitleBarSysMenu && (option->state & State_Sunken))
2932 stateId = SBS_PUSHED;
2933 else if (option->activeSubControls == SC_TitleBarSysMenu && (option->state & State_MouseOver))
2936 stateId = SBS_NORMAL;
2937 if (!tb->icon.isNull()) {
2938 tb->icon.paint(p, theme.rect);
2942 if (theme.size().isEmpty()) {
2943 int iconSize = proxy()->pixelMetric(PM_SmallIconSize, tb);
2944 QPixmap pm = proxy()->standardIcon(SP_TitleBarMenuButton, tb).pixmap(iconSize, iconSize);
2946 drawItemPixmap(p, theme.rect, Qt::AlignCenter, pm);
2949 d->drawBackground(theme);
2954 if (sub & SC_TitleBarMinButton && tb->titleBarFlags & Qt::WindowMinimizeButtonHint
2955 && !(tb->titleBarState & Qt::WindowMinimized)) {
2956 populateTitleBarButtonTheme(proxy(), option, SC_TitleBarMinButton, isActive, WP_MINBUTTON, &theme);
2957 d->drawBackground(theme);
2959 if (sub & SC_TitleBarMaxButton && tb->titleBarFlags & Qt::WindowMaximizeButtonHint
2960 && !(tb->titleBarState & Qt::WindowMaximized)) {
2961 populateTitleBarButtonTheme(proxy(), option, SC_TitleBarMaxButton, isActive, WP_MAXBUTTON, &theme);
2962 d->drawBackground(theme);
2964 if (sub & SC_TitleBarContextHelpButton
2965 && tb->titleBarFlags & Qt::WindowContextHelpButtonHint) {
2966 populateTitleBarButtonTheme(proxy(), option, SC_TitleBarContextHelpButton, isActive, WP_HELPBUTTON, &theme);
2967 d->drawBackground(theme);
2969 bool drawNormalButton = (sub & SC_TitleBarNormalButton)
2970 && (((tb->titleBarFlags & Qt::WindowMinimizeButtonHint)
2971 && (tb->titleBarState & Qt::WindowMinimized))
2972 || ((tb->titleBarFlags & Qt::WindowMaximizeButtonHint)
2973 && (tb->titleBarState & Qt::WindowMaximized)));
2974 if (drawNormalButton) {
2975 populateTitleBarButtonTheme(proxy(), option, SC_TitleBarNormalButton, isActive, WP_RESTOREBUTTON, &theme);
2976 d->drawBackground(theme);
2978 if (sub & SC_TitleBarShadeButton && tb->titleBarFlags & Qt::WindowShadeButtonHint
2979 && !(tb->titleBarState & Qt::WindowMinimized)) {
2980 populateTitleBarButtonTheme(proxy(), option, SC_TitleBarShadeButton, isActive, WP_MINBUTTON, &theme);
2981 d->drawBackground(theme);
2983 if (sub & SC_TitleBarUnshadeButton && tb->titleBarFlags & Qt::WindowShadeButtonHint
2984 && tb->titleBarState & Qt::WindowMinimized) {
2985 populateTitleBarButtonTheme(proxy(), option, SC_TitleBarUnshadeButton, isActive, WP_RESTOREBUTTON, &theme);
2986 d->drawBackground(theme);
2988 if (sub & SC_TitleBarCloseButton && tb->titleBarFlags & Qt::WindowSystemMenuHint) {
2989 populateTitleBarButtonTheme(proxy(), option, SC_TitleBarCloseButton, isActive, WP_CLOSEBUTTON, &theme);
2990 d->drawBackground(theme);
2996#if 0
&& QT_CONFIG(mdiarea)
2997 case CC_MdiControls:
2999 XPThemeData theme(option->window, p, QWindowsXPStylePrivate::WindowTheme, WP_MDICLOSEBUTTON, CBS_NORMAL);
3000 if (Q_UNLIKELY(!theme.isValid()))
3003 if (option->subControls.testFlag(SC_MdiCloseButton)) {
3004 populateMdiButtonTheme(proxy(), option, SC_MdiCloseButton, WP_MDICLOSEBUTTON, &theme);
3005 d->drawBackground(theme, mdiButtonCorrectionFactor(theme));
3007 if (option->subControls.testFlag(SC_MdiNormalButton)) {
3008 populateMdiButtonTheme(proxy(), option, SC_MdiNormalButton, WP_MDIRESTOREBUTTON, &theme);
3009 d->drawBackground(theme, mdiButtonCorrectionFactor(theme));
3011 if (option->subControls.testFlag(QStyle::SC_MdiMinButton)) {
3012 populateMdiButtonTheme(proxy(), option, SC_MdiMinButton, WP_MDIMINBUTTON, &theme);
3013 d->drawBackground(theme, mdiButtonCorrectionFactor(theme));
3018#if 0
&& QT_CONFIG(dial)
3020 if (
const QStyleOptionSlider *dial = qstyleoption_cast<
const QStyleOptionSlider *>(option))
3021 QStyleHelper::drawDial(dial, p);
3025 QWindowsStyle::drawComplexControl(cc, option, p);
3208 SubControl subControl)
const
3210 if (!QWindowsXPStylePrivate::useXP())
3211 return QWindowsStyle::subControlRect(cc, option, subControl);
3217 rect = visualRect(option->direction, option->rect,
3218 QWindowsStyle::subControlRect(cc, option, subControl));
3219 if (subControl == QStyle::SC_GroupBoxContents) {
3222 rect.adjust(9, 9, -9, -9);
3227 if (!buttonVisible(subControl, tb))
3229 const bool isToolTitle =
false;
3230 const int height = tb->rect.height();
3231 const int width = tb->rect.width();
3232 const int buttonMargin =
int(QStyleHelper::dpiScaled(4, option));
3233 const qreal factor = QWindowsStylePrivate::nativeMetricScaleFactor(option);
3234 int buttonHeight = qRound(qreal(GetSystemMetrics(SM_CYSIZE)) * factor)
3236 int buttonWidth = qRound(qreal(GetSystemMetrics(SM_CXSIZE)) * factor)
3238 const int delta = buttonWidth + 2;
3239 int controlTop = option->rect.bottom() - buttonHeight - 2;
3240 const int frameWidth = proxy()->pixelMetric(PM_MdiSubWindowFrameWidth, option);
3241 const bool sysmenuHint = (tb->titleBarFlags & Qt::WindowSystemMenuHint) != 0;
3242 const bool minimizeHint = (tb->titleBarFlags & Qt::WindowMinimizeButtonHint) != 0;
3243 const bool maximizeHint = (tb->titleBarFlags & Qt::WindowMaximizeButtonHint) != 0;
3244 const bool contextHint = (tb->titleBarFlags & Qt::WindowContextHelpButtonHint) != 0;
3245 const bool shadeHint = (tb->titleBarFlags & Qt::WindowShadeButtonHint) != 0;
3246 bool isMinimized = tb->titleBarState & Qt::WindowMinimized;
3247 bool isMaximized = tb->titleBarState & Qt::WindowMaximized;
3250 switch (subControl) {
3251 case SC_TitleBarLabel:
3252 rect = QRect(frameWidth, 0, width - (buttonWidth + frameWidth + 10), height);
3255 rect.adjust(0, 0, -buttonWidth - 3, 0);
3257 if (minimizeHint || maximizeHint)
3258 rect.adjust(0, 0, -buttonWidth - 2, 0);
3261 const int leftOffset = height - 8;
3262 rect.adjust(leftOffset, 0, 0, 0);
3265 rect.adjust(0, 0, -buttonWidth - 2, 0);
3267 rect.adjust(0, 0, -buttonWidth - 2, 0);
3269 rect.adjust(0, 0, -buttonWidth - 2, 0);
3271 rect.adjust(0, 0, -buttonWidth - 2, 0);
3275 case SC_TitleBarContextHelpButton:
3276 if (tb->titleBarFlags & Qt::WindowContextHelpButtonHint)
3279 case SC_TitleBarMinButton:
3280 if (!isMinimized && (tb->titleBarFlags & Qt::WindowMinimizeButtonHint))
3282 else if (subControl == SC_TitleBarMinButton)
3285 case SC_TitleBarNormalButton:
3286 if (isMinimized && (tb->titleBarFlags & Qt::WindowMinimizeButtonHint))
3288 else if (isMaximized && (tb->titleBarFlags & Qt::WindowMaximizeButtonHint))
3290 else if (subControl == SC_TitleBarNormalButton)
3293 case SC_TitleBarMaxButton:
3294 if (!isMaximized && (tb->titleBarFlags & Qt::WindowMaximizeButtonHint))
3296 else if (subControl == SC_TitleBarMaxButton)
3299 case SC_TitleBarShadeButton:
3300 if (!isMinimized && (tb->titleBarFlags & Qt::WindowShadeButtonHint))
3302 else if (subControl == SC_TitleBarShadeButton)
3305 case SC_TitleBarUnshadeButton:
3306 if (isMinimized && (tb->titleBarFlags & Qt::WindowShadeButtonHint))
3308 else if (subControl == SC_TitleBarUnshadeButton)
3311 case SC_TitleBarCloseButton:
3312 if (tb->titleBarFlags & Qt::WindowSystemMenuHint)
3314 else if (subControl == SC_TitleBarCloseButton)
3317 rect.setRect(width - offset - controlTop + 1, controlTop,
3318 buttonWidth, buttonHeight);
3321 case SC_TitleBarSysMenu:
3323 const int controlTop = 6;
3324 const int controlHeight = height - controlTop - 3;
3325 const int iconExtent = proxy()->pixelMetric(PM_SmallIconSize, option);
3326 QSize iconSize = tb->icon.actualSize(QSize(iconExtent, iconExtent));
3327 if (tb->icon.isNull())
3328 iconSize = QSize(controlHeight, controlHeight);
3329 int hPad = (controlHeight - iconSize.height())/2;
3330 int vPad = (controlHeight - iconSize.width())/2;
3331 rect = QRect(frameWidth + hPad, controlTop + vPad, iconSize.width(), iconSize.height());
3341 const int x = cmb->rect.x(), y = cmb->rect.y(), wi = cmb->rect.width(), he = cmb->rect.height();
3342 const int xpos = x + wi - qRound(QStyleHelper::dpiScaled(1 + 16, option));
3344 switch (subControl) {
3345 case SC_ComboBoxFrame:
3349 case SC_ComboBoxArrow: {
3350 const qreal dpi = QStyleHelper::dpi(option);
3351 rect = QRect(xpos, y + qRound(QStyleHelper::dpiScaled(1, dpi)),
3352 qRound(QStyleHelper::dpiScaled(16, dpi)),
3353 he - qRound(QStyleHelper::dpiScaled(2, dpi)));
3357 case SC_ComboBoxEditField: {
3358 const qreal dpi = QStyleHelper::dpi(option);
3359 const int frame = qRound(QStyleHelper::dpiScaled(2, dpi));
3360 rect = QRect(x + frame, y + frame,
3361 wi - qRound(QStyleHelper::dpiScaled(3 + 16, dpi)),
3362 he - qRound(QStyleHelper::dpiScaled(4, dpi)));
3366 case SC_ComboBoxListBoxPopup:
3375#if 0
&& QT_CONFIG(mdiarea)
3376 case CC_MdiControls:
3378 int numSubControls = 0;
3379 if (option->subControls & SC_MdiCloseButton)
3381 if (option->subControls & SC_MdiMinButton)
3383 if (option->subControls & SC_MdiNormalButton)
3385 if (numSubControls == 0)
3388 int buttonWidth = option->rect.width() / numSubControls;
3390 switch (subControl) {
3391 case SC_MdiCloseButton:
3393 if (numSubControls == 1)
3395 offset += buttonWidth;
3397 case SC_MdiNormalButton:
3401 if (numSubControls == 1 || (numSubControls == 2 && !(option->subControls & SC_MdiMinButton)))
3403 if (option->subControls & SC_MdiNormalButton)
3404 offset += buttonWidth;
3409 rect = QRect(offset, 0, buttonWidth, option->rect.height());
3415 rect = visualRect(option->direction, option->rect,
3416 QWindowsStyle::subControlRect(cc, option, subControl));
3419 return visualRect(option->direction, option->rect, rect);
3699 return QWindowsStyle::standardIcon(standardIcon, option);
3702 QWindowsXPStylePrivate *d =
const_cast<QWindowsXPStylePrivate*>(d_func());
3703 switch (standardIcon) {
3704 case SP_TitleBarMaxButton:
3705 if (qstyleoption_cast<
const QStyleOptionDockWidget *>(option))
3707 if (d->dockFloat.isNull()) {
3708 XPThemeData themeSize(
nullptr,
nullptr, QWindowsXPStylePrivate::WindowTheme,
3709 WP_SMALLCLOSEBUTTON, CBS_NORMAL);
3710 XPThemeData theme(
nullptr,
nullptr, QWindowsXPStylePrivate::WindowTheme,
3711 WP_MAXBUTTON, MAXBS_NORMAL);
3712 if (theme.isValid()) {
3713 const QSize size = (themeSize.size() * QWindowsStylePrivate::nativeMetricScaleFactor(option)).toSize();
3715 pm.fill(Qt::transparent);
3718 theme.rect = QRect(QPoint(0, 0), size);
3719 d->drawBackground(theme);
3720 d->dockFloat.addPixmap(pm, QIcon::Normal, QIcon::Off);
3721 pm.fill(Qt::transparent);
3722 theme.stateId = MAXBS_PUSHED;
3723 d->drawBackground(theme);
3724 d->dockFloat.addPixmap(pm, QIcon::Normal, QIcon::On);
3725 pm.fill(Qt::transparent);
3726 theme.stateId = MAXBS_HOT;
3727 d->drawBackground(theme);
3728 d->dockFloat.addPixmap(pm, QIcon::Active, QIcon::Off);
3729 pm.fill(Qt::transparent);
3730 theme.stateId = MAXBS_INACTIVE;
3731 d->drawBackground(theme);
3732 d->dockFloat.addPixmap(pm, QIcon::Disabled, QIcon::Off);
3735 if (widget && widget->isWindow())
3736 return d->dockFloat;
3740 case SP_TitleBarCloseButton:
3741 if (qstyleoption_cast<
const QStyleOptionDockWidget *>(option))
3743 if (d->dockClose.isNull()) {
3744 XPThemeData theme(
nullptr,
nullptr, QWindowsXPStylePrivate::WindowTheme,
3745 WP_SMALLCLOSEBUTTON, CBS_NORMAL);
3746 if (theme.isValid()) {
3747 const QSize size = (theme.size() * QWindowsStylePrivate::nativeMetricScaleFactor(option)).toSize();
3749 pm.fill(Qt::transparent);
3752 theme.partId = WP_CLOSEBUTTON;
3753 theme.rect = QRect(QPoint(0, 0), size);
3754 d->drawBackground(theme);
3755 d->dockClose.addPixmap(pm, QIcon::Normal, QIcon::Off);
3756 pm.fill(Qt::transparent);
3757 theme.stateId = CBS_PUSHED;
3758 d->drawBackground(theme);
3759 d->dockClose.addPixmap(pm, QIcon::Normal, QIcon::On);
3760 pm.fill(Qt::transparent);
3761 theme.stateId = CBS_HOT;
3762 d->drawBackground(theme);
3763 d->dockClose.addPixmap(pm, QIcon::Active, QIcon::Off);
3764 pm.fill(Qt::transparent);
3765 theme.stateId = CBS_INACTIVE;
3766 d->drawBackground(theme);
3767 d->dockClose.addPixmap(pm, QIcon::Disabled, QIcon::Off);
3770 if (widget && widget->isWindow())
3771 return d->dockClose;
3774 case SP_TitleBarNormalButton:
3775 if (qstyleoption_cast<
const QStyleOptionDockWidget *>(option))
3777 if (d->dockFloat.isNull()) {
3778 XPThemeData themeSize(
nullptr,
nullptr, QWindowsXPStylePrivate::WindowTheme,
3779 WP_SMALLCLOSEBUTTON, CBS_NORMAL);
3780 XPThemeData theme(
nullptr,
nullptr, QWindowsXPStylePrivate::WindowTheme,
3781 WP_RESTOREBUTTON, RBS_NORMAL);
3782 if (theme.isValid()) {
3783 const QSize size = (themeSize.size() * QWindowsStylePrivate::nativeMetricScaleFactor(option)).toSize();
3785 pm.fill(Qt::transparent);
3788 theme.rect = QRect(QPoint(0, 0), size);
3789 d->drawBackground(theme);
3790 d->dockFloat.addPixmap(pm, QIcon::Normal, QIcon::Off);
3791 pm.fill(Qt::transparent);
3792 theme.stateId = RBS_PUSHED;
3793 d->drawBackground(theme);
3794 d->dockFloat.addPixmap(pm, QIcon::Normal, QIcon::On);
3795 pm.fill(Qt::transparent);
3796 theme.stateId = RBS_HOT;
3797 d->drawBackground(theme);
3798 d->dockFloat.addPixmap(pm, QIcon::Active, QIcon::Off);
3799 pm.fill(Qt::transparent);
3800 theme.stateId = RBS_INACTIVE;
3801 d->drawBackground(theme);
3802 d->dockFloat.addPixmap(pm, QIcon::Disabled, QIcon::Off);
3805 if (widget && widget->isWindow())
3806 return d->dockFloat;
3814 return QWindowsStyle::standardIcon(standardIcon, option);