Skip to content

Commit

Permalink
Merge pull request #13669 from acolombier/feat/controller-setting-fil…
Browse files Browse the repository at this point in the history
…e-and-color

feat: add file and color controller setting types
  • Loading branch information
Swiftb0y authored Nov 22, 2024
2 parents 2f04ffc + b59c0cb commit 894e96f
Show file tree
Hide file tree
Showing 4 changed files with 387 additions and 15 deletions.
56 changes: 56 additions & 0 deletions res/controllers/Dummy Device Screen.hid.xml
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,62 @@
<product protocol="hid" vendor_id="0xdead" product_id="0xbeaf" />
</devices>
</info>
<settings>
<group label="Cosmetic">
<row orientation="vertical">
<option
variable="theme"
type="enum"
label="Theme use for the screen">
<description>
The theme used for the screens
</description>
<value label="Classic" default="true">stock</value>
<value label="Advanced">advanced</value>
</option>
<option
variable="idleBackground"
type="file"
pattern="Images (*.png *.gif *.jpg)"
label="Idle deck background">
<description>
The background used for empty decks
</description>
</option>
<option
variable="accentColor"
type="color"
default="orange"
label="Accent color">
<description>
The background used for empty decks
</description>
</option>
<option
variable="deckA"
type="enum"
label="Deck A">
<value color="#FF0000" label="Red">red</value>
<value color="#FF5E00" label="Carrot">carrot</value>
<value color="#FF7800" label="Orange">orange</value>
<value color="#FF9200" label="Honey">honey</value>
<value color="#FFFF00" label="Yellow">yellow</value>
<value color="#81FF00" label="Lime">lime</value>
<value color="#00FF00" label="Green">green</value>
<value color="#00FF49" label="Aqua">aqua</value>
<value color="#00FFFF" label="Celeste">celeste</value>
<value color="#0091FF" label="Sky">sky</value>
<value color="#0000FF" label="Blue">blue</value>
<value color="#FF00FF" label="Purple">purple</value>
<value color="#FF0091" label="Fuscia">fuscia</value>
<value color="#FF0079" label="Magenta">magenta</value>
<value color="#FF477E" label="Azalea">azalea</value>
<value color="#FF4761" label="Salmon">salmon</value>
<value color="#FFFFFF" label="White">white</value>
</option>
</row>
</group>
</settings>
<controller id="DummyDevice">
<screens>
<screen identifier="main" width="480" height="360" targetFps="20" pixelType="RBGA" splashoff="500" />
Expand Down
172 changes: 167 additions & 5 deletions src/controllers/legacycontrollersettings.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,19 @@

#include <util/assert.h>

#include <QBoxLayout>
#include <QCheckBox>
#include <QColorDialog>
#include <QComboBox>
#include <QDoubleSpinBox>
#include <QFileDialog>
#include <QLabel>
#include <QLayout>
#include <QPainter>
#include <QPixmap>
#include <QPushButton>
#include <QSpinBox>
#include <QStringLiteral>

#include "moc_legacycontrollersettings.cpp"

Expand Down Expand Up @@ -54,6 +61,8 @@ LegacyControllerSettingBuilder::LegacyControllerSettingBuilder() {
registerType<LegacyControllerIntegerSetting>();
registerType<LegacyControllerRealSetting>();
registerType<LegacyControllerEnumSetting>();
registerType<LegacyControllerColorSetting>();
registerType<LegacyControllerFileSetting>();
}

AbstractLegacyControllerSetting::AbstractLegacyControllerSetting(const QDomElement& element) {
Expand Down Expand Up @@ -225,7 +234,15 @@ LegacyControllerEnumSetting::LegacyControllerEnumSetting(
!value.isNull();
value = value.nextSiblingElement("value")) {
QString val = value.text();
m_options.append(std::tuple<QString, QString>(val, value.attribute("label", val)));
QColor color = QColor(value.attribute("color"));
// TODO: Remove once we mandate GCC 10/Clang 16
#if defined(__cpp_aggregate_paren_init) && \
__cpp_aggregate_paren_init >= 201902L && \
!defined(_MSC_VER) // FIXME: Bug in MSVC preventing the use of this feature
m_options.emplace_back(val, value.attribute("label", val), color);
#else
m_options.emplace_back(Item{val, value.attribute("label", val), color});
#endif
if (value.hasAttribute("default")) {
m_defaultValue = pos;
}
Expand All @@ -243,8 +260,8 @@ void LegacyControllerEnumSetting::parse(const QString& in, bool* ok) {
save();

size_t pos = 0;
for (const auto& value : std::as_const(m_options)) {
if (std::get<0>(value) == in) {
for (const auto& item : std::as_const(m_options)) {
if (item.value == in) {
if (ok != nullptr) {
*ok = true;
}
Expand All @@ -259,8 +276,15 @@ void LegacyControllerEnumSetting::parse(const QString& in, bool* ok) {
QWidget* LegacyControllerEnumSetting::buildInputWidget(QWidget* pParent) {
auto* pComboBox = new QComboBox(pParent);

for (const auto& value : std::as_const(m_options)) {
pComboBox->addItem(std::get<1>(value));
for (const auto& item : std::as_const(m_options)) {
if (item.color.isValid()) {
QPixmap icon(24, 24);
QPainter painter(&icon);
painter.fillRect(0, 0, 24, 24, item.color);
pComboBox->addItem(QIcon(icon), item.label);
} else {
pComboBox->addItem(item.label);
}
}
pComboBox->setCurrentIndex(static_cast<int>(m_editedValue));

Expand All @@ -278,3 +302,141 @@ QWidget* LegacyControllerEnumSetting::buildInputWidget(QWidget* pParent) {

return pComboBox;
}

LegacyControllerColorSetting::LegacyControllerColorSetting(
const QDomElement& element)
: AbstractLegacyControllerSetting(element),
m_defaultValue(QColor(element.attribute("default"))),
m_savedValue(m_defaultValue),
m_editedValue(m_defaultValue) {
reset();
save();
}

LegacyControllerColorSetting::~LegacyControllerColorSetting() = default;

void LegacyControllerColorSetting::parse(const QString& in, bool* ok) {
if (ok != nullptr) {
*ok = false;
}
reset();
save();

m_savedValue = QColor(in);
if (ok != nullptr) {
*ok = m_editedValue.isValid();
}
if (!m_editedValue.isValid()) {
return;
}
m_editedValue = m_savedValue;
}

QWidget* LegacyControllerColorSetting::buildInputWidget(QWidget* pParent) {
auto* pPushButton = new QPushButton(tr("Change color"), pParent);

auto setColorIcon = [pPushButton](const QColor& color) {
QPixmap icon(24, 24);
QPainter painter(&icon);
painter.fillRect(0, 0, 24, 24, color);
pPushButton->setIcon(QIcon(icon));
};

connect(this,
&AbstractLegacyControllerSetting::valueReset,
pPushButton,
[this, pPushButton, setColorIcon]() {
if (m_editedValue.isValid()) {
setColorIcon(m_editedValue);
} else {
pPushButton->setIcon(QIcon());
}
});

connect(pPushButton, &QPushButton::clicked, this, [this, pPushButton, setColorIcon](bool) {
auto color = QColorDialog::getColor(m_editedValue, pPushButton, tr("Choose a new color"));
if (color.isValid()) {
m_editedValue = color;
setColorIcon(color);
emit changed();
}
});

if (m_savedValue.isValid()) {
setColorIcon(m_savedValue);
}

return pPushButton;
}

LegacyControllerFileSetting::LegacyControllerFileSetting(
const QDomElement& element)
: AbstractLegacyControllerSetting(element),
m_fileFilter(element.attribute("pattern")),
m_defaultValue(QFileInfo(element.attribute("default"))),
m_savedValue(m_defaultValue),
m_editedValue(m_defaultValue) {
reset();
save();
}
LegacyControllerFileSetting::~LegacyControllerFileSetting() = default;

void LegacyControllerFileSetting::parse(const QString& in, bool* ok) {
if (ok != nullptr) {
*ok = false;
}
reset();
save();

m_editedValue = QFileInfo(in);
if (ok != nullptr) {
*ok = m_editedValue.exists();
}
if (!m_editedValue.exists()) {
return;
}
m_savedValue = m_editedValue;
}

QWidget* LegacyControllerFileSetting::buildInputWidget(QWidget* pParent) {
auto* pWidget = new QWidget(pParent);
pWidget->setLayout(new QHBoxLayout);
auto* pPushButton = new QPushButton(tr("Browse..."), pWidget);
auto* pLabel = new QLabel(pWidget);
auto setLabelText = [pLabel](QString&& text) {
pLabel->setText(QStringLiteral("<i>%1</i>").arg(text));
};
pWidget->layout()->addWidget(pLabel);
pWidget->layout()->addWidget(pPushButton);

connect(this, &AbstractLegacyControllerSetting::valueReset, pLabel, [this, setLabelText]() {
if (m_editedValue.exists()) {
setLabelText(m_editedValue.absoluteFilePath());
} else {
setLabelText(tr("No file selected"));
}
});

connect(pPushButton,
&QPushButton::clicked,
this,
[this, pLabel, pPushButton](bool) {
auto file = QFileInfo(QFileDialog::getOpenFileName(pPushButton,
tr("Select a file"),
QString(),
m_fileFilter));
if (file.exists()) {
m_editedValue = file;
pLabel->setText(QStringLiteral("<i>%1</i>").arg(file.absoluteFilePath()));
emit changed();
}
});

if (m_savedValue.exists()) {
setLabelText(m_savedValue.absoluteFilePath());
} else {
setLabelText(tr("No file selected"));
}

return pWidget;
}
Loading

0 comments on commit 894e96f

Please sign in to comment.