From 79e51fcd67b5c07f0afbad797f5a02be33b34f2d Mon Sep 17 00:00:00 2001 From: Danny Wensley Date: Mon, 27 May 2024 19:37:52 +0100 Subject: [PATCH 1/4] Add user-configurable summary to unlock screen. --- src/core/Database.cpp | 30 +++++++++ src/core/Database.h | 5 ++ src/gui/DatabaseOpenWidget.cpp | 24 +++++++ src/gui/DatabaseOpenWidget.ui | 18 ++++- .../DatabaseSettingsWidgetGeneral.cpp | 17 +++++ .../DatabaseSettingsWidgetGeneral.h | 3 + .../DatabaseSettingsWidgetGeneral.ui | 67 ++++++++++++++++++- src/gui/styles/base/basestyle.qss | 2 +- src/gui/styles/base/classicstyle.qss | 2 +- 9 files changed, 164 insertions(+), 4 deletions(-) diff --git a/src/core/Database.cpp b/src/core/Database.cpp index b91601256e..c6375a414a 100644 --- a/src/core/Database.cpp +++ b/src/core/Database.cpp @@ -1060,3 +1060,33 @@ bool Database::isTemporaryDatabase() { return m_isTemporaryDatabase; } + +QString Database::publicSummary() +{ + if (!publicCustomData().contains("KPXC_PUBLIC_SUMMARY")) { + return QString(); + } + + return publicCustomData()["KPXC_PUBLIC_SUMMARY"].toString(); +} + +void Database::setPublicSummary(const QString& newSummary) +{ + publicCustomData().insert("KPXC_PUBLIC_SUMMARY", newSummary); + markAsModified(); +} + +QString Database::publicColor() +{ + if (!publicCustomData().contains("KPXC_PUBLIC_COLOR")) { + return QString(); + } + + return publicCustomData()["KPXC_PUBLIC_COLOR"].toString(); +} + +void Database::setPublicColor(const QString& newSummary) +{ + publicCustomData().insert("KPXC_PUBLIC_COLOR", newSummary); + markAsModified(); +} diff --git a/src/core/Database.h b/src/core/Database.h index d4e8aac2ab..3a6b1a439a 100644 --- a/src/core/Database.h +++ b/src/core/Database.h @@ -108,6 +108,11 @@ class Database : public ModifiableObject QString canonicalFilePath() const; void setFilePath(const QString& filePath); + QString publicSummary(); + void setPublicSummary(const QString& newSummary); + QString publicColor(); + void setPublicColor(const QString& newSummary); + Metadata* metadata(); const Metadata* metadata() const; Group* rootGroup(); diff --git a/src/gui/DatabaseOpenWidget.cpp b/src/gui/DatabaseOpenWidget.cpp index 5d45b3531b..40051b42f5 100644 --- a/src/gui/DatabaseOpenWidget.cpp +++ b/src/gui/DatabaseOpenWidget.cpp @@ -74,6 +74,8 @@ DatabaseOpenWidget::DatabaseOpenWidget(QWidget* parent) m_ui->labelHeadline->setFont(font); m_ui->labelHeadline->setText(tr("Unlock KeePassXC Database")); + m_ui->publicSummaryLabel->setVisible(false); + m_ui->quickUnlockButton->setFont(font); m_ui->quickUnlockButton->setIcon( icons()->icon("fingerprint", true, palette().color(QPalette::Active, QPalette::HighlightedText))); @@ -229,6 +231,28 @@ void DatabaseOpenWidget::load(const QString& filename) m_ui->fileNameLabel->setRawText(m_filename); + if (!m_db->publicSummary().isEmpty()) { + m_ui->publicSummaryLabel->setVisible(true); + m_ui->publicSummaryLabel->setText(m_db->publicSummary()); + } + + m_ui->publicSummaryLabel->setStyleSheet(""); + + if (!m_db->publicColor().isEmpty()) { + QColor userColor = QColor(m_db->publicColor()); + + if (userColor.isValid()) { + float luminance = (0.299 * userColor.redF() + 0.587 * userColor.greenF() + 0.114 * userColor.blueF()); + + QColor textColor = Qt::white; + if (luminance > 0.5) { + textColor = Qt::black; + } + + m_ui->publicSummaryLabel->setStyleSheet(QString("background-color:%1;color:%2;border-color:%1;").arg(userColor.name(), textColor.name())); + } + } + if (config()->get(Config::RememberLastKeyFiles).toBool()) { auto lastKeyFiles = config()->get(Config::LastKeyFiles).toHash(); if (lastKeyFiles.contains(m_filename)) { diff --git a/src/gui/DatabaseOpenWidget.ui b/src/gui/DatabaseOpenWidget.ui index a045ba82ce..aecffe7f30 100644 --- a/src/gui/DatabaseOpenWidget.ui +++ b/src/gui/DatabaseOpenWidget.ui @@ -40,7 +40,7 @@ - + @@ -91,6 +91,22 @@ + + + + QFrame::StyledPanel + + + publicSummary + + + Qt::AlignCenter + + + 10 + + + diff --git a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp index 84b903b5c2..f794cbe7b6 100644 --- a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp +++ b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp @@ -18,6 +18,8 @@ #include "DatabaseSettingsWidgetGeneral.h" #include "ui_DatabaseSettingsWidgetGeneral.h" +#include + #include "core/Clock.h" #include "core/Group.h" #include "core/Metadata.h" @@ -29,6 +31,8 @@ DatabaseSettingsWidgetGeneral::DatabaseSettingsWidgetGeneral(QWidget* parent) { m_ui->setupUi(this); + connect(m_ui->dbPublicColorChooseButton, SIGNAL(clicked()), SLOT(pickColor())); + connect(m_ui->historyMaxItemsCheckBox, SIGNAL(toggled(bool)), m_ui->historyMaxItemsSpinBox, SLOT(setEnabled(bool))); connect(m_ui->historyMaxSizeCheckBox, SIGNAL(toggled(bool)), m_ui->historyMaxSizeSpinBox, SLOT(setEnabled(bool))); connect(m_ui->autosaveDelayCheckBox, SIGNAL(toggled(bool)), m_ui->autosaveDelaySpinBox, SLOT(setEnabled(bool))); @@ -46,6 +50,9 @@ void DatabaseSettingsWidgetGeneral::initialize() m_ui->defaultUsernameEdit->setText(meta->defaultUserName()); m_ui->compressionCheckbox->setChecked(m_db->compressionAlgorithm() != Database::CompressionNone); + m_ui->dbPublicSummary->setText(m_db->publicSummary()); + m_ui->dbPublicColor->setText(m_db->publicColor()); + if (meta->historyMaxItems() > -1) { m_ui->historyMaxItemsSpinBox->setValue(meta->historyMaxItems()); m_ui->historyMaxItemsCheckBox->setChecked(true); @@ -116,6 +123,9 @@ bool DatabaseSettingsWidgetGeneral::saveSettings() meta->setRecycleBinEnabled(m_ui->recycleBinEnabledCheckBox->isChecked()); meta->setSettingsChanged(Clock::currentDateTimeUtc()); + m_db->setPublicSummary(m_ui->dbPublicSummary->text()); + m_db->setPublicColor(m_ui->dbPublicColor->text()); + bool truncate = false; int historyMaxItems; @@ -155,3 +165,10 @@ bool DatabaseSettingsWidgetGeneral::saveSettings() return true; } + +void DatabaseSettingsWidgetGeneral::pickColor() +{ + QColor oldColor = QColor(m_ui->dbPublicColor->text()); + QColor newColor = QColorDialog::getColor(oldColor); + m_ui->dbPublicColor->setText(newColor.name()); +} diff --git a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h index 548490cf0d..cce66bb291 100644 --- a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h +++ b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h @@ -40,6 +40,9 @@ public slots: void uninitialize() override; bool saveSettings() override; +private slots: + void pickColor(); + protected: void showEvent(QShowEvent* event) override; diff --git a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui index 939b699631..0cf5fd16f4 100644 --- a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui +++ b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui @@ -7,7 +7,7 @@ 0 0 453 - 394 + 647 @@ -92,6 +92,71 @@ + + + + Public Database Metadata + + + + + + Warning: the following settings are stored unencrypted. + + + + + + + 0 + + + + + Database summary: + + + + + + + Database summary field + + + + + + + Database color: + + + + + + + 0 + + + + + Database color field + + + + + + + Pick color... + + + + + + + + + + diff --git a/src/gui/styles/base/basestyle.qss b/src/gui/styles/base/basestyle.qss index ee0fa4e021..8d40281a38 100644 --- a/src/gui/styles/base/basestyle.qss +++ b/src/gui/styles/base/basestyle.qss @@ -38,7 +38,7 @@ EntryPreviewWidget TagsEdit padding-left: 0px; } -DatabaseOpenWidget #centralStack { +DatabaseOpenWidget #centralStack, DatabaseOpenWidget #publicSummaryLabel { border: 1px solid palette(mid); background: palette(light); } diff --git a/src/gui/styles/base/classicstyle.qss b/src/gui/styles/base/classicstyle.qss index d0ab2b88fc..72308f39e2 100644 --- a/src/gui/styles/base/classicstyle.qss +++ b/src/gui/styles/base/classicstyle.qss @@ -1,4 +1,4 @@ -DatabaseOpenWidget #centralStack { +DatabaseOpenWidget #centralStack, DatabaseOpenWidget #publicSummaryLabel { border: 2px groove palette(mid); background: palette(light); } From d68a1fc6b9887b266a1f18c9eedd2868ff867fad Mon Sep 17 00:00:00 2001 From: Jonathan White Date: Sat, 1 Jun 2024 23:04:36 -0400 Subject: [PATCH 2/4] Improved interface and cleanup --- share/translations/keepassxc_en.ts | 36 +++++++++ src/core/Database.cpp | 42 +++++----- src/core/Database.h | 6 +- src/gui/DatabaseOpenWidget.cpp | 30 +++---- src/gui/DatabaseOpenWidget.ui | 68 ++++++++++------ .../DatabaseSettingsWidgetGeneral.cpp | 29 +++++-- .../DatabaseSettingsWidgetGeneral.h | 10 ++- .../DatabaseSettingsWidgetGeneral.ui | 80 +++++++++++++------ 8 files changed, 196 insertions(+), 105 deletions(-) diff --git a/share/translations/keepassxc_en.ts b/share/translations/keepassxc_en.ts index 7180159138..55e22dbff5 100644 --- a/share/translations/keepassxc_en.ts +++ b/share/translations/keepassxc_en.ts @@ -2194,6 +2194,42 @@ removed from the database. Autosave delay since last change checkbox + + Public Database Metadata + + + + Warning: the following settings are not encrypted. + + + + Display name: + + + + Publically visible display name used on the unlock dialog + + + + Database public display name + + + + Display color: + + + + Publically visible color used on the unlock dialog + + + + Database public display color chooser + + + + Clear + + DatabaseSettingsWidgetKeeShare diff --git a/src/core/Database.cpp b/src/core/Database.cpp index c6375a414a..4cccdbf61e 100644 --- a/src/core/Database.cpp +++ b/src/core/Database.cpp @@ -1051,42 +1051,42 @@ QUuid Database::publicUuid() return QUuid::fromRfc4122(publicCustomData()["KPXC_PUBLIC_UUID"].toByteArray()); } -void Database::markAsTemporaryDatabase() +QString Database::publicName() { - m_isTemporaryDatabase = true; + return publicCustomData().value("KPXC_PUBLIC_NAME").toString(); } -bool Database::isTemporaryDatabase() +void Database::setPublicName(const QString& name) { - return m_isTemporaryDatabase; + if (name.isEmpty()) { + publicCustomData().remove("KPXC_PUBLIC_NAME"); + } else { + publicCustomData().insert("KPXC_PUBLIC_NAME", name); + } + markAsModified(); } -QString Database::publicSummary() +QString Database::publicColor() { - if (!publicCustomData().contains("KPXC_PUBLIC_SUMMARY")) { - return QString(); - } - - return publicCustomData()["KPXC_PUBLIC_SUMMARY"].toString(); + return publicCustomData().value("KPXC_PUBLIC_COLOR").toString(); } -void Database::setPublicSummary(const QString& newSummary) +void Database::setPublicColor(const QString& color) { - publicCustomData().insert("KPXC_PUBLIC_SUMMARY", newSummary); + if (color.isEmpty()) { + publicCustomData().remove("KPXC_PUBLIC_COLOR"); + } else { + publicCustomData().insert("KPXC_PUBLIC_COLOR", color); + } markAsModified(); } -QString Database::publicColor() +void Database::markAsTemporaryDatabase() { - if (!publicCustomData().contains("KPXC_PUBLIC_COLOR")) { - return QString(); - } - - return publicCustomData()["KPXC_PUBLIC_COLOR"].toString(); + m_isTemporaryDatabase = true; } -void Database::setPublicColor(const QString& newSummary) +bool Database::isTemporaryDatabase() { - publicCustomData().insert("KPXC_PUBLIC_COLOR", newSummary); - markAsModified(); + return m_isTemporaryDatabase; } diff --git a/src/core/Database.h b/src/core/Database.h index 3a6b1a439a..7b4efc003e 100644 --- a/src/core/Database.h +++ b/src/core/Database.h @@ -108,10 +108,10 @@ class Database : public ModifiableObject QString canonicalFilePath() const; void setFilePath(const QString& filePath); - QString publicSummary(); - void setPublicSummary(const QString& newSummary); + QString publicName(); + void setPublicName(const QString& name); QString publicColor(); - void setPublicColor(const QString& newSummary); + void setPublicColor(const QString& color); Metadata* metadata(); const Metadata* metadata() const; diff --git a/src/gui/DatabaseOpenWidget.cpp b/src/gui/DatabaseOpenWidget.cpp index 40051b42f5..ba524fd80f 100644 --- a/src/gui/DatabaseOpenWidget.cpp +++ b/src/gui/DatabaseOpenWidget.cpp @@ -72,9 +72,6 @@ DatabaseOpenWidget::DatabaseOpenWidget(QWidget* parent) font.setPointSize(font.pointSize() + 4); font.setBold(true); m_ui->labelHeadline->setFont(font); - m_ui->labelHeadline->setText(tr("Unlock KeePassXC Database")); - - m_ui->publicSummaryLabel->setVisible(false); m_ui->quickUnlockButton->setFont(font); m_ui->quickUnlockButton->setIcon( @@ -231,27 +228,18 @@ void DatabaseOpenWidget::load(const QString& filename) m_ui->fileNameLabel->setRawText(m_filename); - if (!m_db->publicSummary().isEmpty()) { - m_ui->publicSummaryLabel->setVisible(true); - m_ui->publicSummaryLabel->setText(m_db->publicSummary()); + auto label = tr("Unlock KeePassXC Database"); + if (!m_db->publicName().isEmpty()) { + label.append(QString(": %1").arg(m_db->publicName())); } + m_ui->labelHeadline->setText(label); - m_ui->publicSummaryLabel->setStyleSheet(""); - - if (!m_db->publicColor().isEmpty()) { - QColor userColor = QColor(m_db->publicColor()); + auto color = m_db->publicColor(); + m_ui->displayColorLabel->setVisible(!color.isEmpty()); + m_ui->displayColorLabel->setStyleSheet( + QString("background: %1; border: 1px solid palette(dark); border-radius: 4px").arg(color)); - if (userColor.isValid()) { - float luminance = (0.299 * userColor.redF() + 0.587 * userColor.greenF() + 0.114 * userColor.blueF()); - - QColor textColor = Qt::white; - if (luminance > 0.5) { - textColor = Qt::black; - } - - m_ui->publicSummaryLabel->setStyleSheet(QString("background-color:%1;color:%2;border-color:%1;").arg(userColor.name(), textColor.name())); - } - } + // m_ui->centralStack->setStyleSheet(QString("QStackedWidget {border: 4px solid %1}").arg(color)); if (config()->get(Config::RememberLastKeyFiles).toBool()) { auto lastKeyFiles = config()->get(Config::LastKeyFiles).toHash(); diff --git a/src/gui/DatabaseOpenWidget.ui b/src/gui/DatabaseOpenWidget.ui index aecffe7f30..7e882dcbee 100644 --- a/src/gui/DatabaseOpenWidget.ui +++ b/src/gui/DatabaseOpenWidget.ui @@ -55,16 +55,52 @@ - - - - 12 - 75 - true - + + + 9 + + + + + + 12 + 75 + true + + + + Unlock KeePassXC Database + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + + 16777215 + 8 + + + + background:cyan; border: 1px solid black; border-radius: 4px - Unlock KeePassXC Database + @@ -91,22 +127,6 @@ - - - - QFrame::StyledPanel - - - publicSummary - - - Qt::AlignCenter - - - 10 - - - diff --git a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp index f794cbe7b6..aa85a859db 100644 --- a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp +++ b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp @@ -31,7 +31,8 @@ DatabaseSettingsWidgetGeneral::DatabaseSettingsWidgetGeneral(QWidget* parent) { m_ui->setupUi(this); - connect(m_ui->dbPublicColorChooseButton, SIGNAL(clicked()), SLOT(pickColor())); + connect(m_ui->dbPublicColorButton, &QPushButton::clicked, this, &DatabaseSettingsWidgetGeneral::pickColor); + connect(m_ui->dbPublicColorClearButton, &QPushButton::clicked, this, [this] { setupColorButton({}); }); connect(m_ui->historyMaxItemsCheckBox, SIGNAL(toggled(bool)), m_ui->historyMaxItemsSpinBox, SLOT(setEnabled(bool))); connect(m_ui->historyMaxSizeCheckBox, SIGNAL(toggled(bool)), m_ui->historyMaxSizeSpinBox, SLOT(setEnabled(bool))); @@ -50,8 +51,8 @@ void DatabaseSettingsWidgetGeneral::initialize() m_ui->defaultUsernameEdit->setText(meta->defaultUserName()); m_ui->compressionCheckbox->setChecked(m_db->compressionAlgorithm() != Database::CompressionNone); - m_ui->dbPublicSummary->setText(m_db->publicSummary()); - m_ui->dbPublicColor->setText(m_db->publicColor()); + m_ui->dbPublicName->setText(m_db->publicName()); + setupColorButton(m_db->publicColor()); if (meta->historyMaxItems() > -1) { m_ui->historyMaxItemsSpinBox->setValue(meta->historyMaxItems()); @@ -123,8 +124,8 @@ bool DatabaseSettingsWidgetGeneral::saveSettings() meta->setRecycleBinEnabled(m_ui->recycleBinEnabledCheckBox->isChecked()); meta->setSettingsChanged(Clock::currentDateTimeUtc()); - m_db->setPublicSummary(m_ui->dbPublicSummary->text()); - m_db->setPublicColor(m_ui->dbPublicColor->text()); + m_db->setPublicName(m_ui->dbPublicName->text()); + m_db->setPublicColor(m_ui->dbPublicColorButton->property("color").toString()); bool truncate = false; @@ -168,7 +169,19 @@ bool DatabaseSettingsWidgetGeneral::saveSettings() void DatabaseSettingsWidgetGeneral::pickColor() { - QColor oldColor = QColor(m_ui->dbPublicColor->text()); - QColor newColor = QColorDialog::getColor(oldColor); - m_ui->dbPublicColor->setText(newColor.name()); + auto oldColor = QColor(m_ui->dbPublicColorButton->property("color").toString()); + setupColorButton(QColorDialog::getColor(oldColor)); +} + +void DatabaseSettingsWidgetGeneral::setupColorButton(const QColor& color) +{ + m_ui->dbPublicColorClearButton->setVisible(color.isValid()); + auto button = m_ui->dbPublicColorButton; + if (color.isValid()) { + button->setStyleSheet(QString("background-color:%1").arg(color.name())); + button->setProperty("color", color.name()); + } else { + button->setStyleSheet(""); + button->setProperty("color", {}); + } } diff --git a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h index cce66bb291..2089f9c3a5 100644 --- a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h +++ b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h @@ -20,6 +20,8 @@ #include "DatabaseSettingsWidget.h" +#include + class Database; namespace Ui { @@ -40,12 +42,14 @@ public slots: void uninitialize() override; bool saveSettings() override; -private slots: - void pickColor(); - protected: void showEvent(QShowEvent* event) override; +private slots: + void pickColor(); + void setupColorButton(const QColor& color); + +private: const QScopedPointer m_ui; }; diff --git a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui index 0cf5fd16f4..1c15cb2351 100644 --- a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui +++ b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui @@ -100,8 +100,13 @@ + + + true + + - Warning: the following settings are stored unencrypted. + Warning: the following settings are not encrypted. @@ -113,43 +118,68 @@ - Database summary: + Display name: - + + + Publically visible display name used on the unlock dialog + - Database summary field + Database public display name - Database color: + Display color: - - 0 - - + + + + 25 + 25 + + + + Publically visible color used on the unlock dialog + - Database color field + Database public display color chooser + + + - + - Pick color... + Clear + + + + Qt::Horizontal + + + + 40 + 20 + + + + @@ -178,6 +208,19 @@ of entries remain at most. + + + + Move entries to a recycle bin group +instead of deleting them from the database. +Entries deleted from the recycle bin are +removed from the database. + + + Use recycle bin + + + @@ -223,19 +266,6 @@ add up to the specified amount at most. - - - - Move entries to a recycle bin group -instead of deleting them from the database. -Entries deleted from the recycle bin are -removed from the database. - - - Use recycle bin - - - From e46b810786692a9c827aad13b72a7bfdf02cda33 Mon Sep 17 00:00:00 2001 From: Jonathan White Date: Sat, 10 Aug 2024 11:25:44 -0400 Subject: [PATCH 3/4] Place color around central widget instead of horizontal bar --- src/gui/DatabaseOpenWidget.cpp | 10 +++++----- src/gui/DatabaseOpenWidget.ui | 18 +----------------- 2 files changed, 6 insertions(+), 22 deletions(-) diff --git a/src/gui/DatabaseOpenWidget.cpp b/src/gui/DatabaseOpenWidget.cpp index ba524fd80f..72d349a996 100644 --- a/src/gui/DatabaseOpenWidget.cpp +++ b/src/gui/DatabaseOpenWidget.cpp @@ -235,11 +235,11 @@ void DatabaseOpenWidget::load(const QString& filename) m_ui->labelHeadline->setText(label); auto color = m_db->publicColor(); - m_ui->displayColorLabel->setVisible(!color.isEmpty()); - m_ui->displayColorLabel->setStyleSheet( - QString("background: %1; border: 1px solid palette(dark); border-radius: 4px").arg(color)); - - // m_ui->centralStack->setStyleSheet(QString("QStackedWidget {border: 4px solid %1}").arg(color)); + if (!color.isEmpty()) { + m_ui->centralStack->setStyleSheet(QString("QStackedWidget {border: 4px solid %1}").arg(color)); + } else { + m_ui->centralStack->setStyleSheet(""); + } if (config()->get(Config::RememberLastKeyFiles).toBool()) { auto lastKeyFiles = config()->get(Config::LastKeyFiles).toHash(); diff --git a/src/gui/DatabaseOpenWidget.ui b/src/gui/DatabaseOpenWidget.ui index 7e882dcbee..f9dc5b7619 100644 --- a/src/gui/DatabaseOpenWidget.ui +++ b/src/gui/DatabaseOpenWidget.ui @@ -40,7 +40,7 @@ - + @@ -88,22 +88,6 @@ - - - - - 16777215 - 8 - - - - background:cyan; border: 1px solid black; border-radius: 4px - - - - - - From 4382e18ae139fb8609ec47d4afc5a83358e4921b Mon Sep 17 00:00:00 2001 From: Jonathan White Date: Mon, 2 Sep 2024 16:30:34 -0400 Subject: [PATCH 4/4] Add database icon support --- share/translations/keepassxc_en.ts | 8 ++ src/core/Database.cpp | 18 ++++ src/core/Database.h | 2 + src/gui/DatabaseOpenWidget.cpp | 12 +++ src/gui/DatabaseOpenWidget.ui | 16 ++++ .../DatabaseSettingsWidgetGeneral.cpp | 88 ++++++++++++++++--- .../DatabaseSettingsWidgetGeneral.h | 6 +- .../DatabaseSettingsWidgetGeneral.ui | 54 +++++++++++- 8 files changed, 189 insertions(+), 15 deletions(-) diff --git a/share/translations/keepassxc_en.ts b/share/translations/keepassxc_en.ts index 55e22dbff5..daaa67606e 100644 --- a/share/translations/keepassxc_en.ts +++ b/share/translations/keepassxc_en.ts @@ -2230,6 +2230,14 @@ removed from the database. Clear + + Display icon: + + + + Select Database Icon + + DatabaseSettingsWidgetKeeShare diff --git a/src/core/Database.cpp b/src/core/Database.cpp index 4cccdbf61e..5734f9521d 100644 --- a/src/core/Database.cpp +++ b/src/core/Database.cpp @@ -1081,6 +1081,24 @@ void Database::setPublicColor(const QString& color) markAsModified(); } +int Database::publicIcon() +{ + if (publicCustomData().contains("KPXC_PUBLIC_ICON")) { + return publicCustomData().value("KPXC_PUBLIC_ICON").toInt(); + } + return -1; +} + +void Database::setPublicIcon(int iconIndex) +{ + if (iconIndex < 0) { + publicCustomData().remove("KPXC_PUBLIC_ICON"); + } else { + publicCustomData().insert("KPXC_PUBLIC_ICON", iconIndex); + } + markAsModified(); +} + void Database::markAsTemporaryDatabase() { m_isTemporaryDatabase = true; diff --git a/src/core/Database.h b/src/core/Database.h index 7b4efc003e..29314650e2 100644 --- a/src/core/Database.h +++ b/src/core/Database.h @@ -112,6 +112,8 @@ class Database : public ModifiableObject void setPublicName(const QString& name); QString publicColor(); void setPublicColor(const QString& color); + int publicIcon(); + void setPublicIcon(int iconIndex); Metadata* metadata(); const Metadata* metadata() const; diff --git a/src/gui/DatabaseOpenWidget.cpp b/src/gui/DatabaseOpenWidget.cpp index 72d349a996..14d8f4650e 100644 --- a/src/gui/DatabaseOpenWidget.cpp +++ b/src/gui/DatabaseOpenWidget.cpp @@ -228,12 +228,14 @@ void DatabaseOpenWidget::load(const QString& filename) m_ui->fileNameLabel->setRawText(m_filename); + // Set the public name if defined auto label = tr("Unlock KeePassXC Database"); if (!m_db->publicName().isEmpty()) { label.append(QString(": %1").arg(m_db->publicName())); } m_ui->labelHeadline->setText(label); + // Apply the public color to the central unlock stack if defined auto color = m_db->publicColor(); if (!color.isEmpty()) { m_ui->centralStack->setStyleSheet(QString("QStackedWidget {border: 4px solid %1}").arg(color)); @@ -241,6 +243,16 @@ void DatabaseOpenWidget::load(const QString& filename) m_ui->centralStack->setStyleSheet(""); } + // Show the database icon if defined + auto iconIndex = m_db->publicIcon(); + if (iconIndex >= 0 && iconIndex < databaseIcons()->count()) { + m_ui->dbIconLabel->setPixmap(databaseIcons()->icon(iconIndex, IconSize::Large)); + m_ui->dbIconLabel->setVisible(true); + } else { + m_ui->dbIconLabel->setPixmap({}); + m_ui->dbIconLabel->setVisible(false); + } + if (config()->get(Config::RememberLastKeyFiles).toBool()) { auto lastKeyFiles = config()->get(Config::LastKeyFiles).toHash(); if (lastKeyFiles.contains(m_filename)) { diff --git a/src/gui/DatabaseOpenWidget.ui b/src/gui/DatabaseOpenWidget.ui index f9dc5b7619..1ef04a5287 100644 --- a/src/gui/DatabaseOpenWidget.ui +++ b/src/gui/DatabaseOpenWidget.ui @@ -59,6 +59,22 @@ 9 + + + + + 32 + 32 + + + + + + + true + + + diff --git a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp index aa85a859db..c8a9ec8dcd 100644 --- a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp +++ b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.cpp @@ -19,10 +19,15 @@ #include "ui_DatabaseSettingsWidgetGeneral.h" #include +#include +#include +#include #include "core/Clock.h" #include "core/Group.h" #include "core/Metadata.h" +#include "gui/DatabaseIcons.h" +#include "gui/IconModels.h" #include "gui/MessageBox.h" DatabaseSettingsWidgetGeneral::DatabaseSettingsWidgetGeneral(QWidget* parent) @@ -31,8 +36,10 @@ DatabaseSettingsWidgetGeneral::DatabaseSettingsWidgetGeneral(QWidget* parent) { m_ui->setupUi(this); - connect(m_ui->dbPublicColorButton, &QPushButton::clicked, this, &DatabaseSettingsWidgetGeneral::pickColor); - connect(m_ui->dbPublicColorClearButton, &QPushButton::clicked, this, [this] { setupColorButton({}); }); + connect(m_ui->dbPublicColorButton, &QPushButton::clicked, this, &DatabaseSettingsWidgetGeneral::pickPublicColor); + connect(m_ui->dbPublicColorClearButton, &QPushButton::clicked, this, [this] { setupPublicColorButton({}); }); + connect(m_ui->dbPublicIconButton, &QPushButton::clicked, this, &DatabaseSettingsWidgetGeneral::pickPublicIcon); + connect(m_ui->dbPublicIconClearButton, &QPushButton::clicked, this, [this] { setupPublicIconButton(-1); }); connect(m_ui->historyMaxItemsCheckBox, SIGNAL(toggled(bool)), m_ui->historyMaxItemsSpinBox, SLOT(setEnabled(bool))); connect(m_ui->historyMaxSizeCheckBox, SIGNAL(toggled(bool)), m_ui->historyMaxSizeSpinBox, SLOT(setEnabled(bool))); @@ -52,7 +59,8 @@ void DatabaseSettingsWidgetGeneral::initialize() m_ui->compressionCheckbox->setChecked(m_db->compressionAlgorithm() != Database::CompressionNone); m_ui->dbPublicName->setText(m_db->publicName()); - setupColorButton(m_db->publicColor()); + setupPublicColorButton(m_db->publicColor()); + setupPublicIconButton(m_db->publicIcon()); if (meta->historyMaxItems() > -1) { m_ui->historyMaxItemsSpinBox->setValue(meta->historyMaxItems()); @@ -126,6 +134,7 @@ bool DatabaseSettingsWidgetGeneral::saveSettings() m_db->setPublicName(m_ui->dbPublicName->text()); m_db->setPublicColor(m_ui->dbPublicColorButton->property("color").toString()); + m_db->setPublicIcon(m_ui->dbPublicIconButton->property("iconIndex").toInt()); bool truncate = false; @@ -167,21 +176,78 @@ bool DatabaseSettingsWidgetGeneral::saveSettings() return true; } -void DatabaseSettingsWidgetGeneral::pickColor() +void DatabaseSettingsWidgetGeneral::pickPublicColor() { auto oldColor = QColor(m_ui->dbPublicColorButton->property("color").toString()); - setupColorButton(QColorDialog::getColor(oldColor)); + auto newColor = QColorDialog::getColor(oldColor); + if (newColor.isValid()) { + setupPublicColorButton(newColor); + } } -void DatabaseSettingsWidgetGeneral::setupColorButton(const QColor& color) +void DatabaseSettingsWidgetGeneral::setupPublicColorButton(const QColor& color) { m_ui->dbPublicColorClearButton->setVisible(color.isValid()); - auto button = m_ui->dbPublicColorButton; if (color.isValid()) { - button->setStyleSheet(QString("background-color:%1").arg(color.name())); - button->setProperty("color", color.name()); + m_ui->dbPublicColorButton->setStyleSheet(QString("background-color:%1").arg(color.name())); + m_ui->dbPublicColorButton->setProperty("color", color.name()); + } else { + m_ui->dbPublicColorButton->setStyleSheet(""); + m_ui->dbPublicColorButton->setProperty("color", {}); + } +} + +void DatabaseSettingsWidgetGeneral::pickPublicIcon() +{ + QDialog dialog(this); + dialog.setSizeGripEnabled(false); + dialog.setWindowTitle(tr("Select Database Icon")); + + auto iconList = new QListView; + iconList->setFlow(QListView::LeftToRight); + iconList->setMovement(QListView::Static); + iconList->setResizeMode(QListView::Adjust); + iconList->setWrapping(true); + iconList->setSpacing(4); + + auto iconModel = new DefaultIconModel; + iconList->setModel(iconModel); + if (m_ui->dbPublicIconButton->property("iconIndex").toInt() >= 0) { + iconList->setCurrentIndex(iconModel->index(m_ui->dbPublicIconButton->property("iconIndex").toInt(), 0)); + } else { + iconList->setCurrentIndex(iconModel->index(0, 0)); + } + + auto buttonBox = new QDialogButtonBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel); + auto layout = new QVBoxLayout(&dialog); + layout->addWidget(iconList); + layout->addWidget(buttonBox); + + // Resize the dialog to fit the default icon list + auto cellSize = iconList->sizeHintForIndex(iconModel->index(0, 0)); + auto spacing = iconList->spacing() * 2; + dialog.resize((cellSize.width() + spacing) * 15, (cellSize.height() + spacing) * 6 + 16); + + connect(iconList, &QListView::doubleClicked, &dialog, &QDialog::accept); + connect(buttonBox, &QDialogButtonBox::accepted, &dialog, &QDialog::accept); + connect(buttonBox, &QDialogButtonBox::rejected, &dialog, &QDialog::reject); + connect( + &dialog, &QDialog::accepted, this, [this, iconList] { setupPublicIconButton(iconList->currentIndex().row()); }); + + dialog.exec(); +} + +void DatabaseSettingsWidgetGeneral::setupPublicIconButton(int iconIndex) +{ + auto valid = iconIndex >= 0 && iconIndex < databaseIcons()->count(); + m_ui->dbPublicIconClearButton->setVisible(valid); + if (valid) { + m_ui->dbPublicIconButton->setIcon(databaseIcons()->icon(iconIndex)); + m_ui->dbPublicIconButton->setProperty("iconIndex", iconIndex); + m_ui->dbPublicIconClearButton->setVisible(true); } else { - button->setStyleSheet(""); - button->setProperty("color", {}); + m_ui->dbPublicIconButton->setIcon(QIcon()); + m_ui->dbPublicIconButton->setProperty("iconIndex", -1); + m_ui->dbPublicIconClearButton->setVisible(false); } } diff --git a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h index 2089f9c3a5..7c0c1ebe9a 100644 --- a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h +++ b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.h @@ -46,8 +46,10 @@ public slots: void showEvent(QShowEvent* event) override; private slots: - void pickColor(); - void setupColorButton(const QColor& color); + void pickPublicColor(); + void setupPublicColorButton(const QColor& color); + void pickPublicIcon(); + void setupPublicIconButton(int iconIndex); private: const QScopedPointer m_ui; diff --git a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui index 1c15cb2351..324ae6d3db 100644 --- a/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui +++ b/src/gui/dbsettings/DatabaseSettingsWidgetGeneral.ui @@ -145,8 +145,8 @@ - 25 - 25 + 30 + 30 @@ -182,6 +182,56 @@ + + + + Display icon: + + + + + + + + + + 30 + 30 + + + + + + + + 30 + 30 + + + + + + + + Clear + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + +