Introduce rounded plain frames, group boxes in QWindows11Style

Plain frames and group boxes are now drawn with rounded edges. In
QWindows11Style.

Change-Id: I576873d31c2252b7a22d84e8e86c64e09e2e5023
Reviewed-by: Oliver Wolff <oliver.wolff@qt.io>
bb10
Wladimir Leuschner 2023-06-22 15:49:32 +03:00
parent 6723515e5b
commit 51499e7a17
3 changed files with 150 additions and 2 deletions

View File

@ -438,6 +438,20 @@ void QWindows11Style::drawPrimitive(PrimitiveElement element, const QStyleOption
}
switch (element) {
case PE_FrameGroupBox:
if (const QStyleOptionFrame *frame = qstyleoption_cast<const QStyleOptionFrame *>(option)) {
painter->setPen(frameColorStrong);
painter->setBrush(Qt::NoBrush);
if (frame->features & QStyleOptionFrame::Flat) {
QRect fr = frame->rect;
QPoint p1(fr.x(), fr.y() + 1);
QPoint p2(fr.x() + fr.width(), p1.y());
painter->drawLine(p1,p2);
} else {
painter->drawRoundedRect(frame->rect.marginsRemoved(QMargins(1,1,1,1)), secondLevelRoundingRadius, secondLevelRoundingRadius);
}
}
break;
case PE_IndicatorCheckBox:
{
QNumberStyleAnimation* animation = qobject_cast<QNumberStyleAnimation*>(d->animation(option->styleObject));
@ -720,6 +734,36 @@ void QWindows11Style::drawControl(ControlElement element, const QStyleOption *op
}
}
break;
case QStyle::CE_ShapedFrame:
if (const QStyleOptionFrame *f = qstyleoption_cast<const QStyleOptionFrame *>(option)) {
int frameShape = f->frameShape;
int frameShadow = QFrame::Plain;
if (f->state & QStyle::State_Sunken)
frameShadow = QFrame::Sunken;
else if (f->state & QStyle::State_Raised)
frameShadow = QFrame::Raised;
int lw = f->lineWidth;
int mlw = f->midLineWidth;
switch (frameShape) {
case QFrame::Box:
if (frameShadow == QFrame::Plain)
qDrawPlainRoundedRect(painter, f->rect, secondLevelRoundingRadius, secondLevelRoundingRadius, frameColorStrong, lw);
else
qDrawShadeRect(painter, f->rect, f->palette, frameShadow == QFrame::Sunken, lw, mlw);
break;
case QFrame::Panel:
if (frameShadow == QFrame::Plain)
qDrawPlainRoundedRect(painter, f->rect, secondLevelRoundingRadius, secondLevelRoundingRadius, frameColorStrong, lw);
else
qDrawShadePanel(painter, f->rect, f->palette, frameShadow == QFrame::Sunken, lw);
break;
default:
QWindowsVistaStyle::drawControl(element, option, painter, widget);
}
}
break;
case QStyle::CE_ProgressBarGroove:{
if (const QStyleOptionProgressBar* progbaropt = qstyleoption_cast<const QStyleOptionProgressBar*>(option)) {
const QProgressBar* bar = qobject_cast<const QProgressBar*>(widget);
@ -1182,6 +1226,10 @@ void QWindows11Style::drawControl(ControlElement element, const QStyleOption *op
int QWindows11Style::styleHint(StyleHint hint, const QStyleOption *opt,
const QWidget *widget, QStyleHintReturn *returnData) const {
switch (hint) {
case SH_GroupBox_TextLabelColor:
if (opt!=nullptr && widget!=nullptr)
return opt->palette.text().color().rgba();
return 0;
case QStyle::SH_ItemView_ShowDecorationSelected:
return 1;
default:
@ -1242,6 +1290,7 @@ int QWindows11Style::pixelMetric(PixelMetric metric, const QStyleOption *option,
return res;
}
void QWindows11Style::polish(QWidget* widget)
{
QWindowsVistaStyle::polish(widget);

View File

@ -297,7 +297,6 @@ void qDrawShadeRect(QPainter *p, int x, int y, int w, int h,
p->setPen(oldPen); // restore pen
}
/*!
\fn void qDrawShadePanel(QPainter *painter, int x, int y, int width, int height,
const QPalette &palette, bool sunken,
@ -409,7 +408,6 @@ void qDrawShadePanel(QPainter *p, int x, int y, int w, int h,
p->setPen(oldPen); // restore pen
}
/*!
\internal
This function draws a rectangle with two pixel line width.
@ -611,6 +609,69 @@ void qDrawPlainRect(QPainter *p, int x, int y, int w, int h, const QColor &c,
p->setBrush(oldBrush);
}
/*!
\fn void qDrawPlainRoundedRect(QPainter *painter, int x, int y,
int width, int height, qreal rx, qreal ry,
const QColor &lineColor, int lineWidth,
const QBrush *fill)
\relates <qdrawutil.h>
Draws the plain rounded rectangle beginning at (\a x, \a y)
with the given \a width and \a height,
using the horizontal \a rx and vertical radius \a ry,
specified \a painter, \a lineColor and \a lineWidth.
The rectangle's interior is filled with the \a
fill brush unless \a fill is \nullptr.
\warning This function does not look at QWidget::style() or
QApplication::style(). Use the drawing functions in QStyle to make
widgets that follow the current GUI style.
Alternatively you can use a QFrame widget and apply the
QFrame::setFrameStyle() function to display a plain rectangle:
\snippet code/src_gui_painting_qdrawutil.cpp 4
\sa qDrawShadeRect(), QStyle
*/
void qDrawPlainRoundedRect(QPainter *p, int x, int y, int w, int h,
qreal rx, qreal ry, const QColor &c,
int lineWidth, const QBrush *fill)
{
if (w == 0 || h == 0)
return;
if (Q_UNLIKELY(w < 0 || h < 0 || lineWidth < 0)) {
qWarning("qDrawPlainRect: Invalid parameters");
}
PainterStateGuard painterGuard(p);
const qreal devicePixelRatio = p->device()->devicePixelRatio();
if (!qFuzzyCompare(devicePixelRatio, qreal(1))) {
painterGuard.save();
const qreal inverseScale = qreal(1) / devicePixelRatio;
p->scale(inverseScale, inverseScale);
x = qRound(devicePixelRatio * x);
y = qRound(devicePixelRatio * y);
w = devicePixelRatio * w;
h = devicePixelRatio * h;
lineWidth = qRound(devicePixelRatio * lineWidth);
p->translate(0.5, 0.5);
}
p->save();
p->setPen(c);
p->setBrush(Qt::NoBrush);
for (int i=0; i<lineWidth; i++)
p->drawRoundedRect(x+i, y+i, w-i*2 - 1, h-i*2 - 1, rx, ry);
if (fill) { // fill with fill color
p->setPen(Qt::NoPen);
p->setBrush(*fill);
p->drawRoundedRect(x+lineWidth, y+lineWidth, w-lineWidth*2, h-lineWidth*2, rx, ry);
}
p->restore();
}
/*****************************************************************************
Overloaded functions.
*****************************************************************************/
@ -819,6 +880,38 @@ void qDrawPlainRect(QPainter *p, const QRect &r, const QColor &c,
lineWidth, fill);
}
/*!
\fn void qDrawPlainRoundedRect(QPainter *painter, const QRect &rect,
qreal rx, qreal ry,
const QColor &lineColor, int lineWidth,
const QBrush *fill)
\relates <qdrawutil.h>
\overload
Draws the plain rectangle specified by \a rect using
the horizontal \a rx and vertical radius \a ry,
the given \a painter, \a lineColor and \a lineWidth.
The rectangle's interior is filled with the
\a fill brush unless \a fill is \nullptr.
\warning This function does not look at QWidget::style() or
QApplication::style(). Use the drawing functions in QStyle to make
widgets that follow the current GUI style.
Alternatively you can use a QFrame widget and apply the
QFrame::setFrameStyle() function to display a plain rectangle:
\snippet code/src_gui_painting_qdrawutil.cpp 9
\sa qDrawShadeRect(), QStyle
*/
void qDrawPlainRoundedRect(QPainter *p, const QRect &r, qreal rx, qreal ry,
const QColor &c, int lineWidth, const QBrush *fill)
{
qDrawPlainRoundedRect(p, r.x(), r.y(), r.width(), r.height(), rx, ry, c,
lineWidth, fill);
}
/*!
\class QTileRules

View File

@ -71,6 +71,12 @@ Q_WIDGETS_EXPORT void qDrawPlainRect(QPainter *p, int x, int y, int w, int h, co
Q_WIDGETS_EXPORT void qDrawPlainRect(QPainter *p, const QRect &r, const QColor &,
int lineWidth = 1, const QBrush *fill = nullptr);
Q_WIDGETS_EXPORT void qDrawPlainRoundedRect(QPainter *p, int x, int y, int w, int h,
qreal rx, qreal ry, const QColor &, int lineWidth = 1,
const QBrush *fill = nullptr);
Q_WIDGETS_EXPORT void qDrawPlainRoundedRect(QPainter *p, const QRect& r, qreal rx, qreal ry,
const QColor &, int lineWidth = 1, const QBrush *fill = nullptr);
struct QTileRules