forked from qt-creator/qt-creator
Core: Add Core::Switch
New Component, implemented according to the design spec in Figma. Change-Id: I12e4882141a1f800b17175ca6dfc2f55517b7115 Reviewed-by: Cristian Adam <cristian.adam@qt.io>
This commit is contained in:
@@ -445,6 +445,95 @@ void ComboBox::paintEvent(QPaintEvent *)
|
|||||||
p.drawPixmap(iconPos, icon);
|
p.drawPixmap(iconPos, icon);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
constexpr TextFormat SwitchLabelTf
|
||||||
|
{Theme::Token_Text_Default, StyleHelper::UiElementLabelMedium};
|
||||||
|
constexpr QSize switchTrackS(32, 16);
|
||||||
|
|
||||||
|
Switch::Switch(const QString &text, QWidget *parent)
|
||||||
|
: QAbstractButton(parent)
|
||||||
|
{
|
||||||
|
setText(text);
|
||||||
|
setCheckable(true);
|
||||||
|
setAttribute(Qt::WA_Hover);
|
||||||
|
setSizePolicy(QSizePolicy::Preferred, QSizePolicy::MinimumExpanding);
|
||||||
|
setLayoutDirection(Qt::RightToLeft); // Switch right, label left
|
||||||
|
}
|
||||||
|
|
||||||
|
QSize Switch::sizeHint() const
|
||||||
|
{
|
||||||
|
const QFontMetrics fm(SwitchLabelTf.font());
|
||||||
|
const int textWidth = fm.horizontalAdvance(text());
|
||||||
|
const int width = switchTrackS.width() + HGapS + textWidth;
|
||||||
|
return {width, ExPaddingGapM + SwitchLabelTf.lineHeight() + ExPaddingGapM};
|
||||||
|
}
|
||||||
|
|
||||||
|
QSize Switch::minimumSizeHint() const
|
||||||
|
{
|
||||||
|
return switchTrackS;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Switch::paintEvent([[maybe_unused]] QPaintEvent *event)
|
||||||
|
{
|
||||||
|
const bool ltr = layoutDirection() == Qt::LeftToRight;
|
||||||
|
const int trackX = ltr ? 0 : width() - switchTrackS.width();
|
||||||
|
const int trackY = (height() - switchTrackS.height()) / 2;
|
||||||
|
const QRect trackR(QPoint(trackX, trackY), switchTrackS);
|
||||||
|
const int trackRounding = trackR.height() / 2;
|
||||||
|
const bool checkedEnabled = isChecked() && isEnabled();
|
||||||
|
QPainter p(this);
|
||||||
|
|
||||||
|
{ // track
|
||||||
|
const bool hovered = underMouse();
|
||||||
|
const QBrush fill = creatorColor(checkedEnabled ? (hovered ? Theme::Token_Accent_Subtle
|
||||||
|
: Theme::Token_Accent_Default)
|
||||||
|
: Theme::Token_Foreground_Subtle);
|
||||||
|
const QPen outline = checkedEnabled ? QPen(Qt::NoPen)
|
||||||
|
: creatorColor(hovered ? Theme::Token_Stroke_Muted
|
||||||
|
: Theme::Token_Stroke_Subtle);
|
||||||
|
drawCardBackground(&p, trackR, fill, outline, trackRounding);
|
||||||
|
}
|
||||||
|
{ // track label
|
||||||
|
const QColor color = creatorColor(isEnabled() ? (isChecked() ? Theme::Token_Basic_White
|
||||||
|
: Theme::Token_Text_Muted)
|
||||||
|
: Theme::Token_Text_Subtle);
|
||||||
|
const int labelS = 6;
|
||||||
|
const int labelY = (height() - labelS) / 2;
|
||||||
|
if (isChecked()) {
|
||||||
|
const QRect onLabelR(trackX + 8, labelY, 1, labelS);
|
||||||
|
p.fillRect(onLabelR, color);
|
||||||
|
} else {
|
||||||
|
const QRect offLabelR(trackX + switchTrackS.width() - trackRounding - labelS / 2 - 1,
|
||||||
|
labelY, labelS, labelS);
|
||||||
|
drawCardBackground(&p, offLabelR, Qt::NoBrush, color, labelS / 2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
{ // knob
|
||||||
|
const int thumbPadding = checkedEnabled ? 3 : 2;
|
||||||
|
const int thumbH = switchTrackS.height() - thumbPadding - thumbPadding;
|
||||||
|
const int thumbW = isDown() ? (checkedEnabled ? 17 : 19)
|
||||||
|
: thumbH;
|
||||||
|
const int thumbRounding = thumbH / 2;
|
||||||
|
const int thumbX = trackX + (isChecked() ? switchTrackS.width() - thumbW - thumbPadding
|
||||||
|
: thumbPadding);
|
||||||
|
const QRect thumbR(thumbX, trackY + thumbPadding, thumbW, thumbH);
|
||||||
|
const QBrush fill = creatorColor(isEnabled() ? Theme::Token_Basic_White
|
||||||
|
: Theme::Token_Foreground_Default);
|
||||||
|
const QPen outline = checkedEnabled ? QPen(Qt::NoPen)
|
||||||
|
: creatorColor(Theme::Token_Stroke_Subtle);
|
||||||
|
drawCardBackground(&p, thumbR, fill, outline, thumbRounding);
|
||||||
|
}
|
||||||
|
{ // switch text label
|
||||||
|
const int switchAndGapWidth = switchTrackS.width() + HGapS;
|
||||||
|
const QRect textR(ltr ? switchAndGapWidth : 0, 0, width() - switchAndGapWidth,
|
||||||
|
trackY + switchTrackS.height());
|
||||||
|
p.setFont(SwitchLabelTf.font());
|
||||||
|
p.setPen(isEnabled() ? SwitchLabelTf.color() : creatorColor(Theme::Token_Text_Subtle));
|
||||||
|
const QString elidedLabel =
|
||||||
|
p.fontMetrics().elidedText(text(), Qt::ElideRight, textR.width());
|
||||||
|
p.drawText(textR, SwitchLabelTf.drawTextFlags, elidedLabel);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
GridView::GridView(QWidget *parent)
|
GridView::GridView(QWidget *parent)
|
||||||
: QListView(parent)
|
: QListView(parent)
|
||||||
{
|
{
|
||||||
|
@@ -141,6 +141,18 @@ protected:
|
|||||||
void leaveEvent(QEvent *event) override;
|
void leaveEvent(QEvent *event) override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class CORE_EXPORT Switch : public QAbstractButton
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
explicit Switch(const QString &text, QWidget *parent = nullptr);
|
||||||
|
|
||||||
|
QSize sizeHint() const override;
|
||||||
|
QSize minimumSizeHint() const override;
|
||||||
|
|
||||||
|
protected:
|
||||||
|
void paintEvent(QPaintEvent *event) override;
|
||||||
|
};
|
||||||
|
|
||||||
class CORE_EXPORT GridView : public QListView
|
class CORE_EXPORT GridView : public QListView
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
@@ -17,6 +17,11 @@ QWidget *widgets()
|
|||||||
const QStringList content = QColor::colorNames();
|
const QStringList content = QColor::colorNames();
|
||||||
comboBox->addItems(content.first(8));
|
comboBox->addItems(content.first(8));
|
||||||
|
|
||||||
|
auto switchOn = new Core::Switch("Qt::RightToLeft");
|
||||||
|
switchOn->setChecked(true);
|
||||||
|
auto switchOff = new Core::Switch("Qt::LeftToRight");
|
||||||
|
switchOff->setLayoutDirection(Qt::LeftToRight);
|
||||||
|
|
||||||
using namespace Layouting;
|
using namespace Layouting;
|
||||||
Column {
|
Column {
|
||||||
Group {
|
Group {
|
||||||
@@ -50,6 +55,13 @@ QWidget *widgets()
|
|||||||
comboBox,
|
comboBox,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
Group {
|
||||||
|
title("Core::Switch"),
|
||||||
|
Column {
|
||||||
|
switchOn,
|
||||||
|
switchOff,
|
||||||
|
},
|
||||||
|
},
|
||||||
}.attachTo(widget);
|
}.attachTo(widget);
|
||||||
|
|
||||||
return widget;
|
return widget;
|
||||||
|
Reference in New Issue
Block a user