From 4114823b3e8d00087eb67631fb98465944059581 Mon Sep 17 00:00:00 2001 From: Ilya Panov <89508801+mirotvoretts@users.noreply.github.com> Date: Sat, 5 Apr 2025 13:24:42 +0300 Subject: [PATCH 01/17] docs: update installation guide and add screenshot --- README.md | 17 +++++++---------- 1 file changed, 7 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index d2242e4..5e9cacd 100644 --- a/README.md +++ b/README.md @@ -39,15 +39,7 @@ GRANT ALL PRIVILEGES ON DATABASE efficio TO efficio; \q ``` -4. Enter under **efficio** profile - -```bash -psql -U efficio -d efficio -h localhost -``` - -> After that run the server on address **localhost** and **port** 5432 in your pgAdmin4 - -5. Build and start app +4. Build and start app ```bash mkdir -p build && cd build @@ -56,6 +48,11 @@ make ./EfficioTaskTracker -platform xcb ``` +## Current result + + + + ## Technologies Used - Qt 6.8.2 - PostgreSQL 17.4 @@ -64,4 +61,4 @@ make ## License -This project is licensed under the **MIT License**. See the [LICENSE](https://github.com/toximu/efficio-task-tracker/blob/main/LICENSE) file for details. \ No newline at end of file +This project is licensed under the **MIT License**. See the [LICENSE](https://github.com/toximu/efficio-task-tracker/blob/main/LICENSE) file for details. From 3d06e251d23bc5fd07b0ea0282be86775dcf170c Mon Sep 17 00:00:00 2001 From: Ilya Panov <89508801+mirotvoretts@users.noreply.github.com> Date: Thu, 10 Apr 2025 23:11:37 +0300 Subject: [PATCH 02/17] docs: update building app guide --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 5e9cacd..cbfcd75 100644 --- a/README.md +++ b/README.md @@ -30,6 +30,8 @@ git clone git@github.com:toximu/efficio-task-tracker.git sudo service postgresql start && sudo -u postgres psql ``` +> If you use fish shell, replace `service` with `systemctl` + 3. Create **efficio** user ```SQL From 69edfb7591027829178d832cc7ac63817b2ceee2 Mon Sep 17 00:00:00 2001 From: tima bytsan <86739929+toximu@users.noreply.github.com> Date: Thu, 10 Apr 2025 23:17:00 +0300 Subject: [PATCH 03/17] return main.cpp --- main.cpp | 34 ++++++++++++++++++++++++++++++++++ 1 file changed, 34 insertions(+) create mode 100644 main.cpp diff --git a/main.cpp b/main.cpp new file mode 100644 index 0000000..91bce06 --- /dev/null +++ b/main.cpp @@ -0,0 +1,34 @@ +#include +#include +#include +#include +#include +#include "applicationwindow.h" +#include "login_window.h" +#include "mainwindow.h" + +int main(int argc, char *argv[]) { + QApplication application(argc, argv); + + QTranslator translator; + const QStringList ui_languages = QLocale::system().uiLanguages(); + for (const QString &locale : ui_languages) { + const QString base_name = "MainWindow_" + QLocale(locale).name(); + if (translator.load(":/i18n/" + base_name)) { + QApplication::installTranslator(&translator); + break; + } + } + + auto *app_window = new Ui::ApplicationWindow("EFFICIO"); + auto *login_window = new LoginWindow(app_window); + + app_window->setCentralWidget(login_window); + const QRect screen_geometry = QApplication::primaryScreen()->availableGeometry(); + const int x = (screen_geometry.width() - login_window->width()) / 2; + const int y = (screen_geometry.height() - login_window->height()) / 2; + app_window->move(x, y); + app_window->show(); + + return QApplication::exec(); +} From 34b3b8d594dd7991546e01286fe10b5d5d1e1ced Mon Sep 17 00:00:00 2001 From: MuravAna Date: Fri, 11 Apr 2025 15:39:03 +0300 Subject: [PATCH 04/17] Changes in login_window style: add 4 new themes, but have bug because of gradient --- .../include/login_window.h | 10 +- .../include/login_window_style_sheet.h | 387 +++++++++++++++--- .../include/registration_window_style_sheet.h | 58 ++- ui/authorization-windows/src/login_window.cpp | 32 +- .../src/registration_window.cpp | 2 +- ui/authorization-windows/ui/login_window.ui | 22 + 6 files changed, 451 insertions(+), 60 deletions(-) diff --git a/ui/authorization-windows/include/login_window.h b/ui/authorization-windows/include/login_window.h index 5aed300..c2c4746 100644 --- a/ui/authorization-windows/include/login_window.h +++ b/ui/authorization-windows/include/login_window.h @@ -7,26 +7,30 @@ #include #include "database_manager.hpp" #include "lr_dao.hpp" +#include QT_BEGIN_NAMESPACE - namespace Ui { class LoginWindow; } - QT_END_NAMESPACE class LoginWindow : public QWidget { Q_OBJECT public: - explicit LoginWindow(QWidget *parent = nullptr); + explicit LoginWindow(QWidget *parent = nullptr, int number_of_theme_ = 3); ~LoginWindow(); + + static const std::vector THEMES; private slots: void on_switch_mode_clicked(); void on_push_enter_clicked(); + void on_switch_theme_clicked(); private: Ui::LoginWindow *ui; + int number_of_theme; + int counter_on_switch_theme_clicks = 0; }; \ No newline at end of file diff --git a/ui/authorization-windows/include/login_window_style_sheet.h b/ui/authorization-windows/include/login_window_style_sheet.h index f5cb58a..1641a4a 100644 --- a/ui/authorization-windows/include/login_window_style_sheet.h +++ b/ui/authorization-windows/include/login_window_style_sheet.h @@ -3,54 +3,343 @@ #include "ui_login_window.h" namespace Ui { -QString login_window_light_theme = R"( - QWidget { - background-color: #f5f5f5; - } - - QLabel { - font-family: 'Arial'; - font-size: 13px; - color: #089083; - padding: 1px; - } - - QPushButton#pushEnter { - font-family: 'Arial'; - border-radius: 10px; - background-color: #fea36b; - color: white; - padding: 5px 10px; - } - - QPushButton#switchMode { - font-family: 'Arial'; - border-radius: 10px; - background-color: white; - color: #fea36b; - padding: 5px 10px; - } - - QPushButton#pushEnter:hover { - background-color: #d58745; - } - - QPushButton#switchMode:hover { - background-color: #dadada; - } - - QLineEdit { - border-radius: 10px; - border: 1px solid white; - background: white; - color: black; - padding: 5px; - } - - QLineEdit::placeholder { - color: #727272; - } - -)"; + QString login_window_light_autumn_theme = R"( + QWidget { + background-color: #f5f5f5; + } + + QLabel { + background-color: transparent; + font-family: 'Arial'; + font-size: 13px; + color: #089083; + padding: 1px; + } + + QPushButton#pushEnter { + font-family: 'Arial'; + border-radius: 10px; + background-color: #fea36b; + color: white; + padding: 5px 10px; + } + + QPushButton#switchMode { + font-family: 'Arial'; + border-radius: 10px; + background-color: white; + color: #fea36b; + padding: 5px 10px; + } + + QPushButton#pushEnter:hover { + background-color: #d58745; + } + + QPushButton#switchMode:hover { + background-color: #dadada; + } + + QLineEdit { + border-radius: 10px; + border: 1px solid white; + background: white; + color: black; + padding: 5px; + } + + QLineEdit::placeholder { + color: #727272; + } + QPushButton#switch_theme { + background-color: rgb(163, 162, 162); + border-radius: 9px; + border: 2px solid #089083; + padding: 5px; + } + QPushButton::hover#switch_theme { + background-color: #089083; + } + QPushButton::pressed#switch_theme { + background-color:rgb(7, 110, 100); + } + + )"; + + QString login_window_dark_autumn_theme = R"( + QWidget { + background-color: #202020; + } + + QLabel { + background-color: transparent; + font-family: 'Arial'; + font-size: 13px; + color: #089083; + padding: 1px; + } + + QPushButton#pushEnter { + font-family: 'Arial'; + border-radius: 10px; + background-color: #fea36b; + color: #263238; + padding: 5px 10px; + } + + QPushButton#pushEnter:hover { + background-color:rgb(225, 133, 76); + } + + QPushButton#switchMode { + font-family: 'Arial'; + border-radius: 10px; + background-color: #089083; + color: white; + padding: 5px 10px; + } + + QPushButton#switchMode:hover { + background-color: #01635d; + } + + QLineEdit { + border-radius: 10px; + border: 1px solid rgb(0, 0, 0); + background:rgb(0, 0, 0); + color: #727272; + padding: 5px; + } + + QLineEdit::placeholder { + color: #727272; + } + + QPushButton#switch_theme { + background-color: #202020; + border-radius: 9px; + border: 2px solid #089083; + padding: 5px; + } + QPushButton::hover#switch_theme { + background-color: #089083; + } + QPushButton::pressed#switch_theme { + background-color:rgb(13, 93, 85); + } + )"; + + + + QString login_window_light_purple_theme = R"( + QWidget { + background: qlineargradient(x1:0, y1:0, x2:0, y2:1, + stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(103, 88, 126)); + margin: 0; + padding: 0; + border: none; + } + + QLabel { + background-color: transparent; + font-family: 'Arial'; + font-size: 13px; + color: rgb(42, 10, 25); + padding: 1px; + } + + QPushButton#pushEnter { + font-family: 'Arial'; + border-radius: 10px; + background-color: #722548; + color:rgb(206, 193, 224); + padding: 5px 10px; + } + + QPushButton#pushEnter:hover { + background-color:rgb(98, 27, 59) + } + + QPushButton#switchMode { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: rgb(218, 207, 235); + padding: 5px 10px; + } + + QPushButton#switchMode:hover { + background-color:rgb(27, 6, 16); + } + + QLineEdit { + border-radius: 10px; + border: 1px solid rgb(221, 210, 238); + background: rgb(221, 210, 238); + color: #221932; + padding: 5px; + } + + QLineEdit::placeholder { + color: white; + } + + QPushButton#switch_theme { + background-color: #9882B9; + border-radius: 9px; + border: 2px solid #060407; + padding: 5px; + } + QPushButton::hover#switch_theme { + background-color: #060407; + } + QPushButton::pressed#switch_theme { + background-color:rgb(2, 0, 2); + } + )"; + + QString login_window_dark_purple_theme = R"( + QWidget { + background-color:rgb(9, 6, 10); + } + + QLabel { + background-color: transparent; + font-family: 'Arial'; + font-size: 13px; + color: #9882B9; + padding: 1px; + } + + QPushButton#pushEnter { + font-family: 'Arial'; + border-radius: 10px; + background-color: #722548; + color: #060407; + padding: 5px 10px; + } + + QPushButton#pushEnter:hover { + background-color:rgb(98, 27, 59) + } + + QPushButton#switchMode { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: #9882B9; + padding: 5px 10px; + } + + QPushButton#switchMode:hover { + background-color:rgb(27, 6, 16); + } + + QLineEdit { + border-radius: 10px; + border: 1px solid #221932; + background: #221932; + color: #9882B9; + padding: 5px; + } + + QLineEdit::placeholder { + color: white; + } + + QPushButton#switch_theme { + background-color: #060407; + border-radius: 9px; + border: 2px solid #9882B9; + padding: 5px; + } + QPushButton::hover#switch_theme { + background-color: #9882B9; + } + QPushButton::pressed#switch_theme { + background-color:rgb(113, 93, 143); + } + + )"; + + QString login_window_nature_flat_theme = R"( + QWidget { + background: qlineargradient(x1:0, y1:0, x2:0, y2:1, + stop:0 #173C4C, stop:0.5 #326D6C, stop:1 #07142B); + margin: 0; + padding: 0; + border: none; + } + + QLabel { + background-color: transparent; + font-family: 'Arial'; + font-size: 13px; + color: #BDD1BD; + padding: 1px; + } + + QPushButton#pushEnter { + font-family: 'Arial'; + border-radius: 10px; + background-color: #568F7C; + color: #BDD1BD; + padding: 5px 10px; + border: none; + font-weight: bold; + } + + QPushButton#pushEnter:hover { + background-color: #326D6C; + } + + QPushButton#pushEnter:pressed { + background-color: #07142B; + } + + QPushButton#switchMode { + font-family: 'Arial'; + border-radius: 10px; + background-color: #326D6C; + color: #BDD1BD; + padding: 5px 10px; + border: 1px solid #568F7C; + } + + QPushButton#switchMode:hover { + background-color: #568F7C; + color: #07142B; + } + + QLineEdit { + border-radius: 10px; + border: 1px solid #568F7C; + background: #07142B; + color: #BDD1BD; + padding: 5px; + selection-background-color: #326D6C; + } + + QLineEdit::placeholder { + color: #85B093; + opacity: 0.7; + } + + QPushButton#switch_theme { + background-color: #173C4C; + border-radius: 9px; + border: 2px solid #85B093; + padding: 5px; + color: #BDD1BD; + } + + QPushButton#switch_theme:hover { + background-color: #85B093; + } + + QPushButton#switch_theme:pressed { + background-color:rgb(107, 141, 118); + } + )"; } // namespace Ui \ No newline at end of file diff --git a/ui/authorization-windows/include/registration_window_style_sheet.h b/ui/authorization-windows/include/registration_window_style_sheet.h index d17480e..8045fa9 100644 --- a/ui/authorization-windows/include/registration_window_style_sheet.h +++ b/ui/authorization-windows/include/registration_window_style_sheet.h @@ -3,13 +3,65 @@ #include "ui_registration_window.h" namespace Ui { -QString registration_window_light_theme = R"( + QString registration_window_light_theme = R"( + QWidget { + background-color: #f5f5f5; + } + + QLabel { + font-family: 'Arial'; + background-color: transparent; + font-size: 13px; + color: #089083; + padding: 1px; + } + + QPushButton#pushRegistration { + font-family: 'Arial'; + border-radius: 10px; + background-color: #fea36b; + color: white; + padding: 5px 10px; + } + + QPushButton#switchMode { + font-family: 'Arial'; + border-radius: 10px; + background-color: white; + color: #fea36b; + padding: 5px 10px; + } + + QPushButton#pushRegistration:hover { + background-color: #d58745; + } + + QPushButton#switchMode:hover { + background-color: #dadada; + } + + QLineEdit { + border-radius: 10px; + border: 1px solid white; + background: white; + color: black; + padding: 5px; + } + + QLineEdit::placeholder { + color: #727272; + } + + )"; + +QString registration_window_dark_autumm_theme = R"( QWidget { - background-color: #f5f5f5; + background-color: #121318; } QLabel { font-family: 'Arial'; + background-color: transparent; font-size: 13px; color: #089083; padding: 1px; @@ -36,7 +88,7 @@ QString registration_window_light_theme = R"( } QPushButton#switchMode:hover { - background-color: #dadada; + background-color: #300B1C; } QLineEdit { diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index 0583ef5..ac83043 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -10,21 +10,30 @@ #include "applicationwindow.h" #include "bottombar.h" #include "database_manager.hpp" -#include "login_window_style_sheet.h" #include "lr_dao.hpp" #include "mainwindow.h" #include "notelist.h" #include "registration_window.h" #include "serialization.hpp" +#include "login_window_style_sheet.h" + +const std::vector LoginWindow::THEMES = { + Ui::login_window_light_autumn_theme, + Ui::login_window_dark_autumn_theme, + Ui::login_window_dark_purple_theme, + Ui::login_window_light_purple_theme, + Ui::login_window_nature_flat_theme +}; -LoginWindow::LoginWindow(QWidget *parent) - : QWidget(parent), ui(new Ui::LoginWindow) { +LoginWindow::LoginWindow(QWidget *parent, int number_of_theme_) + : QWidget(parent), ui(new Ui::LoginWindow), number_of_theme(number_of_theme_) { ui->setupUi(this); setFixedSize(380, 480); ui->inputLogin->setPlaceholderText("Введите логин:"); ui->inputPassword->setPlaceholderText("Введите пароль:"); - setStyleSheet(Ui::login_window_light_theme); + + setStyleSheet(THEMES[number_of_theme_]); ui->inputPassword->setEchoMode(QLineEdit::Password); connect( @@ -35,6 +44,10 @@ LoginWindow::LoginWindow(QWidget *parent) ui->pushEnter, &QPushButton::clicked, this, &LoginWindow::on_push_enter_clicked ); + connect( + ui->switch_theme, &QPushButton::clicked, this, + &LoginWindow::on_switch_theme_clicked + ); } LoginWindow::~LoginWindow() { @@ -115,4 +128,15 @@ void LoginWindow::on_push_enter_clicked() { this, "Ошибка ввода данных", "Пожалуйста, заполните все поля!" ); } +} + +void LoginWindow::on_switch_theme_clicked() { + // Attention: костыль. + // Почему-то кнопка switch_theme дважды кликается, + // из-за чего темы переключаются не подряд, а через одну. + // Поэтому ведем счетчик кликов и только на нечетных переключаем тему. + if ((this->counter_on_switch_theme_clicks++)%2){ + this->number_of_theme = (this->number_of_theme+1)%THEMES.size(); + setStyleSheet(THEMES[this->number_of_theme]); + } } \ No newline at end of file diff --git a/ui/authorization-windows/src/registration_window.cpp b/ui/authorization-windows/src/registration_window.cpp index f30f7d8..f59ad6a 100644 --- a/ui/authorization-windows/src/registration_window.cpp +++ b/ui/authorization-windows/src/registration_window.cpp @@ -25,7 +25,7 @@ RegistrationWindow::RegistrationWindow(QWidget *parent) ui->createLogin->setPlaceholderText("Введите логин:"); ui->createPassword->setPlaceholderText("Введите пароль:"); ui->repeatPassword->setPlaceholderText("Повторите пароль:"); - setStyleSheet(Ui::registration_window_light_theme); + setStyleSheet(Ui::registration_window_dark_autumm_theme); ui->createPassword->setEchoMode(QLineEdit::Password); ui->repeatPassword->setEchoMode(QLineEdit::Password); diff --git a/ui/authorization-windows/ui/login_window.ui b/ui/authorization-windows/ui/login_window.ui index 02ffce3..4fb7339 100644 --- a/ui/authorization-windows/ui/login_window.ui +++ b/ui/authorization-windows/ui/login_window.ui @@ -104,6 +104,28 @@ border-radius: 10px; Еще нет аккаунта? Зарегистрируйтесь! + + + + 350 + 455 + 20 + 20 + + + + + 20 + 20 + + + + + 20 + 20 + + + From e7c2a9a29dd6e560d2bff0f80070463dfafabe7f Mon Sep 17 00:00:00 2001 From: MuravAna Date: Sat, 12 Apr 2025 01:37:17 +0300 Subject: [PATCH 05/17] Update of themes in AutorizationWindows and MainWindow --- .../include/login_window.h | 2 +- .../include/login_window_style_sheet.h | 58 +- .../include/registration_window.h | 7 +- .../include/registration_window_style_sheet.h | 339 ++++++++-- ui/authorization-windows/src/login_window.cpp | 27 +- .../src/registration_window.cpp | 61 +- ui/authorization-windows/ui/login_window.ui | 12 +- .../ui/registration_window.ui | 40 +- ui/main-window/include/main_window_style.hpp | 604 +++++++++++++++++- ui/main-window/include/mainwindow.h | 8 +- ui/main-window/src/mainwindow.cpp | 35 +- .../include/note_edit_dialog_styles.h | 15 +- ui/note-widget/src/note_edit_dialog.cpp | 2 +- ui/note-widget/ui/note_edit_dialog.ui | 2 +- 14 files changed, 1071 insertions(+), 141 deletions(-) diff --git a/ui/authorization-windows/include/login_window.h b/ui/authorization-windows/include/login_window.h index c2c4746..584cd9c 100644 --- a/ui/authorization-windows/include/login_window.h +++ b/ui/authorization-windows/include/login_window.h @@ -19,7 +19,7 @@ class LoginWindow : public QWidget { Q_OBJECT public: - explicit LoginWindow(QWidget *parent = nullptr, int number_of_theme_ = 3); + explicit LoginWindow(QWidget *parent = nullptr, int number_of_theme_ = 0); ~LoginWindow(); static const std::vector THEMES; diff --git a/ui/authorization-windows/include/login_window_style_sheet.h b/ui/authorization-windows/include/login_window_style_sheet.h index 1641a4a..79e9a42 100644 --- a/ui/authorization-windows/include/login_window_style_sheet.h +++ b/ui/authorization-windows/include/login_window_style_sheet.h @@ -16,7 +16,7 @@ namespace Ui { padding: 1px; } - QPushButton#pushEnter { + QPushButton#push_enter { font-family: 'Arial'; border-radius: 10px; background-color: #fea36b; @@ -24,7 +24,7 @@ namespace Ui { padding: 5px 10px; } - QPushButton#switchMode { + QPushButton#switch_mode { font-family: 'Arial'; border-radius: 10px; background-color: white; @@ -32,11 +32,11 @@ namespace Ui { padding: 5px 10px; } - QPushButton#pushEnter:hover { + QPushButton#push_enter:hover { background-color: #d58745; } - QPushButton#switchMode:hover { + QPushButton#switch_mode:hover { background-color: #dadada; } @@ -53,7 +53,7 @@ namespace Ui { } QPushButton#switch_theme { - background-color: rgb(163, 162, 162); + background-color: transparent; border-radius: 9px; border: 2px solid #089083; padding: 5px; @@ -80,7 +80,7 @@ namespace Ui { padding: 1px; } - QPushButton#pushEnter { + QPushButton#push_enter { font-family: 'Arial'; border-radius: 10px; background-color: #fea36b; @@ -88,11 +88,11 @@ namespace Ui { padding: 5px 10px; } - QPushButton#pushEnter:hover { + QPushButton#push_enter:hover { background-color:rgb(225, 133, 76); } - QPushButton#switchMode { + QPushButton#switch_mode { font-family: 'Arial'; border-radius: 10px; background-color: #089083; @@ -100,7 +100,7 @@ namespace Ui { padding: 5px 10px; } - QPushButton#switchMode:hover { + QPushButton#switch_mode:hover { background-color: #01635d; } @@ -117,7 +117,7 @@ namespace Ui { } QPushButton#switch_theme { - background-color: #202020; + background-color: transparent; border-radius: 9px; border: 2px solid #089083; padding: 5px; @@ -130,11 +130,9 @@ namespace Ui { } )"; - - QString login_window_light_purple_theme = R"( QWidget { - background: qlineargradient(x1:0, y1:0, x2:0, y2:1, + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(103, 88, 126)); margin: 0; padding: 0; @@ -149,7 +147,7 @@ namespace Ui { padding: 1px; } - QPushButton#pushEnter { + QPushButton#push_enter { font-family: 'Arial'; border-radius: 10px; background-color: #722548; @@ -157,11 +155,11 @@ namespace Ui { padding: 5px 10px; } - QPushButton#pushEnter:hover { + QPushButton#push_enter:hover { background-color:rgb(98, 27, 59) } - QPushButton#switchMode { + QPushButton#switch_mode { font-family: 'Arial'; border-radius: 10px; background-color: rgb(42, 10, 25); @@ -169,7 +167,7 @@ namespace Ui { padding: 5px 10px; } - QPushButton#switchMode:hover { + QPushButton#switch_mode:hover { background-color:rgb(27, 6, 16); } @@ -186,7 +184,7 @@ namespace Ui { } QPushButton#switch_theme { - background-color: #9882B9; + background-color: transparent; border-radius: 9px; border: 2px solid #060407; padding: 5px; @@ -212,7 +210,7 @@ namespace Ui { padding: 1px; } - QPushButton#pushEnter { + QPushButton#push_enter { font-family: 'Arial'; border-radius: 10px; background-color: #722548; @@ -220,11 +218,11 @@ namespace Ui { padding: 5px 10px; } - QPushButton#pushEnter:hover { + QPushButton#push_enter:hover { background-color:rgb(98, 27, 59) } - QPushButton#switchMode { + QPushButton#switch_mode { font-family: 'Arial'; border-radius: 10px; background-color: rgb(42, 10, 25); @@ -232,7 +230,7 @@ namespace Ui { padding: 5px 10px; } - QPushButton#switchMode:hover { + QPushButton#switch_mode:hover { background-color:rgb(27, 6, 16); } @@ -249,7 +247,7 @@ namespace Ui { } QPushButton#switch_theme { - background-color: #060407; + background-color: transparent; border-radius: 9px; border: 2px solid #9882B9; padding: 5px; @@ -265,7 +263,7 @@ namespace Ui { QString login_window_nature_flat_theme = R"( QWidget { - background: qlineargradient(x1:0, y1:0, x2:0, y2:1, + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, stop:0 #173C4C, stop:0.5 #326D6C, stop:1 #07142B); margin: 0; padding: 0; @@ -280,7 +278,7 @@ namespace Ui { padding: 1px; } - QPushButton#pushEnter { + QPushButton#push_enter { font-family: 'Arial'; border-radius: 10px; background-color: #568F7C; @@ -290,15 +288,15 @@ namespace Ui { font-weight: bold; } - QPushButton#pushEnter:hover { + QPushButton#push_enter:hover { background-color: #326D6C; } - QPushButton#pushEnter:pressed { + QPushButton#push_enter:pressed { background-color: #07142B; } - QPushButton#switchMode { + QPushButton#switch_mode { font-family: 'Arial'; border-radius: 10px; background-color: #326D6C; @@ -307,7 +305,7 @@ namespace Ui { border: 1px solid #568F7C; } - QPushButton#switchMode:hover { + QPushButton#switch_mode:hover { background-color: #568F7C; color: #07142B; } @@ -327,7 +325,7 @@ namespace Ui { } QPushButton#switch_theme { - background-color: #173C4C; + background-color: transparent; border-radius: 9px; border: 2px solid #85B093; padding: 5px; diff --git a/ui/authorization-windows/include/registration_window.h b/ui/authorization-windows/include/registration_window.h index 35f4bc4..968c333 100644 --- a/ui/authorization-windows/include/registration_window.h +++ b/ui/authorization-windows/include/registration_window.h @@ -5,6 +5,7 @@ #include #include "database_manager.hpp" #include "lr_dao.hpp" +#include QT_BEGIN_NAMESPACE @@ -18,14 +19,18 @@ class RegistrationWindow : public QWidget { Q_OBJECT public: - explicit RegistrationWindow(QWidget *parent = nullptr); + explicit RegistrationWindow(QWidget *parent = nullptr, int number_of_theme_ = 0); ~RegistrationWindow(); bool is_strong_and_valid_password(const QString &password); + static const std::vector THEMES; private slots: void on_switch_mode_clicked(); void on_push_registration_clicked(); + void on_switch_theme_clicked(); private: Ui::RegistrationWindow *ui; + int number_of_theme; + int counter_on_switch_theme_clicks = 0; }; \ No newline at end of file diff --git a/ui/authorization-windows/include/registration_window_style_sheet.h b/ui/authorization-windows/include/registration_window_style_sheet.h index 8045fa9..1b8e177 100644 --- a/ui/authorization-windows/include/registration_window_style_sheet.h +++ b/ui/authorization-windows/include/registration_window_style_sheet.h @@ -3,7 +3,7 @@ #include "ui_registration_window.h" namespace Ui { - QString registration_window_light_theme = R"( + QString registration_window_light_autumn_theme = R"( QWidget { background-color: #f5f5f5; } @@ -16,7 +16,7 @@ namespace Ui { padding: 1px; } - QPushButton#pushRegistration { + QPushButton#push_registration { font-family: 'Arial'; border-radius: 10px; background-color: #fea36b; @@ -24,7 +24,7 @@ namespace Ui { padding: 5px 10px; } - QPushButton#switchMode { + QPushButton#switch_mode { font-family: 'Arial'; border-radius: 10px; background-color: white; @@ -32,11 +32,11 @@ namespace Ui { padding: 5px 10px; } - QPushButton#pushRegistration:hover { + QPushButton#push_registration:hover { background-color: #d58745; } - QPushButton#switchMode:hover { + QPushButton#switch_mode:hover { background-color: #dadada; } @@ -51,58 +51,289 @@ namespace Ui { QLineEdit::placeholder { color: #727272; } - + + QPushButton#switch_theme { + background-color: transparent; + border-radius: 9px; + border: 2px solid #089083; + padding: 5px; + } + QPushButton::hover#switch_theme { + background-color: #089083; + } + QPushButton::pressed#switch_theme { + background-color:rgb(7, 110, 100); + } )"; - -QString registration_window_dark_autumm_theme = R"( - QWidget { - background-color: #121318; - } - - QLabel { - font-family: 'Arial'; - background-color: transparent; - font-size: 13px; - color: #089083; - padding: 1px; - } - - QPushButton#pushRegistration { - font-family: 'Arial'; - border-radius: 10px; - background-color: #fea36b; - color: white; - padding: 5px 10px; - } - - QPushButton#switchMode { - font-family: 'Arial'; - border-radius: 10px; - background-color: white; - color: #fea36b; - padding: 5px 10px; - } - - QPushButton#pushRegistration:hover { - background-color: #d58745; - } - QPushButton#switchMode:hover { - background-color: #300B1C; - } - - QLineEdit { - border-radius: 10px; - border: 1px solid white; - background: white; - color: black; - padding: 5px; - } + QString registration_window_dark_autumn_theme = R"( + QWidget { + background-color: #202020; + } + + QLabel { + font-family: 'Arial'; + background-color: transparent; + font-size: 13px; + color: #089083; + padding: 1px; + } + + QPushButton#push_registration { + font-family: 'Arial'; + border-radius: 10px; + background-color: #fea36b; + color: #263238; + padding: 5px 10px; + } + + QPushButton#push_registration:hover { + background-color: rgb(225, 133, 76); + } + + QPushButton#switch_mode { + font-family: 'Arial'; + border-radius: 10px; + background-color: #089083; + color: white; + padding: 5px 10px; + } + + QPushButton#switch_mode:hover { + background-color: #01635d; + } + + QLineEdit { + border-radius: 10px; + border: 1px solid rgb(0, 0, 0); + background: rgb(0, 0, 0); + color: #727272; + padding: 5px; + } + + QLineEdit::placeholder { + color: #727272; + } + + QPushButton#switch_theme { + background-color: transparent; + border-radius: 9px; + border: 2px solid #089083; + padding: 5px; + } + QPushButton::hover#switch_theme { + background-color: #089083; + } + QPushButton::pressed#switch_theme { + background-color:rgb(13, 93, 85); + } + )"; - QLineEdit::placeholder { - color: #727272; - } + QString registration_window_light_purple_theme = R"( + QWidget { + background: qlineargradient(x1:0, y1:0, x2:0, y2:1, + stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(103, 88, 126)); + margin: 0; + padding: 0; + border: none; + } + + QLabel { + font-family: 'Arial'; + background-color: transparent; + font-size: 13px; + color: rgb(42, 10, 25); + padding: 1px; + } + + QPushButton#push_registration { + font-family: 'Arial'; + border-radius: 10px; + background-color: #722548; + color: rgb(206, 193, 224); + padding: 5px 10px; + } + + QPushButton#push_registration:hover { + background-color: rgb(98, 27, 59); + } + + QPushButton#switch_mode { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: rgb(218, 207, 235); + padding: 5px 10px; + } + + QPushButton#switch_mode:hover { + background-color: rgb(27, 6, 16); + } + + QLineEdit { + border-radius: 10px; + border: 1px solid rgb(221, 210, 238); + background: rgb(221, 210, 238); + color: #221932; + padding: 5px; + } + + QLineEdit::placeholder { + color: white; + } + + QPushButton#switch_theme { + background-color: transparent; + border-radius: 9px; + border: 2px solid #060407; + padding: 5px; + } + QPushButton::hover#switch_theme { + background-color: #060407; + } + QPushButton::pressed#switch_theme { + background-color:rgb(2, 0, 2); + } + )"; -)"; + QString registration_window_dark_purple_theme = R"( + QWidget { + background-color: rgb(9, 6, 10); + } + + QLabel { + font-family: 'Arial'; + background-color: transparent; + font-size: 13px; + color: #9882B9; + padding: 1px; + } + + QPushButton#push_registration { + font-family: 'Arial'; + border-radius: 10px; + background-color: #722548; + color: #060407; + padding: 5px 10px; + } + + QPushButton#push_registration:hover { + background-color: rgb(98, 27, 59); + } + + QPushButton#switch_mode { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: #9882B9; + padding: 5px 10px; + } + + QPushButton#switch_mode:hover { + background-color: rgb(27, 6, 16); + } + + QLineEdit { + border-radius: 10px; + border: 1px solid #221932; + background: #221932; + color: #9882B9; + padding: 5px; + } + + QLineEdit::placeholder { + color: white; + } + + QPushButton#switch_theme { + background-color: transparent; + border-radius: 9px; + border: 2px solid #9882B9; + padding: 5px; + } + QPushButton::hover#switch_theme { + background-color: #9882B9; + } + QPushButton::pressed#switch_theme { + background-color:rgb(113, 93, 143); + } + )"; + QString registration_window_nature_flat_theme = R"( + QWidget { + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, + stop:0 #173C4C, stop:0.5 #326D6C, stop:1 #07142B) !important; + margin: 0; + padding: 0; + border: none; + } + + QLabel { + font-family: 'Arial'; + background-color: transparent; + font-size: 13px; + color: #BDD1BD; + padding: 1px; + } + + QPushButton#push_registration { + font-family: 'Arial'; + border-radius: 10px; + background-color: #568F7C; + color: #BDD1BD; + padding: 5px 10px; + border: none; + font-weight: bold; + } + + QPushButton#push_registration:hover { + background-color: #326D6C; + } + + QPushButton#push_registration:pressed { + background-color: #07142B; + } + + QPushButton#switch_mode { + font-family: 'Arial'; + border-radius: 10px; + background-color: #326D6C; + color: #BDD1BD; + padding: 5px 10px; + border: 1px solid #568F7C; + } + + QPushButton#switch_mode:hover { + background-color: #568F7C; + color: #07142B; + } + + QLineEdit { + border-radius: 10px; + border: 1px solid #568F7C; + background: #07142B; + color: #BDD1BD; + padding: 5px; + selection-background-color: #326D6C; + } + + QLineEdit::placeholder { + color: #85B093; + opacity: 0.7; + } + + QPushButton#switch_theme { + background-color: transparent; + border-radius: 9px; + border: 2px solid #85B093; + padding: 5px; + color: #BDD1BD; + } + QPushButton::hover#switch_theme { + background-color: #85B093; + } + QPushButton::pressed#switch_theme { + background-color:rgb(107, 141, 118); + } + )"; } // namespace Ui \ No newline at end of file diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index ac83043..31b5b65 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -30,23 +30,24 @@ LoginWindow::LoginWindow(QWidget *parent, int number_of_theme_) ui->setupUi(this); setFixedSize(380, 480); - ui->inputLogin->setPlaceholderText("Введите логин:"); - ui->inputPassword->setPlaceholderText("Введите пароль:"); + ui->input_login->setPlaceholderText("Введите логин:"); + ui->input_password->setPlaceholderText("Введите пароль:"); + ui->input_password->setEchoMode(QLineEdit::Password); setStyleSheet(THEMES[number_of_theme_]); - ui->inputPassword->setEchoMode(QLineEdit::Password); connect( - ui->switchMode, &QPushButton::clicked, this, - &LoginWindow::on_switch_mode_clicked + ui->switch_theme, &QPushButton::clicked, this, + &LoginWindow::on_switch_theme_clicked ); + connect( - ui->pushEnter, &QPushButton::clicked, this, - &LoginWindow::on_push_enter_clicked + ui->switch_mode, &QPushButton::clicked, this, + &LoginWindow::on_switch_mode_clicked ); connect( - ui->switch_theme, &QPushButton::clicked, this, - &LoginWindow::on_switch_theme_clicked + ui->push_enter, &QPushButton::clicked, this, + &LoginWindow::on_push_enter_clicked ); } @@ -64,7 +65,7 @@ void LoginWindow::on_switch_mode_clicked() { } project_storage_model::Storage storage; RegistrationWindow *registration_window = - new RegistrationWindow(app_window); + new RegistrationWindow(app_window, this->number_of_theme); app_window->setCentralWidget(registration_window); QRect screenGeometry = QApplication::primaryScreen()->availableGeometry(); @@ -76,8 +77,8 @@ void LoginWindow::on_switch_mode_clicked() { } void LoginWindow::on_push_enter_clicked() { - QString login = ui->inputLogin->text(); - QString password = ui->inputPassword->text(); + QString login = ui->input_login->text(); + QString password = ui->input_password->text(); if (!login.isEmpty() && !password.isEmpty()) { if (login.size() > 50) { @@ -107,7 +108,7 @@ void LoginWindow::on_push_enter_clicked() { Serialization::get_storage(*storage, login.toStdString()); Ui::MainWindow *main_window = - new Ui::MainWindow(app_window, login.toStdString(), storage); + new Ui::MainWindow(app_window, login.toStdString(), storage, this->number_of_theme); app_window->setCentralWidget(main_window); app_window->resize(800, 600); diff --git a/ui/authorization-windows/src/registration_window.cpp b/ui/authorization-windows/src/registration_window.cpp index f59ad6a..97f595a 100644 --- a/ui/authorization-windows/src/registration_window.cpp +++ b/ui/authorization-windows/src/registration_window.cpp @@ -15,26 +15,42 @@ #include "notelist.h" #include "registration_window.h" #include "registration_window_style_sheet.h" - -RegistrationWindow::RegistrationWindow(QWidget *parent) - : QWidget(parent), ui(new Ui::RegistrationWindow) { +#include + +const std::vector RegistrationWindow::THEMES = { + Ui::registration_window_light_autumn_theme, + Ui::registration_window_dark_autumn_theme, + Ui::registration_window_dark_purple_theme, + Ui::registration_window_light_purple_theme, + Ui::registration_window_nature_flat_theme + }; + +RegistrationWindow::RegistrationWindow(QWidget *parent, int number_of_theme_) + : QWidget(parent), ui(new Ui::RegistrationWindow), number_of_theme(number_of_theme_) { ui->setupUi(this); setFixedSize(380, 480); - ui->createLogin->setPlaceholderText("Введите логин:"); - ui->createPassword->setPlaceholderText("Введите пароль:"); - ui->repeatPassword->setPlaceholderText("Повторите пароль:"); - setStyleSheet(Ui::registration_window_dark_autumm_theme); - ui->createPassword->setEchoMode(QLineEdit::Password); - ui->repeatPassword->setEchoMode(QLineEdit::Password); + ui->create_login->setPlaceholderText("Введите логин:"); + ui->create_password->setPlaceholderText("Введите пароль:"); + ui->repeat_password->setPlaceholderText("Повторите пароль:"); + ui->create_password->setEchoMode(QLineEdit::Password); + ui->repeat_password->setEchoMode(QLineEdit::Password); + + setStyleSheet(THEMES[number_of_theme_]); + setAttribute(Qt::WA_StyledBackground, true); + + connect( + ui->switch_theme, &QPushButton::clicked, this, + &RegistrationWindow::on_switch_theme_clicked + ); connect( - ui->pushRegistration, &QPushButton::clicked, this, + ui->push_registration, &QPushButton::clicked, this, &RegistrationWindow::on_push_registration_clicked ); connect( - ui->switchMode, &QPushButton::clicked, this, + ui->switch_mode, &QPushButton::clicked, this, &RegistrationWindow::on_switch_mode_clicked ); } @@ -52,7 +68,7 @@ void RegistrationWindow::on_switch_mode_clicked() { old->deleteLater(); } project_storage_model::Storage storage; - LoginWindow *login_window = new LoginWindow(app_window); + LoginWindow *login_window = new LoginWindow(app_window, number_of_theme); app_window->setCentralWidget(login_window); QRect screenGeometry = QApplication::primaryScreen()->availableGeometry(); @@ -108,9 +124,9 @@ bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { } void RegistrationWindow::on_push_registration_clicked() { - QString created_login = ui->createLogin->text(); - QString created_password = ui->createPassword->text(); - QString repeated_password = ui->repeatPassword->text(); + QString created_login = ui->create_login->text(); + QString created_password = ui->create_password->text(); + QString repeated_password = ui->repeat_password->text(); if (!created_login.isEmpty() && !created_password.isEmpty() && !repeated_password.isEmpty()) { @@ -132,7 +148,7 @@ void RegistrationWindow::on_push_registration_clicked() { if (try_register_user == 0) { QMessageBox::warning( this, "Ошибка", - "Извините, разрабы дауны и не подключили толком бд." + "Извините, внутренняя ошибка с базами данных." ); } else if (try_register_user == -1) { QMessageBox::warning( @@ -145,10 +161,21 @@ void RegistrationWindow::on_push_registration_clicked() { this, "Регистрация", "Вы успешно зарегистрировались! Пожалуйста, выполните вход." ); - on_switch_mode_clicked(); // TODO: fix + on_switch_mode_clicked(); } } } else { QMessageBox::warning(this, "Ошибка", "Пожалуйста, заполните все поля."); } +} + +void RegistrationWindow::on_switch_theme_clicked() { + // Attention: костыль. + // Почему-то кнопка switch_theme дважды кликается, + // из-за чего темы переключаются не подряд, а через одну. + // Поэтому ведем счетчик кликов и только на нечетных переключаем тему. + if ((this->counter_on_switch_theme_clicks++)%2){ + this->number_of_theme = (this->number_of_theme+1)%THEMES.size(); + setStyleSheet(THEMES[this->number_of_theme]); + } } \ No newline at end of file diff --git a/ui/authorization-windows/ui/login_window.ui b/ui/authorization-windows/ui/login_window.ui index 4fb7339..a9ea57e 100644 --- a/ui/authorization-windows/ui/login_window.ui +++ b/ui/authorization-windows/ui/login_window.ui @@ -22,7 +22,7 @@ 501 - + 120 @@ -39,10 +39,10 @@ border-radius: 10px; Войти - + - 140 + 133 130 91 41 @@ -55,7 +55,7 @@ border-radius: 10px; Вход - + 62 @@ -71,7 +71,7 @@ border-radius: 10px; Логин - + 62 @@ -87,7 +87,7 @@ border-radius: 10px; Пароль - + 80 diff --git a/ui/authorization-windows/ui/registration_window.ui b/ui/authorization-windows/ui/registration_window.ui index d0b20d4..0ba3e34 100644 --- a/ui/authorization-windows/ui/registration_window.ui +++ b/ui/authorization-windows/ui/registration_window.ui @@ -13,12 +13,34 @@ Dialog - + - 90 + 350 + 455 + 20 + 20 + + + + + 20 + 20 + + + + + 20 + 20 + + + + + + + 85 290 - 201 + 210 51 @@ -30,7 +52,7 @@ border-radius: 10px; Зарегистрироваться - + 110 @@ -47,7 +69,7 @@ border-radius: 10px; Уже есть аккаунт? Войдите! - + 60 @@ -57,7 +79,7 @@ border-radius: 10px; - + 60 @@ -67,7 +89,7 @@ border-radius: 10px; - + 60 @@ -77,10 +99,10 @@ border-radius: 10px; - + - 100 + 94 90 201 51 diff --git a/ui/main-window/include/main_window_style.hpp b/ui/main-window/include/main_window_style.hpp index 3e594c1..aa06013 100644 --- a/ui/main-window/include/main_window_style.hpp +++ b/ui/main-window/include/main_window_style.hpp @@ -4,7 +4,7 @@ namespace Ui { -QString main_window_style = R"( +QString main_window_light_autumn_theme = R"( #main-window { background-color : #f5f5f5; } @@ -42,7 +42,7 @@ QScrollArea { outline: 0; font-family: 'Arial'; font-weight: bold; - font-size: 14px; + font-size: 13px; color:rgb(44, 44, 44); } @@ -96,7 +96,7 @@ QScrollArea { #BottomBar QLabel { color : white; font-family: 'Arial'; - font-size: 14px; + font-size: 13px; } #NoteList { @@ -119,6 +119,11 @@ QScrollArea { padding: 5px 10px; } + +#NoteWidget QPushButton:hover { + background-color:rgb(213, 167, 88); +} + QPushButton { font-family: 'Arial'; font-size: 13px; @@ -131,8 +136,601 @@ QPushButton { min-height: 25px; } +QPushButton::hover { + background-color:rgb(245, 148, 89); +} + +QPushButton::pressed { + background-color:rgb(238, 122, 50); +} + +QPushButton#switch_theme_button_ { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; + + border: 2px solid #fea36b; + + background-color: transparent; +} +QPushButton::hover#switch_theme_button_ { + background-color: #fea36b; +} +QPushButton::pressed#switch_theme_button_ { + background-color:#fea36b; +} )"; +QString main_window_dark_autumn_theme = R"( +#main-window { + background-color: black; +} + +#main-window QLabel { + font-weight: bold; + color: #BDD1BD; +} + +QScrollBar:vertical { + border: none; + background: #202020; + width: 10px; + margin: 0; +} +QScrollBar::handle:vertical { + background: #089083; + border-radius: 5px; + min-height: 20px; +} + +QScrollArea { + border: none; + background: transparent; +} + +#ProjectList { + background-color: #202020; + border-radius: 8px; + padding: 8px; + outline: 0; + font-family: 'Arial'; + font-weight: bold; + font-size: 13px; + color: #BDD1BD; +} + +#ProjectList::item { + background-color: #1E2A30; + border: none; + padding: 10px; + margin: 2px; + border-radius: 6px; +} + +#ProjectList::item:hover { + background-color: #2C3E44; +} + +#ProjectList::item:selected { + background-color: #089083; + color: #263238; +} + +#BottomBar { + background-color: #202020; + border-radius: 8px; + padding: 8px; + outline: 0; +} + +#BottomBar QLabel { + color: #BDD1BD; + font-family: 'Arial'; + font-size: 13px; +} + +#NoteList { + border-radius: 8px; + background-color: #202020; +} + +#NoteWidget { + background-color: #ffdda2; + border-radius: 8px; +} + +#NoteWidget QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color:rgb(241, 201, 132); + color: rgb(33, 44, 50); + padding: 5px 10px; +} + + +#NoteWidget QPushButton:hover { + background-color:rgb(213, 167, 88); +} + +QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #fea36b; + color: white; + padding: 5px 10px; + min-width: 60px; + min-height: 25px; +} + +#NoteWidget QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #5E3E3E; + color: #BDD1BD; + padding: 5px 10px; +} + +#NoteWidget QPushButton:hover { + background-color:rgb(53, 28, 28); +} + +QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #fea36b; + color: #263238; + padding: 5px 10px; + min-width: 60px; + min-height: 25px; +} + +QPushButton:hover { + background-color: #d58745; +} + +QPushButton#switch_theme_button_ { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; + + border: 2px solid #089083; + + background-color: transparent; +} +QPushButton::hover#switch_theme_button_ { + background-color: #089083; +} +QPushButton::pressed#switch_theme_button_ { + background-color:rgb(13, 93, 85); +} +)"; + +QString main_window_light_purple_theme = R"( +#main-window { + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, + stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(103, 88, 126)); +} + +#main-window QLabel { + font-weight: bold; + color: rgb(42, 10, 25); +} + +QScrollBar:vertical { + border: none; + background: transparent; + width: 10px; + margin: 0; +} +QScrollBar::handle:vertical { + background: #722548; + border-radius: 5px; + min-height: 20px; +} + +QScrollArea { + border: none; + background: transparent; +} + +#ProjectList { + background-color: rgb(221, 210, 238); + border-radius: 8px; + padding: 8px; + outline: 0; + font-family: 'Arial'; + font-weight: bold; + font-size: 13px; + color: rgb(42, 10, 25); +} + +#ProjectList::item { + background-color: rgb(206, 193, 224); + border: none; + padding: 10px; + margin: 2px; + border-radius: 6px; +} + +#ProjectList::item:hover { + background-color: rgb(168, 147, 199); +} + +#ProjectList::item:selected { + background-color:rgb(82, 69, 101); + color: rgb(221, 210, 238); +} + +#BottomBar { + background-color: rgb(42, 10, 25); + border-radius: 8px; + padding: 8px; + outline: 0; +} + +#BottomBar QLabel { + color: rgb(218, 207, 235); + font-family: 'Arial'; + font-size: 13px; +} + +#NoteList { + border-radius: 8px; + background-color: rgb(221, 210, 238); +} + +#NoteWidget { + background-color: #D4A5C9; + border-radius: 8px; +} + +#NoteWidget QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #C98BB8; + color: rgb(42, 10, 25); + padding: 5px 10px; +} + + +#NoteWidget QPushButton:hover { + background-color:rgb(134, 82, 120); +} + +QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #722548; + color: #9882B9; + padding: 5px 10px; + min-width: 60px; + min-height: 25px; +} + +QPushButton:hover { + background-color: rgb(98, 27, 59); +} + +QPushButton#switch_theme_button_ { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; + + border: 2px solid #722548; + + background-color: transparent; +} + +QPushButton::hover#switch_theme_button_ { + background-color: #722548; +} +QPushButton::pressed#switch_theme_button_ { + background-color: #722548; +} +)"; + +QString main_window_dark_purple_theme = R"( +#main-window { + background-color:rgb(9, 6, 10); +} + +#main-window QLabel { + font-weight: bold; + color: #9882B9; +} + +QScrollBar:vertical { + border: none; + background: #221932; + width: 10px; + margin: 0; +} +QScrollBar::handle:vertical { + background: #722548; + border-radius: 5px; + min-height: 20px; +} + +QScrollArea { + border: none; + background: transparent; +} + +#ProjectList { + background-color: #221932; + border-radius: 8px; + padding: 8px; + outline: 0; + font-family: 'Arial'; + font-weight: bold; + font-size: 13px; + color: #9882B9; +} + +#ProjectList::item { + background-color: rgb(34, 25, 48); + border: none; + padding: 10px; + margin: 2px; + border-radius: 6px; +} + +#ProjectList::item:hover { + background-color: rgb(42, 31, 59); +} + +#ProjectList::item:selected { + background-color: #722548; + color: #9882B9; +} + +#BottomBar { + background-color: rgb(42, 10, 25); + border-radius: 8px; + padding: 8px; + outline: 0; +} + +#BottomBar QLabel { + color: #9882B9; + font-family: 'Arial'; + font-size: 13px; +} + +#NoteList { + border-radius: 8px; + background-color: #221932; +} + +#NoteWidget { + background-color: #3D2A3D; + border-radius: 8px; +} + +#NoteWidget QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #5D3A5D; + color: #9882B9; + padding: 5px 10px; +} + + +#NoteWidget QPushButton:hover { + background-color:rgb(56, 35, 56); +} + +QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #722548; + color: #060407; + padding: 5px 10px; + min-width: 60px; + min-height: 25px; +} + +QPushButton:hover { + background-color: rgb(98, 27, 59); +} +QPushButton#switch_theme_button_ { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; + + border: 2px solid #9882B9; + + background-color: transparent; +} +QPushButton::hover#switch_theme_button_ { + background-color: #9882B9; +} +QPushButton::pressed#switch_theme_button_ { + background-color:rgb(113, 93, 143); +} +)"; + +QString main_window_nature_flat_theme = R"( +#main-window { + background: #07142B; +} + +#main-window QLabel { + font-weight: bold; + color: #BDD1BD; +} + +QScrollBar:vertical { + border: none; + background: #173C4C; + width: 10px; + margin: 0; +} +QScrollBar::handle:vertical { + background: #568F7C; + border-radius: 5px; + min-height: 20px; +} + +QScrollArea { + border: none; + background: transparent; +} + +#ProjectList { + background-color: #173C4C; + border-radius: 8px; + padding: 8px; + outline: 0; + font-family: 'Arial'; + font-weight: bold; + font-size: 13px; + color: #BDD1BD; + border: 1px solid; +} + +#ProjectList::item { + background-color: #173C4C; + border: none; + padding: 10px; + margin: 2px; + border-radius: 6px; +} + +#ProjectList::item:hover { + background-color: #326D6C; +} + +#ProjectList::item:selected { + background-color: #568F7C; + color: #173C4C; +} + +#BottomBar { + background-color: #173C4C; + border-radius: 8px; + padding: 8px; + outline: 0; + border: 1px solid; +} + +#BottomBar QLabel { + color: #BDD1BD; + font-family: 'Arial'; + font-size: 13px; +} + +#NoteList { + border-radius: 8px; + background-color: #173C4C; + border: 1px solid; +} + +#NoteWidget { + background-color: #2D4C3C; + border-radius: 8px; + border: 1px solid; +} + +#NoteWidget QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #326D6C; + color: #07142B; + padding: 5px 10px; +} + + +#NoteWidget QPushButton:hover { + background-color:rgb(36, 82, 81); +} + +QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #568F7C; + color: #07142B; + padding: 5px 10px; + min-width: 60px; + min-height: 25px; + border: none; +} + +QPushButton:hover { + background-color: #326D6C; +} + +QPushButton:pressed { + background-color: #173C4C; +} + +QPushButton#switch_theme_button_ { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; + + border: 2px solid #85B093; + + background-color: transparent; +} + +QPushButton::hover#switch_theme_button_ { + background-color: #85B093; +} +QPushButton::pressed#switch_theme_button_ { + background-color:rgb(107, 141, 118); +} +)"; } // namespace Ui diff --git a/ui/main-window/include/mainwindow.h b/ui/main-window/include/mainwindow.h index e5242f7..27e60f0 100644 --- a/ui/main-window/include/mainwindow.h +++ b/ui/main-window/include/mainwindow.h @@ -12,6 +12,7 @@ #include "notelist.h" #include "projectlist.h" #include "storage.hpp" +#include namespace Ui { class MainWindow : public QWidget { @@ -25,19 +26,24 @@ class MainWindow : public QWidget { QWidget *content_widget_; QPushButton *new_project_button_; QPushButton *new_note_button_; + QPushButton *switch_theme_button_; project_storage_model::Storage *storage_; friend ProjectList; private slots: void add_project(); void add_note(); + void on_switch_theme_clicked(); public: explicit MainWindow( QWidget *parent = nullptr, std::string username = "none", - project_storage_model::Storage *storage = nullptr + project_storage_model::Storage *storage = nullptr, + int number_of_theme_ = 0 ); + static const std::vector THEMES; + int number_of_theme; }; } // namespace Ui #endif // MAINWINDOW_H \ No newline at end of file diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index 907f902..62dbbf6 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -20,10 +20,20 @@ #include "projectlist.h" namespace Ui { + +const std::vector MainWindow::THEMES = { + Ui::main_window_light_autumn_theme, + Ui::main_window_dark_autumn_theme, + Ui::main_window_dark_purple_theme, + Ui::main_window_light_purple_theme, + Ui::main_window_nature_flat_theme +}; + MainWindow::MainWindow( QWidget *parent, std::string username, - project_storage_model::Storage *storage + project_storage_model::Storage *storage, + int number_of_theme_ ) : QWidget(parent), username(username), @@ -34,12 +44,13 @@ MainWindow::MainWindow( note_list_(new NoteList(this)), content_widget_(new QWidget(this)), new_project_button_(new QPushButton("Новый проект", this)), + switch_theme_button_(new QPushButton(this)), new_note_button_(new QPushButton("Новая заметка", this)), - storage_(storage) { + storage_(storage), + number_of_theme(number_of_theme_) { this->setObjectName("main-window"); this->setAttribute(Qt::WA_StyledBackground); this->setMinimumSize(QSize(800, 600)); - this->setStyleSheet(main_window_style); main_layout_->addWidget(top_bar_, Qt::AlignTop); main_layout_->setAlignment(Qt::AlignCenter); @@ -57,6 +68,10 @@ MainWindow::MainWindow( main_layout_->addWidget(content_widget_); this->setLayout(main_layout_); + switch_theme_button_->setObjectName("switch_theme_button_"); + right_layout->addWidget(switch_theme_button_, 0, Qt::AlignRight | Qt::AlignBottom); + + this->setStyleSheet(THEMES[number_of_theme_]); this->project_list_->load_projects(storage); connect( @@ -66,6 +81,14 @@ MainWindow::MainWindow( connect( new_note_button_, &QPushButton::clicked, this, &Ui::MainWindow::add_note ); + connect( + switch_theme_button_, &QPushButton::clicked, this, + &Ui::MainWindow::on_switch_theme_clicked + ); + connect( + new_project_button_, &QPushButton::clicked, this, + &Ui::MainWindow::add_project + ); connect( new_project_button_, &QPushButton::clicked, this, &Ui::MainWindow::add_project @@ -110,4 +133,10 @@ void MainWindow::add_note() { } } + +void MainWindow::on_switch_theme_clicked() { + this->number_of_theme = (this->number_of_theme+1)%THEMES.size(); + setStyleSheet(THEMES[this->number_of_theme]); +} + } // namespace Ui \ No newline at end of file diff --git a/ui/note-widget/include/note_edit_dialog_styles.h b/ui/note-widget/include/note_edit_dialog_styles.h index 5ad1b63..742d78e 100644 --- a/ui/note-widget/include/note_edit_dialog_styles.h +++ b/ui/note-widget/include/note_edit_dialog_styles.h @@ -4,7 +4,7 @@ #include namespace Ui { -QString light_theme = R"( +QString note_edit_dialog_light_autumn_theme = R"( QDialog { background-color: #f5f5f5; } @@ -167,6 +167,19 @@ QString light_theme = R"( background-color: #d58745; border-color: #d58745; } + + QPushButton#switch_theme { + background-color: transparent; + border-radius: 9px; + border: 2px solid #089083; + padding: 5px; + } + QPushButton::hover#switch_theme { + background-color: #089083; + } + QPushButton::pressed#switch_theme { + background-color:rgb(7, 110, 100); + } )"; } // namespace Ui diff --git a/ui/note-widget/src/note_edit_dialog.cpp b/ui/note-widget/src/note_edit_dialog.cpp index ed18200..620f577 100644 --- a/ui/note-widget/src/note_edit_dialog.cpp +++ b/ui/note-widget/src/note_edit_dialog.cpp @@ -83,7 +83,7 @@ void NoteEditDialog::setup_connections() { void NoteEditDialog::setup_ui() { setFixedSize(700, 480); - setStyleSheet(Ui::light_theme); + setStyleSheet(Ui::note_edit_dialog_light_autumn_theme); ui_->buttonsLayout->setAlignment(Qt::AlignLeft); } diff --git a/ui/note-widget/ui/note_edit_dialog.ui b/ui/note-widget/ui/note_edit_dialog.ui index 60eebd8..ed50361 100644 --- a/ui/note-widget/ui/note_edit_dialog.ui +++ b/ui/note-widget/ui/note_edit_dialog.ui @@ -240,7 +240,7 @@ - + я 504 20 171 From d66245984cd46db29ffe85a5c212d2b4760e8bdf Mon Sep 17 00:00:00 2001 From: MuravAna Date: Tue, 15 Apr 2025 19:27:50 +0300 Subject: [PATCH 06/17] All of the styles for all of the windows work correctlybut without saving in database --- CMakeLists.txt | 2 + main.cpp | 3 + ui/authorization-windows/CMakeLists.txt | 2 +- .../include/login_window.h | 8 +- .../include/login_window_style_sheet.h | 58 +- .../include/registration_window.h | 6 +- .../include/registration_window_style_sheet.h | 62 +- ui/authorization-windows/src/login_window.cpp | 38 +- .../src/registration_window.cpp | 37 +- ui/main-window/CMakeLists.txt | 1 + ui/main-window/include/main_window_style.hpp | 624 ++++++++++------ ui/main-window/include/mainwindow.h | 7 +- ui/main-window/include/notewidget.h | 4 +- ui/main-window/src/mainwindow.cpp | 34 +- ui/main-window/src/notewidget.cpp | 6 +- ui/note-widget/CMakeLists.txt | 2 +- ui/note-widget/include/note_edit_dialog.h | 3 + .../include/note_edit_dialog_styles.h | 692 +++++++++++++++++- ui/note-widget/src/note_edit_dialog.cpp | 37 +- ui/note-widget/ui/note_edit_dialog.ui | 24 +- ui/theme-manager/CMakeLists.txt | 32 + ui/theme-manager/include/theme_manager.h | 28 + ui/theme-manager/src/theme_manager.cpp | 27 + 23 files changed, 1402 insertions(+), 335 deletions(-) create mode 100644 ui/theme-manager/CMakeLists.txt create mode 100644 ui/theme-manager/include/theme_manager.h create mode 100644 ui/theme-manager/src/theme_manager.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index 05e4157..232c82d 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -16,6 +16,7 @@ add_subdirectory(database) add_subdirectory(ui/main-window) add_subdirectory(ui/authorization-windows) add_subdirectory(ui/note-widget) +add_subdirectory(ui/theme-manager) add_executable(EfficioTaskTracker main.cpp) @@ -29,4 +30,5 @@ target_link_libraries(EfficioTaskTracker PRIVATE AuthorizationWindows MainWindow NoteWidget + ThemeManager ) \ No newline at end of file diff --git a/main.cpp b/main.cpp index 8af3d0d..98dcc4d 100644 --- a/main.cpp +++ b/main.cpp @@ -6,10 +6,13 @@ #include "applicationwindow.h" #include "login_window.h" #include "mainwindow.h" +#include "theme_manager.h" int main(int argc, char *argv[]) { QApplication application(argc, argv); + ThemeManager* themeManager = ThemeManager::instance(); + QTranslator translator; const QStringList ui_languages = QLocale::system().uiLanguages(); for (const QString &locale : ui_languages) { diff --git a/ui/authorization-windows/CMakeLists.txt b/ui/authorization-windows/CMakeLists.txt index e61f562..4926ac5 100644 --- a/ui/authorization-windows/CMakeLists.txt +++ b/ui/authorization-windows/CMakeLists.txt @@ -40,4 +40,4 @@ target_include_directories(AuthorizationWindows $ ) -target_link_libraries(AuthorizationWindows PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts MainWindow) \ No newline at end of file +target_link_libraries(AuthorizationWindows PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts MainWindow ThemeManager) \ No newline at end of file diff --git a/ui/authorization-windows/include/login_window.h b/ui/authorization-windows/include/login_window.h index 584cd9c..beeaa8d 100644 --- a/ui/authorization-windows/include/login_window.h +++ b/ui/authorization-windows/include/login_window.h @@ -19,10 +19,11 @@ class LoginWindow : public QWidget { Q_OBJECT public: - explicit LoginWindow(QWidget *parent = nullptr, int number_of_theme_ = 0); + explicit LoginWindow(QWidget *parent = nullptr); ~LoginWindow(); static const std::vector THEMES; + void handle_theme_changed(int theme); private slots: void on_switch_mode_clicked(); @@ -30,7 +31,6 @@ private slots: void on_switch_theme_clicked(); private: - Ui::LoginWindow *ui; - int number_of_theme; - int counter_on_switch_theme_clicks = 0; + Ui::LoginWindow *ui; + int counter_on_switch_theme_clicks = 0; }; \ No newline at end of file diff --git a/ui/authorization-windows/include/login_window_style_sheet.h b/ui/authorization-windows/include/login_window_style_sheet.h index 79e9a42..4483df3 100644 --- a/ui/authorization-windows/include/login_window_style_sheet.h +++ b/ui/authorization-windows/include/login_window_style_sheet.h @@ -53,10 +53,17 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #089083; - padding: 5px; } QPushButton::hover#switch_theme { background-color: #089083; @@ -117,10 +124,17 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #089083; - padding: 5px; } QPushButton::hover#switch_theme { background-color: #089083; @@ -184,10 +198,17 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #060407; - padding: 5px; } QPushButton::hover#switch_theme { background-color: #060407; @@ -247,10 +268,17 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #9882B9; - padding: 5px; } QPushButton::hover#switch_theme { background-color: #9882B9; @@ -261,7 +289,7 @@ namespace Ui { )"; - QString login_window_nature_flat_theme = R"( + QString login_window_blue_theme = R"( QWidget { background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, stop:0 #173C4C, stop:0.5 #326D6C, stop:1 #07142B); @@ -325,11 +353,17 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #85B093; - padding: 5px; - color: #BDD1BD; } QPushButton#switch_theme:hover { diff --git a/ui/authorization-windows/include/registration_window.h b/ui/authorization-windows/include/registration_window.h index 968c333..2870845 100644 --- a/ui/authorization-windows/include/registration_window.h +++ b/ui/authorization-windows/include/registration_window.h @@ -19,10 +19,11 @@ class RegistrationWindow : public QWidget { Q_OBJECT public: - explicit RegistrationWindow(QWidget *parent = nullptr, int number_of_theme_ = 0); + explicit RegistrationWindow(QWidget *parent = nullptr); ~RegistrationWindow(); bool is_strong_and_valid_password(const QString &password); static const std::vector THEMES; + void handle_theme_changed(int theme); private slots: void on_switch_mode_clicked(); @@ -31,6 +32,5 @@ private slots: private: Ui::RegistrationWindow *ui; - int number_of_theme; - int counter_on_switch_theme_clicks = 0; + int counter_on_switch_theme_clicks = 0; }; \ No newline at end of file diff --git a/ui/authorization-windows/include/registration_window_style_sheet.h b/ui/authorization-windows/include/registration_window_style_sheet.h index 1b8e177..3a7c0f7 100644 --- a/ui/authorization-windows/include/registration_window_style_sheet.h +++ b/ui/authorization-windows/include/registration_window_style_sheet.h @@ -53,10 +53,17 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #089083; - padding: 5px; } QPushButton::hover#switch_theme { background-color: #089083; @@ -116,10 +123,17 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #089083; - padding: 5px; } QPushButton::hover#switch_theme { background-color: #089083; @@ -183,10 +197,17 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #060407; - padding: 5px; } QPushButton::hover#switch_theme { background-color: #060407; @@ -246,10 +267,17 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #9882B9; - padding: 5px; } QPushButton::hover#switch_theme { background-color: #9882B9; @@ -259,7 +287,7 @@ namespace Ui { } )"; - QString registration_window_nature_flat_theme = R"( + QString registration_window_blue_theme = R"( QWidget { background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, stop:0 #173C4C, stop:0.5 #326D6C, stop:1 #07142B) !important; @@ -323,16 +351,22 @@ namespace Ui { } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; background-color: transparent; - border-radius: 9px; border: 2px solid #85B093; - padding: 5px; - color: #BDD1BD; } - QPushButton::hover#switch_theme { + QPushButton#switch_theme:hover { background-color: #85B093; } - QPushButton::pressed#switch_theme { + QPushButton#switch_theme:pressed { background-color:rgb(107, 141, 118); } )"; diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index 31b5b65..14c3ed6 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -16,17 +16,18 @@ #include "registration_window.h" #include "serialization.hpp" #include "login_window_style_sheet.h" +#include "theme_manager.h" const std::vector LoginWindow::THEMES = { Ui::login_window_light_autumn_theme, Ui::login_window_dark_autumn_theme, Ui::login_window_dark_purple_theme, Ui::login_window_light_purple_theme, - Ui::login_window_nature_flat_theme + Ui::login_window_blue_theme }; -LoginWindow::LoginWindow(QWidget *parent, int number_of_theme_) - : QWidget(parent), ui(new Ui::LoginWindow), number_of_theme(number_of_theme_) { +LoginWindow::LoginWindow(QWidget *parent) + : QWidget(parent), ui(new Ui::LoginWindow) { ui->setupUi(this); setFixedSize(380, 480); @@ -34,7 +35,7 @@ LoginWindow::LoginWindow(QWidget *parent, int number_of_theme_) ui->input_password->setPlaceholderText("Введите пароль:"); ui->input_password->setEchoMode(QLineEdit::Password); - setStyleSheet(THEMES[number_of_theme_]); + handle_theme_changed(ThemeManager::instance()->current_theme()); connect( ui->switch_theme, &QPushButton::clicked, this, @@ -49,6 +50,20 @@ LoginWindow::LoginWindow(QWidget *parent, int number_of_theme_) ui->push_enter, &QPushButton::clicked, this, &LoginWindow::on_push_enter_clicked ); + connect(ThemeManager::instance(), &ThemeManager::theme_changed, + this, &LoginWindow::handle_theme_changed); +} + + +void LoginWindow::handle_theme_changed(int theme) { + this->setStyleSheet(THEMES[theme]); +} + +void LoginWindow::on_switch_theme_clicked() { + if ((this->counter_on_switch_theme_clicks++)%2){ + int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; + ThemeManager::instance()->apply_theme(next_theme); + } } LoginWindow::~LoginWindow() { @@ -65,7 +80,7 @@ void LoginWindow::on_switch_mode_clicked() { } project_storage_model::Storage storage; RegistrationWindow *registration_window = - new RegistrationWindow(app_window, this->number_of_theme); + new RegistrationWindow(app_window); app_window->setCentralWidget(registration_window); QRect screenGeometry = QApplication::primaryScreen()->availableGeometry(); @@ -108,7 +123,7 @@ void LoginWindow::on_push_enter_clicked() { Serialization::get_storage(*storage, login.toStdString()); Ui::MainWindow *main_window = - new Ui::MainWindow(app_window, login.toStdString(), storage, this->number_of_theme); + new Ui::MainWindow(app_window, login.toStdString(), storage); app_window->setCentralWidget(main_window); app_window->resize(800, 600); @@ -129,15 +144,4 @@ void LoginWindow::on_push_enter_clicked() { this, "Ошибка ввода данных", "Пожалуйста, заполните все поля!" ); } -} - -void LoginWindow::on_switch_theme_clicked() { - // Attention: костыль. - // Почему-то кнопка switch_theme дважды кликается, - // из-за чего темы переключаются не подряд, а через одну. - // Поэтому ведем счетчик кликов и только на нечетных переключаем тему. - if ((this->counter_on_switch_theme_clicks++)%2){ - this->number_of_theme = (this->number_of_theme+1)%THEMES.size(); - setStyleSheet(THEMES[this->number_of_theme]); - } } \ No newline at end of file diff --git a/ui/authorization-windows/src/registration_window.cpp b/ui/authorization-windows/src/registration_window.cpp index 97f595a..0a5017e 100644 --- a/ui/authorization-windows/src/registration_window.cpp +++ b/ui/authorization-windows/src/registration_window.cpp @@ -16,17 +16,18 @@ #include "registration_window.h" #include "registration_window_style_sheet.h" #include +#include "theme_manager.h" const std::vector RegistrationWindow::THEMES = { Ui::registration_window_light_autumn_theme, Ui::registration_window_dark_autumn_theme, Ui::registration_window_dark_purple_theme, Ui::registration_window_light_purple_theme, - Ui::registration_window_nature_flat_theme + Ui::registration_window_blue_theme }; -RegistrationWindow::RegistrationWindow(QWidget *parent, int number_of_theme_) - : QWidget(parent), ui(new Ui::RegistrationWindow), number_of_theme(number_of_theme_) { +RegistrationWindow::RegistrationWindow(QWidget *parent) + : QWidget(parent), ui(new Ui::RegistrationWindow) { ui->setupUi(this); setFixedSize(380, 480); @@ -37,7 +38,6 @@ RegistrationWindow::RegistrationWindow(QWidget *parent, int number_of_theme_) ui->create_password->setEchoMode(QLineEdit::Password); ui->repeat_password->setEchoMode(QLineEdit::Password); - setStyleSheet(THEMES[number_of_theme_]); setAttribute(Qt::WA_StyledBackground, true); connect( @@ -53,8 +53,24 @@ RegistrationWindow::RegistrationWindow(QWidget *parent, int number_of_theme_) ui->switch_mode, &QPushButton::clicked, this, &RegistrationWindow::on_switch_mode_clicked ); + connect(ThemeManager::instance(), &ThemeManager::theme_changed, + this, &RegistrationWindow::handle_theme_changed); + handle_theme_changed(ThemeManager::instance()->current_theme()); } + +void RegistrationWindow::handle_theme_changed(int theme) { + this->setStyleSheet(THEMES[theme]); +} + +void RegistrationWindow::on_switch_theme_clicked() { + if ((this->counter_on_switch_theme_clicks++)%2){ + int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; + ThemeManager::instance()->apply_theme(next_theme); + } +} + + RegistrationWindow::~RegistrationWindow() { delete ui; } @@ -68,7 +84,7 @@ void RegistrationWindow::on_switch_mode_clicked() { old->deleteLater(); } project_storage_model::Storage storage; - LoginWindow *login_window = new LoginWindow(app_window, number_of_theme); + LoginWindow *login_window = new LoginWindow(app_window); app_window->setCentralWidget(login_window); QRect screenGeometry = QApplication::primaryScreen()->availableGeometry(); @@ -167,15 +183,4 @@ void RegistrationWindow::on_push_registration_clicked() { } else { QMessageBox::warning(this, "Ошибка", "Пожалуйста, заполните все поля."); } -} - -void RegistrationWindow::on_switch_theme_clicked() { - // Attention: костыль. - // Почему-то кнопка switch_theme дважды кликается, - // из-за чего темы переключаются не подряд, а через одну. - // Поэтому ведем счетчик кликов и только на нечетных переключаем тему. - if ((this->counter_on_switch_theme_clicks++)%2){ - this->number_of_theme = (this->number_of_theme+1)%THEMES.size(); - setStyleSheet(THEMES[this->number_of_theme]); - } } \ No newline at end of file diff --git a/ui/main-window/CMakeLists.txt b/ui/main-window/CMakeLists.txt index c8e1f85..d2ef5a1 100644 --- a/ui/main-window/CMakeLists.txt +++ b/ui/main-window/CMakeLists.txt @@ -36,4 +36,5 @@ target_link_libraries(MainWindow PRIVATE Scripts Database NoteWidget + ThemeManager ) \ No newline at end of file diff --git a/ui/main-window/include/main_window_style.hpp b/ui/main-window/include/main_window_style.hpp index aa06013..58cd8dc 100644 --- a/ui/main-window/include/main_window_style.hpp +++ b/ui/main-window/include/main_window_style.hpp @@ -14,22 +14,31 @@ QString main_window_light_autumn_theme = R"( } QScrollBar:vertical { + width: 7px; +} +QScrollBar:horizontal { + height: 7px; +} +QScrollBar:vertical, QScrollBar:horizontal { border: none; background: transparent; - width: 10px; margin: 0; } -QScrollBar::handle:vertical { +QScrollBar::handle:vertical, QScrollBar::handle:horizontal { background: #c0c0c0; - border-radius: 5px; + border-radius: 3px; min-height: 20px; + min-width: 20px; } - QScrollBar::add-line:vertical, QScrollBar::sub-line:vertical, - QScrollBar::add-page:vertical, QScrollBar::sub-page:vertical { - background: none; - height: 0px; - } +QScrollBar::add-line:horizontal, QScrollBar::sub-line:horizontal, +QScrollBar::add-page:vertical, QScrollBar::sub-page:vertical, +QScrollBar::add-page:horizontal, QScrollBar::sub-page:horizontal { + background: none; + height: 0; + width: 0; +} + QScrollArea { border: none; background: transparent; @@ -64,25 +73,32 @@ QScrollArea { } #ProjectList QScrollBar:vertical { + width: 7px; +} +#ProjectList QScrollBar:horizontal { + height: 7px; +} +#ProjectList QScrollBar:vertical, +#ProjectList QScrollBar:horizontal { border: none; - background: #FED6BC; - width: 10px; + background: transparent; margin: 0; } - -#ProjectList QScrollBar::handle:vertical { +#ProjectList QScrollBar::handle:vertical, +#ProjectList QScrollBar::handle:horizontal { background: #c0c0c0; - border-radius: 5px; + border-radius: 3px; min-height: 20px; + min-width: 20px; } - #ProjectList QScrollBar::add-line:vertical, -#ProjectList QScrollBar::sub-line:vertical { - background: none; -} - +#ProjectList QScrollBar::sub-line:vertical, +#ProjectList QScrollBar::add-line:horizontal, +#ProjectList QScrollBar::sub-line:horizontal, #ProjectList QScrollBar::add-page:vertical, -#ProjectList QScrollBar::sub-page:vertical { +#ProjectList QScrollBar::sub-page:vertical, +#ProjectList QScrollBar::add-page:horizontal, +#ProjectList QScrollBar::sub-page:horizontal { background: none; } @@ -119,7 +135,6 @@ QScrollArea { padding: 5px 10px; } - #NoteWidget QPushButton:hover { background-color:rgb(213, 167, 88); } @@ -154,181 +169,195 @@ QPushButton#switch_theme_button_ { border-radius: 7px; padding: 0; margin-bottom: 2px; - border: 2px solid #fea36b; - background-color: transparent; } QPushButton::hover#switch_theme_button_ { background-color: #fea36b; } QPushButton::pressed#switch_theme_button_ { - background-color:#fea36b; + background-color: rgb(185, 117, 61); } )"; QString main_window_dark_autumn_theme = R"( -#main-window { - background-color: black; -} - -#main-window QLabel { - font-weight: bold; - color: #BDD1BD; -} - -QScrollBar:vertical { - border: none; - background: #202020; - width: 10px; - margin: 0; -} -QScrollBar::handle:vertical { - background: #089083; - border-radius: 5px; - min-height: 20px; -} - -QScrollArea { - border: none; - background: transparent; -} - -#ProjectList { - background-color: #202020; - border-radius: 8px; - padding: 8px; - outline: 0; - font-family: 'Arial'; - font-weight: bold; - font-size: 13px; - color: #BDD1BD; -} - -#ProjectList::item { - background-color: #1E2A30; - border: none; - padding: 10px; - margin: 2px; - border-radius: 6px; -} - -#ProjectList::item:hover { - background-color: #2C3E44; -} - -#ProjectList::item:selected { - background-color: #089083; - color: #263238; -} - -#BottomBar { - background-color: #202020; - border-radius: 8px; - padding: 8px; - outline: 0; -} - -#BottomBar QLabel { - color: #BDD1BD; - font-family: 'Arial'; - font-size: 13px; -} - -#NoteList { - border-radius: 8px; - background-color: #202020; -} - -#NoteWidget { - background-color: #ffdda2; - border-radius: 8px; -} - -#NoteWidget QPushButton { - font-family: 'Arial'; - font-size: 13px; - font-weight: bold; - border-radius: 10px; - background-color:rgb(241, 201, 132); - color: rgb(33, 44, 50); - padding: 5px 10px; -} - - -#NoteWidget QPushButton:hover { - background-color:rgb(213, 167, 88); -} - -QPushButton { - font-family: 'Arial'; - font-size: 13px; - font-weight: bold; - border-radius: 10px; - background-color: #fea36b; - color: white; - padding: 5px 10px; - min-width: 60px; - min-height: 25px; -} - -#NoteWidget QPushButton { - font-family: 'Arial'; - font-size: 13px; - font-weight: bold; - border-radius: 10px; - background-color: #5E3E3E; - color: #BDD1BD; - padding: 5px 10px; -} - -#NoteWidget QPushButton:hover { - background-color:rgb(53, 28, 28); -} - -QPushButton { - font-family: 'Arial'; - font-size: 13px; - font-weight: bold; - border-radius: 10px; - background-color: #fea36b; - color: #263238; - padding: 5px 10px; - min-width: 60px; - min-height: 25px; -} - -QPushButton:hover { - background-color: #d58745; -} - -QPushButton#switch_theme_button_ { - width: 20px; - height: 20px; - min-width: 20px; - min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; + #main-window { + background-color: #202020; + } - border: 2px solid #089083; + #main-window QLabel { + font-weight: bold; + color: #BDD1BD; + } - background-color: transparent; -} -QPushButton::hover#switch_theme_button_ { - background-color: #089083; -} -QPushButton::pressed#switch_theme_button_ { - background-color:rgb(13, 93, 85); -} -)"; + QScrollBar:vertical { + width: 7px; + } + QScrollBar:horizontal { + height: 7px; + } + QScrollBar:vertical, QScrollBar:horizontal { + border: none; + background: transparent; + margin: 0; + } + QScrollBar::handle:vertical, QScrollBar::handle:horizontal { + background: #c0c0c0; + border-radius: 3px; + min-height: 20px; + min-width: 20px; + } + QScrollBar::add-line:vertical, QScrollBar::sub-line:vertical, + QScrollBar::add-line:horizontal, QScrollBar::sub-line:horizontal, + QScrollBar::add-page:vertical, QScrollBar::sub-page:vertical, + QScrollBar::add-page:horizontal, QScrollBar::sub-page:horizontal { + background: none; + height: 0; + width: 0; + } + + QScrollArea { + border: none; + background: transparent; + } + + #ProjectList { + background-color: black; + border-radius: 8px; + padding: 8px; + outline: 0; + font-family: 'Arial'; + font-weight: bold; + font-size: 13px; + color: #BDD1BD; + } + + #ProjectList::item { + background-color: rgb(32, 53, 51); + color: #ffffff; + border: none; + padding: 10px; + margin: 2px; + border-radius: 6px; + } + + #ProjectList::item:hover { + background-color: rgb(64, 89, 87); + } + + #ProjectList::item:selected { + background-color: #089083; + color: rgb(33, 44, 50); + } + + #ProjectList QScrollBar:vertical { + width: 7px; + } + #ProjectList QScrollBar:horizontal { + height: 7px; + } + #ProjectList QScrollBar:vertical, + #ProjectList QScrollBar:horizontal { + border: none; + background: transparent; + margin: 0; + } + #ProjectList QScrollBar::handle:vertical, + #ProjectList QScrollBar::handle:horizontal { + background: #c0c0c0; + border-radius: 3px; + min-height: 20px; + min-width: 20px; + } + #ProjectList QScrollBar::add-line:vertical, + #ProjectList QScrollBar::sub-line:vertical, + #ProjectList QScrollBar::add-line:horizontal, + #ProjectList QScrollBar::sub-line:horizontal, + #ProjectList QScrollBar::add-page:vertical, + #ProjectList QScrollBar::sub-page:vertical, + #ProjectList QScrollBar::add-page:horizontal, + #ProjectList QScrollBar::sub-page:horizontal { + background: none; + } + + #BottomBar { + background-color:rgb(0, 0, 0); + border-radius: 8px; + padding: 8px; + outline: 0; + } + + #BottomBar QLabel { + color: #c0c0c0; + font-family: 'Arial'; + font-size: 13px; + } + + #NoteList { + border-radius: 8px; + background-color: black; + } + + #NoteWidget { + background-color:rgb(179, 156, 116); + border-radius: 8px; + } + + #NoteWidget QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color: #ffdda2; + color: #202020; + padding: 5px 10px; + } + + #NoteWidget QPushButton:hover { + background-color:rgb(255, 236, 203); + } + + QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + background-color:rgb(211, 139, 95); + color: #263238; + padding: 5px 10px; + min-width: 60px; + min-height: 25px; + } + + QPushButton:hover { + background-color:rgb(181, 114, 59); + } + + QPushButton#switch_theme_button_ { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; + border: 2px solid rgb(211, 139, 95); + background-color: transparent; + } + QPushButton::hover#switch_theme_button_ { + background-color: rgb(211, 139, 95); + } + QPushButton::pressed#switch_theme_button_ { + background-color: rgb(211, 139, 95); + } + )"; + QString main_window_light_purple_theme = R"( #main-window { - background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, - stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(103, 88, 126)); + background: #9882B9; } #main-window QLabel { @@ -337,15 +366,29 @@ QString main_window_light_purple_theme = R"( } QScrollBar:vertical { + width: 7px; +} +QScrollBar:horizontal { + height: 7px; +} +QScrollBar:vertical, QScrollBar:horizontal { border: none; background: transparent; - width: 10px; margin: 0; } -QScrollBar::handle:vertical { - background: #722548; - border-radius: 5px; +QScrollBar::handle:vertical, QScrollBar::handle:horizontal { + background: white; + border-radius: 3px; min-height: 20px; + min-width: 20px; +} +QScrollBar::add-line:vertical, QScrollBar::sub-line:vertical, +QScrollBar::add-line:horizontal, QScrollBar::sub-line:horizontal, +QScrollBar::add-page:vertical, QScrollBar::sub-page:vertical, +QScrollBar::add-page:horizontal, QScrollBar::sub-page:horizontal { + background: none; + height: 0; + width: 0; } QScrollArea { @@ -373,14 +416,44 @@ QScrollArea { } #ProjectList::item:hover { - background-color: rgb(168, 147, 199); + background-color: rgb(163, 148, 184); } #ProjectList::item:selected { - background-color:rgb(82, 69, 101); + background-color:rgb(121, 103, 148); color: rgb(221, 210, 238); } +#ProjectList QScrollBar:vertical { + width: 7px; +} +#ProjectList QScrollBar:horizontal { + height: 7px; +} +#ProjectList QScrollBar:vertical, +#ProjectList QScrollBar:horizontal { + border: none; + background: transparent; + margin: 0; +} +#ProjectList QScrollBar::handle:vertical, +#ProjectList QScrollBar::handle:horizontal { + background: white; + border-radius: 3px; + min-height: 20px; + min-width: 20px; +} +#ProjectList QScrollBar::add-line:vertical, +#ProjectList QScrollBar::sub-line:vertical, +#ProjectList QScrollBar::add-line:horizontal, +#ProjectList QScrollBar::sub-line:horizontal, +#ProjectList QScrollBar::add-page:vertical, +#ProjectList QScrollBar::sub-page:vertical, +#ProjectList QScrollBar::add-page:horizontal, +#ProjectList QScrollBar::sub-page:horizontal { + background: none; +} + #BottomBar { background-color: rgb(42, 10, 25); border-radius: 8px; @@ -389,7 +462,7 @@ QScrollArea { } #BottomBar QLabel { - color: rgb(218, 207, 235); + color: #9882B9; font-family: 'Arial'; font-size: 13px; } @@ -414,7 +487,6 @@ QScrollArea { padding: 5px 10px; } - #NoteWidget QPushButton:hover { background-color:rgb(134, 82, 120); } @@ -432,7 +504,7 @@ QPushButton { } QPushButton:hover { - background-color: rgb(98, 27, 59); + background-color:rgb(69, 24, 44); } QPushButton#switch_theme_button_ { @@ -445,9 +517,7 @@ QPushButton#switch_theme_button_ { border-radius: 7px; padding: 0; margin-bottom: 2px; - border: 2px solid #722548; - background-color: transparent; } @@ -455,13 +525,13 @@ QPushButton::hover#switch_theme_button_ { background-color: #722548; } QPushButton::pressed#switch_theme_button_ { - background-color: #722548; + background-color: rgb(80, 27, 51); } )"; QString main_window_dark_purple_theme = R"( #main-window { - background-color:rgb(9, 6, 10); + background-color: rgb(9, 6, 10); } #main-window QLabel { @@ -470,15 +540,29 @@ QString main_window_dark_purple_theme = R"( } QScrollBar:vertical { + width: 7px; +} +QScrollBar:horizontal { + height: 7px; +} +QScrollBar:vertical, QScrollBar:horizontal { border: none; - background: #221932; - width: 10px; + background: transparent; margin: 0; } -QScrollBar::handle:vertical { - background: #722548; - border-radius: 5px; +QScrollBar::handle:vertical, QScrollBar::handle:horizontal { + background: #775E88; + border-radius: 3px; min-height: 20px; + min-width: 20px; +} +QScrollBar::add-line:vertical, QScrollBar::sub-line:vertical, +QScrollBar::add-line:horizontal, QScrollBar::sub-line:horizontal, +QScrollBar::add-page:vertical, QScrollBar::sub-page:vertical, +QScrollBar::add-page:horizontal, QScrollBar::sub-page:horizontal { + background: none; + height: 0; + width: 0; } QScrollArea { @@ -498,7 +582,7 @@ QScrollArea { } #ProjectList::item { - background-color: rgb(34, 25, 48); + background-color:rgb(50, 41, 66); border: none; padding: 10px; margin: 2px; @@ -506,16 +590,46 @@ QScrollArea { } #ProjectList::item:hover { - background-color: rgb(42, 31, 59); + background-color:rgb(97, 82, 123); } #ProjectList::item:selected { - background-color: #722548; - color: #9882B9; + background-color:rgb(205, 146, 172); + color: #221932; +} + +#ProjectList QScrollBar:vertical { + width: 7px; +} +#ProjectList QScrollBar:horizontal { + height: 7px; +} +#ProjectList QScrollBar:vertical, +#ProjectList QScrollBar:horizontal { + border: none; + background: transparent; + margin: 0; +} +#ProjectList QScrollBar::handle:vertical, +#ProjectList QScrollBar::handle:horizontal { + background: #775E88; + border-radius: 3px; + min-height: 20px; + min-width: 20px; +} +#ProjectList QScrollBar::add-line:vertical, +#ProjectList QScrollBar::sub-line:vertical, +#ProjectList QScrollBar::add-line:horizontal, +#ProjectList QScrollBar::sub-line:horizontal, +#ProjectList QScrollBar::add-page:vertical, +#ProjectList QScrollBar::sub-page:vertical, +#ProjectList QScrollBar::add-page:horizontal, +#ProjectList QScrollBar::sub-page:horizontal { + background: none; } #BottomBar { - background-color: rgb(42, 10, 25); + background-color: #221932; border-radius: 8px; padding: 8px; outline: 0; @@ -533,7 +647,7 @@ QScrollArea { } #NoteWidget { - background-color: #3D2A3D; + background-color: #9882B9; border-radius: 8px; } @@ -542,14 +656,13 @@ QScrollArea { font-size: 13px; font-weight: bold; border-radius: 10px; - background-color: #5D3A5D; - color: #9882B9; + background-color:rgb(113, 97, 137); + color: #221932; padding: 5px 10px; } - #NoteWidget QPushButton:hover { - background-color:rgb(56, 35, 56); + background-color:rgb(69, 58, 87); } QPushButton { @@ -565,7 +678,7 @@ QPushButton { } QPushButton:hover { - background-color: rgb(98, 27, 59); + background-color: #722548; } QPushButton#switch_theme_button_ { width: 20px; @@ -577,22 +690,20 @@ QPushButton#switch_theme_button_ { border-radius: 7px; padding: 0; margin-bottom: 2px; - - border: 2px solid #9882B9; - + border: 2px solid #722548; background-color: transparent; } QPushButton::hover#switch_theme_button_ { - background-color: #9882B9; + background-color: #722548; } QPushButton::pressed#switch_theme_button_ { - background-color:rgb(113, 93, 143); + background-color:rgb(80, 27, 51); } )"; -QString main_window_nature_flat_theme = R"( +QString main_window_blue_theme = R"( #main-window { - background: #07142B; + background: #173C4C; } #main-window QLabel { @@ -601,15 +712,29 @@ QString main_window_nature_flat_theme = R"( } QScrollBar:vertical { + width: 7px; +} +QScrollBar:horizontal { + height: 7px; +} +QScrollBar:vertical, QScrollBar:horizontal { border: none; - background: #173C4C; - width: 10px; + background: transparent; margin: 0; } -QScrollBar::handle:vertical { - background: #568F7C; - border-radius: 5px; +QScrollBar::handle:vertical, QScrollBar::handle:horizontal { + background: rgb(103, 155, 177); + border-radius: 3px; min-height: 20px; + min-width: 20px; +} +QScrollBar::add-line:vertical, QScrollBar::sub-line:vertical, +QScrollBar::add-line:horizontal, QScrollBar::sub-line:horizontal, +QScrollBar::add-page:vertical, QScrollBar::sub-page:vertical, +QScrollBar::add-page:horizontal, QScrollBar::sub-page:horizontal { + background: none; + height: 0; + width: 0; } QScrollArea { @@ -618,7 +743,7 @@ QScrollArea { } #ProjectList { - background-color: #173C4C; + background-color: #07142B; border-radius: 8px; padding: 8px; outline: 0; @@ -638,16 +763,46 @@ QScrollArea { } #ProjectList::item:hover { - background-color: #326D6C; + background-color:rgb(37, 92, 115); } #ProjectList::item:selected { - background-color: #568F7C; - color: #173C4C; + background-color:rgb(73, 159, 158); + color: #07142B; +} + +#ProjectList QScrollBar:vertical { + width: 7px; +} +#ProjectList QScrollBar:horizontal { + height: 7px; +} +#ProjectList QScrollBar:vertical, +#ProjectList QScrollBar:horizontal { + border: none; + background: transparent; + margin: 0; +} +#ProjectList QScrollBar::handle:vertical, +#ProjectList QScrollBar::handle:horizontal { + background: rgb(103, 155, 177); + border-radius: 3px; + min-height: 20px; + min-width: 20px; +} +#ProjectList QScrollBar::add-line:vertical, +#ProjectList QScrollBar::sub-line:vertical, +#ProjectList QScrollBar::add-line:horizontal, +#ProjectList QScrollBar::sub-line:horizontal, +#ProjectList QScrollBar::add-page:vertical, +#ProjectList QScrollBar::sub-page:vertical, +#ProjectList QScrollBar::add-page:horizontal, +#ProjectList QScrollBar::sub-page:horizontal { + background: none; } #BottomBar { - background-color: #173C4C; + background-color: #07142B; border-radius: 8px; padding: 8px; outline: 0; @@ -662,12 +817,12 @@ QScrollArea { #NoteList { border-radius: 8px; - background-color: #173C4C; + background-color: #07142B; border: 1px solid; } #NoteWidget { - background-color: #2D4C3C; + background-color:rgb(103, 155, 177); border-radius: 8px; border: 1px solid; } @@ -677,14 +832,13 @@ QScrollArea { font-size: 13px; font-weight: bold; border-radius: 10px; - background-color: #326D6C; - color: #07142B; + background-color:rgb(61, 104, 122); + color: #BDD1BD; padding: 5px 10px; } - #NoteWidget QPushButton:hover { - background-color:rgb(36, 82, 81); + background-color:rgb(24, 54, 66); } QPushButton { @@ -718,17 +872,15 @@ QPushButton#switch_theme_button_ { border-radius: 7px; padding: 0; margin-bottom: 2px; - - border: 2px solid #85B093; - + border: 2px solid #568F7C; background-color: transparent; } QPushButton::hover#switch_theme_button_ { - background-color: #85B093; + background-color: #568F7C; } QPushButton::pressed#switch_theme_button_ { - background-color:rgb(107, 141, 118); + background-color:rgb(68, 107, 94); } )"; diff --git a/ui/main-window/include/mainwindow.h b/ui/main-window/include/mainwindow.h index 27e60f0..6268aa9 100644 --- a/ui/main-window/include/mainwindow.h +++ b/ui/main-window/include/mainwindow.h @@ -33,17 +33,16 @@ class MainWindow : public QWidget { private slots: void add_project(); void add_note(); - void on_switch_theme_clicked(); + void on_switch_theme_click(); public: explicit MainWindow( QWidget *parent = nullptr, std::string username = "none", - project_storage_model::Storage *storage = nullptr, - int number_of_theme_ = 0 + project_storage_model::Storage *storage = nullptr ); static const std::vector THEMES; - int number_of_theme; + void handle_theme_changed(int theme); }; } // namespace Ui #endif // MAINWINDOW_H \ No newline at end of file diff --git a/ui/main-window/include/notewidget.h b/ui/main-window/include/notewidget.h index f1f8f6a..959eb5d 100644 --- a/ui/main-window/include/notewidget.h +++ b/ui/main-window/include/notewidget.h @@ -20,8 +20,10 @@ class NoteWidget : public QWidget { public: explicit NoteWidget( QWidget *parent = nullptr, - const project_storage_model::Note *model_note = nullptr + const project_storage_model::Note *model_note = nullptr, + int number_of_theme_ = 0 ); + int number_of_theme; private slots: diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index 62dbbf6..099c58a 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -18,6 +18,7 @@ #include "project_dao.hpp" #include "projectitem.h" #include "projectlist.h" +#include "theme_manager.h" namespace Ui { @@ -26,14 +27,13 @@ const std::vector MainWindow::THEMES = { Ui::main_window_dark_autumn_theme, Ui::main_window_dark_purple_theme, Ui::main_window_light_purple_theme, - Ui::main_window_nature_flat_theme + Ui::main_window_blue_theme }; MainWindow::MainWindow( QWidget *parent, std::string username, - project_storage_model::Storage *storage, - int number_of_theme_ + project_storage_model::Storage *storage ) : QWidget(parent), username(username), @@ -46,8 +46,7 @@ MainWindow::MainWindow( new_project_button_(new QPushButton("Новый проект", this)), switch_theme_button_(new QPushButton(this)), new_note_button_(new QPushButton("Новая заметка", this)), - storage_(storage), - number_of_theme(number_of_theme_) { + storage_(storage) { this->setObjectName("main-window"); this->setAttribute(Qt::WA_StyledBackground); this->setMinimumSize(QSize(800, 600)); @@ -70,8 +69,7 @@ MainWindow::MainWindow( switch_theme_button_->setObjectName("switch_theme_button_"); right_layout->addWidget(switch_theme_button_, 0, Qt::AlignRight | Qt::AlignBottom); - - this->setStyleSheet(THEMES[number_of_theme_]); + handle_theme_changed(ThemeManager::instance()->current_theme()); this->project_list_->load_projects(storage); connect( @@ -83,7 +81,7 @@ MainWindow::MainWindow( ); connect( switch_theme_button_, &QPushButton::clicked, this, - &Ui::MainWindow::on_switch_theme_clicked + &Ui::MainWindow::on_switch_theme_click ); connect( new_project_button_, &QPushButton::clicked, this, @@ -93,6 +91,20 @@ MainWindow::MainWindow( new_project_button_, &QPushButton::clicked, this, &Ui::MainWindow::add_project ); + connect(switch_theme_button_, &QPushButton::clicked, this, + &MainWindow::on_switch_theme_click + ); + connect(ThemeManager::instance(), &ThemeManager::theme_changed, + this, &MainWindow::handle_theme_changed); +} + +void MainWindow::handle_theme_changed(int theme) { + this->setStyleSheet(THEMES[theme]); +} + +void MainWindow::on_switch_theme_click() { + int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; + ThemeManager::instance()->apply_theme(next_theme); } void MainWindow::add_project() { @@ -133,10 +145,4 @@ void MainWindow::add_note() { } } - -void MainWindow::on_switch_theme_clicked() { - this->number_of_theme = (this->number_of_theme+1)%THEMES.size(); - setStyleSheet(THEMES[this->number_of_theme]); -} - } // namespace Ui \ No newline at end of file diff --git a/ui/main-window/src/notewidget.cpp b/ui/main-window/src/notewidget.cpp index 3ced750..1b60987 100644 --- a/ui/main-window/src/notewidget.cpp +++ b/ui/main-window/src/notewidget.cpp @@ -8,12 +8,14 @@ namespace Ui { NoteWidget::NoteWidget( QWidget *parent, - const project_storage_model::Note *model_note + const project_storage_model::Note *model_note, + int number_of_theme_ ) : QWidget(parent), model_note_(model_note), main_layout_(new QVBoxLayout(this)), - open_button_(new QPushButton("Открыть")) { + open_button_(new QPushButton("Открыть")), + number_of_theme(number_of_theme_) { this->setObjectName("NoteWidget"); this->setMinimumWidth(100); this->setFixedHeight(100); diff --git a/ui/note-widget/CMakeLists.txt b/ui/note-widget/CMakeLists.txt index d062724..a76f171 100644 --- a/ui/note-widget/CMakeLists.txt +++ b/ui/note-widget/CMakeLists.txt @@ -37,4 +37,4 @@ target_include_directories(NoteWidget $ ) -target_link_libraries(NoteWidget PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts) \ No newline at end of file +target_link_libraries(NoteWidget PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts ThemeManager) \ No newline at end of file diff --git a/ui/note-widget/include/note_edit_dialog.h b/ui/note-widget/include/note_edit_dialog.h index 46048a3..204f15a 100644 --- a/ui/note-widget/include/note_edit_dialog.h +++ b/ui/note-widget/include/note_edit_dialog.h @@ -27,12 +27,15 @@ class NoteEditDialog final : public QDialog { Note* note = new Note(0, "NULL", "NULL") ); ~NoteEditDialog() override; + static const std::vector THEMES; + void handle_theme_changed(int theme); private slots: void on_save_button_click(); void on_join_button_click(); void on_add_members_button_click(); void on_add_tags_button_click(); + void on_switch_theme_button_click(); private: void init_basic_fields(); diff --git a/ui/note-widget/include/note_edit_dialog_styles.h b/ui/note-widget/include/note_edit_dialog_styles.h index 742d78e..636903c 100644 --- a/ui/note-widget/include/note_edit_dialog_styles.h +++ b/ui/note-widget/include/note_edit_dialog_styles.h @@ -5,6 +5,7 @@ namespace Ui { QString note_edit_dialog_light_autumn_theme = R"( + QDialog { background-color: #f5f5f5; } @@ -45,10 +46,6 @@ QString note_edit_dialog_light_autumn_theme = R"( padding: 5px; } - QTextEdit#descriptionTextEdit::placeholder { - color: #727272; - } - /* Основные кнопки */ QHBoxLayout#buttonsLayout { @@ -169,11 +166,184 @@ QString note_edit_dialog_light_autumn_theme = R"( } QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; background-color: transparent; - border-radius: 9px; + border-radius: 7px; border: 2px solid #089083; + padding: 0; + } + QPushButton::hover#switch_theme { + background-color: #089083; + } + QPushButton::pressed#switch_theme { + background-color:rgb(7, 110, 100); + } +)"; + +QString note_edit_dialog_dark_autumn_theme = R"( + QDialog { + background-color: #202020; + } + + QLineEdit#titleLineEdit { + font-family: 'Arial'; + font-size: 25px; + font-weight: bold; + color: #089083; + border: none; + padding: 0; + background: transparent; + } + + QLabel#projectNameLabel { + font-family: 'Arial'; + font-size: 13px; + color: #727272; + padding: 1px; + } + + QLabel#descriptionLabel { + font-family: 'Arial'; + font-size: 18px; + font-weight: bold; + color:rgb(202, 202, 202); + } + + QTextEdit#descriptionTextEdit { + border-radius: 10px; + border: 1px solid #000000; + background: #000000; + color: #727272; padding: 5px; } + + QHBoxLayout#buttonsLayout { + align: left; + } + + QPushButton#saveButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: #fea36b; + color: #263238; + padding: 5px 10px; + } + + QPushButton#saveButton:hover { + background-color: #d58745; + } + + QPushButton#cancelButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: #089083; + color: white; + padding: 5px 10px; + } + + QPushButton#cancelButton:hover { + background-color: #01635d; + } + + QPushButton#joinButton, + QPushButton#addMembersButton, + QPushButton#addDateButton, + QPushButton#addTagsButton { + font-family: 'Arial'; + background-color: #089083; + color: #ffffff; + padding: 5px 10px; + border-radius: 10px; + font-weight: bold; + text-align: left; + } + + QPushButton#joinButton:hover, + QPushButton#addMembersButton:hover, + QPushButton#addDateButton:hover, + QPushButton#addTagsButton:hover { + background-color: #01635d; + } + + QLabel#sidePanelLabel, + QLabel#sidePanelLabel_2 { + font-family: 'Arial'; + font-size: 14px; + font-weight: bold; + color: #727272; + } + + QLabel#membersLabel, + QLabel#tagsLabel, + QLabel#dateLabel { + color: #727272; + } + + QDateEdit#dateEdit { + font-family: 'Arial'; + border-radius: 5px; + background-color: #ffdda2; + color: #050505; + padding: 5px 5px; + border: none; + width: 70px; + height: 22px; + text-align: center; + font-weight: bold; + } + QDateEdit#dateEdit::drop-down { + border: none; + width: 20px; + } + + QMessageBox { + background-color: #263238; + } + + QMessageBox QLabel { + font-family: 'Arial'; + font-size: 14px; + color: #ffffff; + } + + QMessageBox QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + color: #263238; + background-color: #fea36b; + border-radius: 10px; + padding: 5px 15px; + min-width: 60px; + min-height: 25px; + } + + QMessageBox QPushButton:hover { + background-color: #d58745; + } + + QMessageBox QPushButton:pressed { + background-color: #d58745; + border-color: #d58745; + } + + QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + background-color: transparent; + border-radius: 7px; + border: 2px solid #089083; + padding: 0; + } QPushButton::hover#switch_theme { background-color: #089083; } @@ -182,6 +352,518 @@ QString note_edit_dialog_light_autumn_theme = R"( } )"; +QString note_edit_dialog_light_purple_theme = R"( + QDialog { + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, + stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(125, 109, 148)); + } + + QLineEdit#titleLineEdit { + font-family: 'Arial'; + font-size: 25px; + font-weight: bold; + color: rgb(42, 10, 25); + border: none; + padding: 0; + background: transparent; + } + + QLabel#projectNameLabel { + font-family: 'Arial'; + font-size: 13px; + color: rgb(218, 207, 235); + padding: 1px; + } + + QLabel#descriptionLabel { + font-family: 'Arial'; + font-size: 18px; + font-weight: bold; + color: rgb(42, 10, 25); + } + + QTextEdit#descriptionTextEdit { + border-radius: 10px; + border: 1px solid rgb(221, 210, 238); + background: rgb(221, 210, 238); + color: #221932; + padding: 5px; + } + + QHBoxLayout#buttonsLayout { + align: left; + } + + QPushButton#saveButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: #722548; + color: rgb(206, 193, 224); + padding: 5px 10px; + } + + QPushButton#saveButton:hover { + background-color: rgb(98, 27, 59); + } + + QPushButton#cancelButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: rgb(218, 207, 235); + padding: 5px 10px; + } + + QPushButton#cancelButton:hover { + background-color: rgb(27, 6, 16); + } + + QPushButton#joinButton, + QPushButton#addMembersButton, + QPushButton#addDateButton, + QPushButton#addTagsButton { + font-family: 'Arial'; + background-color: rgb(42, 10, 25); + color: rgb(218, 207, 235); + padding: 5px 10px; + border-radius: 10px; + font-weight: bold; + text-align: left; + } + + QPushButton#joinButton:hover, + QPushButton#addMembersButton:hover, + QPushButton#addDateButton:hover, + QPushButton#addTagsButton:hover { + background-color: rgb(27, 6, 16); + } + + QLabel#sidePanelLabel, + QLabel#sidePanelLabel_2 { + font-family: 'Arial'; + font-size: 14px; + font-weight: bold; + color: rgb(218, 207, 235); + } + + QLabel#membersLabel, + QLabel#tagsLabel, + QLabel#dateLabel { + color: rgb(218, 207, 235); + } + + QDateEdit#dateEdit { + font-family: 'Arial'; + border-radius: 5px; + background-color: #ffdda2; + color: #050505; + padding: 5px 5px; + border: none; + width: 70px; + height: 22px; + text-align: center; + font-weight: bold; + } + QDateEdit#dateEdit::drop-down { + border: none; + width: 20px; + } + + QMessageBox { + background-color: rgb(221, 210, 238); + } + + QMessageBox QLabel { + font-family: 'Arial'; + font-size: 14px; + color: #221932; + } + + QMessageBox QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + color: rgb(206, 193, 224); + background-color: #722548; + border-radius: 10px; + padding: 5px 15px; + min-width: 60px; + min-height: 25px; + } + + QMessageBox QPushButton:hover { + background-color: rgb(98, 27, 59); + } + + QMessageBox QPushButton:pressed { + background-color: rgb(98, 27, 59); + border-color: rgb(98, 27, 59); + } + + QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + background-color: transparent; + border-radius: 7px; + border: 2px solid rgb(42, 10, 25); + padding: 0; + } + QPushButton::hover#switch_theme { + background-color: rgb(42, 10, 25); + } + QPushButton::pressed#switch_theme { + background-color:rgb(26, 6, 15); + } +)"; + +QString note_edit_dialog_dark_purple_theme = R"( + QDialog { + background-color:rgb(9, 6, 10); + } + + QLineEdit#titleLineEdit { + font-family: 'Arial'; + font-size: 25px; + font-weight: bold; + color: #9882B9; + border: none; + padding: 0; + background: transparent; + } + + QLabel#projectNameLabel { + font-family: 'Arial'; + font-size: 13px; + color: rgb(176, 170, 185); + padding: 1px; + } + + QLabel#descriptionLabel { + font-family: 'Arial'; + font-size: 18px; + font-weight: bold; + color: #9882B9; + } + + QTextEdit#descriptionTextEdit { + border-radius: 10px; + border: 1px solid #221932; + background: #221932; + color: rgb(176, 170, 185); + padding: 5px; + } + + QHBoxLayout#buttonsLayout { + align: left; + } + + QPushButton#saveButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: #722548; + color: #060407; + padding: 5px 10px; + } + + QPushButton#saveButton:hover { + background-color: rgb(98, 27, 59); + } + + QPushButton#cancelButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: #9882B9; + padding: 5px 10px; + } + + QPushButton#cancelButton:hover { + background-color: rgb(27, 6, 16); + } + + QPushButton#joinButton, + QPushButton#addMembersButton, + QPushButton#addDateButton, + QPushButton#addTagsButton { + font-family: 'Arial'; + background-color: rgb(42, 10, 25); + color: #9882B9; + padding: 5px 10px; + border-radius: 10px; + font-weight: bold; + text-align: left; + } + + QPushButton#joinButton:hover, + QPushButton#addMembersButton:hover, + QPushButton#addDateButton:hover, + QPushButton#addTagsButton:hover { + background-color: rgb(27, 6, 16); + } + + QLabel#sidePanelLabel, + QLabel#sidePanelLabel_2 { + font-family: 'Arial'; + font-size: 14px; + font-weight: bold; + color: #9882B9; + } + + QLabel#membersLabel, + QLabel#tagsLabel, + QLabel#dateLabel { + color: #9882B9; + } + + QDateEdit#dateEdit { + font-family: 'Arial'; + border-radius: 5px; + background-color: #ffdda2; + color: #050505; + padding: 5px 5px; + border: none; + width: 70px; + height: 22px; + text-align: center; + font-weight: bold; + } + QDateEdit#dateEdit::drop-down { + border: none; + width: 20px; + } + + QMessageBox { + background-color: #221932; + } + + QMessageBox QLabel { + font-family: 'Arial'; + font-size: 14px; + color: #9882B9; + } + + QMessageBox QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + color: #060407; + background-color: #722548; + border-radius: 10px; + padding: 5px 15px; + min-width: 60px; + min-height: 25px; + } + + QMessageBox QPushButton:hover { + background-color: rgb(98, 27, 59); + } + + QMessageBox QPushButton:pressed { + background-color: rgb(98, 27, 59); + border-color: rgb(98, 27, 59); + } + + QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + background-color: transparent; + border-radius: 7px; + border: 2px solid #9882B9; + padding: 0; + } + QPushButton::hover#switch_theme { + background-color: #9882B9; + } + QPushButton::pressed#switch_theme { + background-color:rgb(116, 99, 140); + } +)"; + +QString note_edit_dialog_blue_theme = R"( + QDialog { + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, + stop:0 #173C4C, stop:0.5 rgb(30, 66, 65), stop:1 #07142B); + } + + QLineEdit#titleLineEdit { + font-family: 'Arial'; + font-size: 25px; + font-weight: bold; + color: #BDD1BD; + border: none; + padding: 0; + background: transparent; + } + + QLabel#projectNameLabel { + font-family: 'Arial'; + font-size: 13px; + color: #BDD1BD; + padding: 1px; + } + + QLabel#descriptionLabel { + font-family: 'Arial'; + font-size: 18px; + font-weight: bold; + color: #BDD1BD; + } + + QTextEdit#descriptionTextEdit { + border-radius: 10px; + border: 1px solid #568F7C; + background: #07142B; + color: #BDD1BD; + padding: 5px; + } + + QHBoxLayout#buttonsLayout { + align: left; + } + + QPushButton#saveButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: #568F7C; + color: #BDD1BD; + padding: 5px 10px; + border: none; + font-weight: bold; + } + + QPushButton#saveButton:hover { + background-color: #326D6C; + } + + QPushButton#saveButton:pressed { + background-color: #07142B; + } + + QPushButton#cancelButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: #326D6C; + color: #BDD1BD; + padding: 5px 10px; + border: 1px solid #568F7C; + } + + QPushButton#cancelButton:hover { + background-color: #568F7C; + color: #07142B; + } + + QPushButton#joinButton, + QPushButton#addMembersButton, + QPushButton#addDateButton, + QPushButton#addTagsButton { + font-family: 'Arial'; + background-color: #326D6C; + color: #BDD1BD; + padding: 5px 10px; + border-radius: 10px; + font-weight: bold; + text-align: left; + } + + QPushButton#joinButton:hover, + QPushButton#addMembersButton:hover, + QPushButton#addDateButton:hover, + QPushButton#addTagsButton:hover { + background-color: #568F7C; + color: #07142B; + } + + QLabel#sidePanelLabel, + QLabel#sidePanelLabel_2 { + font-family: 'Arial'; + font-size: 14px; + font-weight: bold; + color: #BDD1BD; + } + + QLabel#membersLabel, + QLabel#tagsLabel, + QLabel#dateLabel { + color: #BDD1BD; + } + + QDateEdit#dateEdit { + font-family: 'Arial'; + border-radius: 5px; + background-color: #ffdda2; + color: #050505; + padding: 5px 5px; + border: none; + width: 70px; + height: 22px; + text-align: center; + font-weight: bold; + } + QDateEdit#dateEdit::drop-down { + border: none; + width: 20px; + } + + QMessageBox { + background-color: #07142B; + } + + QMessageBox QLabel { + font-family: 'Arial'; + font-size: 14px; + color: #BDD1BD; + } + + QMessageBox QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + color: #BDD1BD; + background-color: #568F7C; + border-radius: 10px; + padding: 5px 15px; + min-width: 60px; + min-height: 25px; + } + + QMessageBox QPushButton:hover { + background-color: #326D6C; + } + + QMessageBox QPushButton:pressed { + background-color: #07142B; + border-color: #07142B; + } + + QPushButton#switch_theme { + width: 20px; + height: 20px; + min-width: 20px; + min-height: 20px; + max-width: 20px; + max-height: 20px; + background-color: transparent; + border-radius: 7px; + border: 2px solid #326D6C; + padding: 0; + } + QPushButton::hover#switch_theme { + background-color: #326D6C; + } + QPushButton::pressed#switch_theme { + background-color:rgb(33, 74, 74); + } +)"; + } // namespace Ui #endif // NOTE_EDIT_DIALOG_STYLES_H \ No newline at end of file diff --git a/ui/note-widget/src/note_edit_dialog.cpp b/ui/note-widget/src/note_edit_dialog.cpp index 620f577..664a043 100644 --- a/ui/note-widget/src/note_edit_dialog.cpp +++ b/ui/note-widget/src/note_edit_dialog.cpp @@ -10,11 +10,21 @@ #include "./ui_note_edit_dialog.h" #include "note_edit_dialog_styles.h" #include "tags_dialog.h" +#include "theme_manager.h" + + +const std::vector NoteEditDialog::THEMES = { + Ui::note_edit_dialog_light_autumn_theme, + Ui::note_edit_dialog_dark_autumn_theme, + Ui::note_edit_dialog_dark_purple_theme, + Ui::note_edit_dialog_light_purple_theme, + Ui::note_edit_dialog_blue_theme +}; NoteEditDialog::NoteEditDialog(QWidget* parent, Note* note) : QDialog(parent), ui_(new Ui::NoteEditDialog), - note_(note) { + note_(note) { ui_->setupUi(this); setWindowTitle("EFFICIO"); @@ -22,10 +32,13 @@ NoteEditDialog::NoteEditDialog(QWidget* parent, Note* note) init_additional_fields(); setup_connections(); setup_ui(); + + handle_theme_changed(ThemeManager::instance()->current_theme()); + } -NoteEditDialog::~NoteEditDialog() { - delete ui_; +void NoteEditDialog::handle_theme_changed(int theme) { + this->setStyleSheet(THEMES[theme]); } void NoteEditDialog::init_basic_fields() { @@ -33,6 +46,17 @@ void NoteEditDialog::init_basic_fields() { ui_->descriptionTextEdit->setText(QString::fromStdString(note_->get_text())); } + +void NoteEditDialog::on_switch_theme_button_click() { + int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; + ThemeManager::instance()->apply_theme(next_theme); +} + + +NoteEditDialog::~NoteEditDialog() { + delete ui_; +} + void NoteEditDialog::init_additional_fields() { if (!note_->get_date().empty()) { QDate date = QDate::fromString(QString::fromStdString(note_->get_date()), "yyyy-MM-dd"); @@ -78,12 +102,17 @@ void NoteEditDialog::setup_connections() { ui_->dateLabel->setVisible(!is_visible); ui_->dateEdit->setVisible(!is_visible); }); + connect(ui_->switch_theme, &QPushButton::clicked, this, + &NoteEditDialog::on_switch_theme_button_click + ); + connect(ThemeManager::instance(), &ThemeManager::theme_changed, + this, &NoteEditDialog::handle_theme_changed); connect(ui_->addTagsButton, &QPushButton::clicked, this, &NoteEditDialog::on_add_tags_button_click); } void NoteEditDialog::setup_ui() { setFixedSize(700, 480); - setStyleSheet(Ui::note_edit_dialog_light_autumn_theme); + setStyleSheet(THEMES[ThemeManager::instance()->current_theme()]); ui_->buttonsLayout->setAlignment(Qt::AlignLeft); } diff --git a/ui/note-widget/ui/note_edit_dialog.ui b/ui/note-widget/ui/note_edit_dialog.ui index ed50361..e0057f3 100644 --- a/ui/note-widget/ui/note_edit_dialog.ui +++ b/ui/note-widget/ui/note_edit_dialog.ui @@ -240,7 +240,7 @@ - я + 504 20 171 @@ -363,6 +363,28 @@ + + + + 660 + 440 + 20 + 20 + + + + + 20 + 20 + + + + + 20 + 20 + + + diff --git a/ui/theme-manager/CMakeLists.txt b/ui/theme-manager/CMakeLists.txt new file mode 100644 index 0000000..a290e94 --- /dev/null +++ b/ui/theme-manager/CMakeLists.txt @@ -0,0 +1,32 @@ +cmake_minimum_required(VERSION 3.16) + +project(ThemeManager LANGUAGES CXX) + +set(CMAKE_CXX_STANDARD 20) +set(CMAKE_CXX_STANDARD_REQUIRED ON) + +find_package(Qt6 COMPONENTS Core Gui Widgets Core Gui Sql REQUIRED) + +set(CMAKE_AUTOMOC ON) +set(CMAKE_AUTOUIC ON) +set(CMAKE_AUTORCC ON) + + +set(SOURCES + src/theme_manager.cpp +) + +set(HEADERS + include/theme_manager.h +) + +add_library(ThemeManager STATIC ${SOURCES} ${HEADERS}) + +target_include_directories(ThemeManager + PUBLIC + $ + $ +) + +target_link_libraries(ThemeManager PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts) + diff --git a/ui/theme-manager/include/theme_manager.h b/ui/theme-manager/include/theme_manager.h new file mode 100644 index 0000000..2a24aaf --- /dev/null +++ b/ui/theme-manager/include/theme_manager.h @@ -0,0 +1,28 @@ +#ifndef THEME_MANAGER_H +#define THEME_MANAGER_H + +#include +#include +#include +#include +#include + +class ThemeManager : public QObject { + Q_OBJECT + +public: + static ThemeManager* instance(); + + void apply_theme(int theme); + int current_theme() const; + +signals: + void theme_changed(int new_theme); + +private: + explicit ThemeManager(QObject *parent = nullptr); + static ThemeManager* m_instance; + int current_theme_; +}; + +#endif // THEME_MANAGER_H \ No newline at end of file diff --git a/ui/theme-manager/src/theme_manager.cpp b/ui/theme-manager/src/theme_manager.cpp new file mode 100644 index 0000000..6a34df6 --- /dev/null +++ b/ui/theme-manager/src/theme_manager.cpp @@ -0,0 +1,27 @@ +#include "theme_manager.h" +#include +#include + +ThemeManager* ThemeManager::m_instance = nullptr; + +ThemeManager::ThemeManager(QObject *parent) + : QObject(parent) { + current_theme_ = 0; + emit theme_changed(this->current_theme_); +} + +ThemeManager* ThemeManager::instance() { + if (!m_instance) { + m_instance = new ThemeManager(); + } + return m_instance; +} + +void ThemeManager::apply_theme(int theme) { + this->current_theme_ = theme; + emit theme_changed(this->current_theme_); +} + +int ThemeManager::current_theme() const { + return current_theme_; +} \ No newline at end of file From 7440881c67482319d00ff0e5192cd240d0ab5116 Mon Sep 17 00:00:00 2001 From: MuravAna Date: Tue, 15 Apr 2025 23:07:23 +0300 Subject: [PATCH 07/17] Fix bug with double messages after press buttons in autorization's windows and mainwindow --- .gitignore | 1 + ui/authorization-windows/src/login_window.cpp | 101 +++++++++--------- .../src/registration_window.cpp | 76 ++++++------- ui/main-window/src/mainwindow.cpp | 7 -- 4 files changed, 90 insertions(+), 95 deletions(-) diff --git a/.gitignore b/.gitignore index 0ff8f19..973087b 100644 --- a/.gitignore +++ b/.gitignore @@ -4,6 +4,7 @@ build-* */build-* release/ debug/ +protobuf/ *.exe *.dll *.so diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index 14c3ed6..cfc462f 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -40,16 +40,14 @@ LoginWindow::LoginWindow(QWidget *parent) connect( ui->switch_theme, &QPushButton::clicked, this, &LoginWindow::on_switch_theme_clicked - ); + , Qt::UniqueConnection); connect( ui->switch_mode, &QPushButton::clicked, this, - &LoginWindow::on_switch_mode_clicked - ); + &LoginWindow::on_switch_mode_clicked); connect( ui->push_enter, &QPushButton::clicked, this, - &LoginWindow::on_push_enter_clicked - ); + &LoginWindow::on_push_enter_clicked); connect(ThemeManager::instance(), &ThemeManager::theme_changed, this, &LoginWindow::handle_theme_changed); } @@ -92,56 +90,57 @@ void LoginWindow::on_switch_mode_clicked() { } void LoginWindow::on_push_enter_clicked() { - QString login = ui->input_login->text(); - QString password = ui->input_password->text(); - - if (!login.isEmpty() && !password.isEmpty()) { - if (login.size() > 50) { - QMessageBox::warning( - this, "Ошибка", - "Длина логина не должна превышать пятидесяти символов" - ); - } else if (password.size() > 50) { - QMessageBox::warning( - this, "Ошибка", - "Длина пароля не должна превышать пятидесяти символов" - ); - } else if (LRDao::validate_user(login, password)) { - QMessageBox::information( - this, "Вход", "Вы успешно вошли! Добро пожаловать :)" - ); - QWidget *parent = this->parentWidget(); - - QMainWindow *app_window = qobject_cast(parent); - - if (QWidget *old = app_window->centralWidget()) { - old->deleteLater(); + if ((this->counter_on_switch_theme_clicks++)%2){ + QString login = ui->input_login->text(); + QString password = ui->input_password->text(); + + if (!login.isEmpty() && !password.isEmpty()) { + if (login.size() > 50) { + QMessageBox::warning( + this, "Ошибка", + "Длина логина не должна превышать пятидесяти символов" + ); + } else if (password.size() > 50) { + QMessageBox::warning( + this, "Ошибка", + "Длина пароля не должна превышать пятидесяти символов" + ); + } else if (LRDao::validate_user(login, password)) { + QMessageBox::information( + this, "Вход", "Вы успешно вошли! Добро пожаловать :)" + ); + QWidget *parent = this->parentWidget(); + + QMainWindow *app_window = qobject_cast(parent); + + if (QWidget *old = app_window->centralWidget()) { + old->deleteLater(); + } + project_storage_model::Storage *storage = + new project_storage_model::Storage(); + Serialization::get_storage(*storage, login.toStdString()); + + Ui::MainWindow *main_window = + new Ui::MainWindow(app_window, login.toStdString(), storage); + + app_window->setCentralWidget(main_window); + app_window->resize(800, 600); + QRect screenGeometry = + QApplication::primaryScreen()->availableGeometry(); + int x = (screenGeometry.width() - main_window->width()) / 2; + int y = (screenGeometry.height() - main_window->height()) / 2; + app_window->move(x, y); + + this->close(); + } else { + QMessageBox::warning( + this, "Ошибка ввода данных", "Неверный логин или пароль!" + ); } - // todo load all projects of user to storage - project_storage_model::Storage *storage = - new project_storage_model::Storage(); - Serialization::get_storage(*storage, login.toStdString()); - - Ui::MainWindow *main_window = - new Ui::MainWindow(app_window, login.toStdString(), storage); - - app_window->setCentralWidget(main_window); - app_window->resize(800, 600); - QRect screenGeometry = - QApplication::primaryScreen()->availableGeometry(); - int x = (screenGeometry.width() - main_window->width()) / 2; - int y = (screenGeometry.height() - main_window->height()) / 2; - app_window->move(x, y); - - this->close(); } else { QMessageBox::warning( - this, "Ошибка ввода данных", "Неверный логин или пароль!" + this, "Ошибка ввода данных", "Пожалуйста, заполните все поля!" ); } - } else { - QMessageBox::warning( - this, "Ошибка ввода данных", "Пожалуйста, заполните все поля!" - ); } } \ No newline at end of file diff --git a/ui/authorization-windows/src/registration_window.cpp b/ui/authorization-windows/src/registration_window.cpp index 0a5017e..dcf44e8 100644 --- a/ui/authorization-windows/src/registration_window.cpp +++ b/ui/authorization-windows/src/registration_window.cpp @@ -43,16 +43,16 @@ RegistrationWindow::RegistrationWindow(QWidget *parent) connect( ui->switch_theme, &QPushButton::clicked, this, &RegistrationWindow::on_switch_theme_clicked - ); + , Qt::UniqueConnection); connect( ui->push_registration, &QPushButton::clicked, this, &RegistrationWindow::on_push_registration_clicked - ); + , Qt::UniqueConnection); connect( ui->switch_mode, &QPushButton::clicked, this, &RegistrationWindow::on_switch_mode_clicked - ); + , Qt::UniqueConnection); connect(ThemeManager::instance(), &ThemeManager::theme_changed, this, &RegistrationWindow::handle_theme_changed); handle_theme_changed(ThemeManager::instance()->current_theme()); @@ -140,47 +140,49 @@ bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { } void RegistrationWindow::on_push_registration_clicked() { - QString created_login = ui->create_login->text(); - QString created_password = ui->create_password->text(); - QString repeated_password = ui->repeat_password->text(); - - if (!created_login.isEmpty() && !created_password.isEmpty() && - !repeated_password.isEmpty()) { - if (created_password != repeated_password) { - QMessageBox::warning(this, "Ошибка", "Пароли не совпадают!"); - } else if (created_login.size() > 50) { - QMessageBox::warning( - this, "Ошибка", - "Длина логина не должна превышать пятидесяти символов" - ); - } else if (created_password.size() > 50) { - QMessageBox::warning( - this, "Ошибка", - "Длина пароля не должна превышать пятидесяти символов" - ); - } else if (is_strong_and_valid_password(created_password)) { - int try_register_user = - LRDao::try_register_user(created_login, created_password); - if (try_register_user == 0) { + if ((this->counter_on_switch_theme_clicks++)%2){ + QString created_login = ui->create_login->text(); + QString created_password = ui->create_password->text(); + QString repeated_password = ui->repeat_password->text(); + + if (!created_login.isEmpty() && !created_password.isEmpty() && + !repeated_password.isEmpty()) { + if (created_password != repeated_password) { + QMessageBox::warning(this, "Ошибка", "Пароли не совпадают!"); + } else if (created_login.size() > 50) { QMessageBox::warning( this, "Ошибка", - "Извините, внутренняя ошибка с базами данных." + "Длина логина не должна превышать пятидесяти символов" ); - } else if (try_register_user == -1) { + } else if (created_password.size() > 50) { QMessageBox::warning( this, "Ошибка", - "Пользователь с таким именем уже существует. Пожалуйста, " - "придумайте другое!" - ); - } else { - QMessageBox::information( - this, "Регистрация", - "Вы успешно зарегистрировались! Пожалуйста, выполните вход." + "Длина пароля не должна превышать пятидесяти символов" ); - on_switch_mode_clicked(); + } else if (is_strong_and_valid_password(created_password)) { + int try_register_user = + LRDao::try_register_user(created_login, created_password); + if (try_register_user == 0) { + QMessageBox::warning( + this, "Ошибка", + "Извините, внутренняя ошибка с базами данных." + ); + } else if (try_register_user == -1) { + QMessageBox::warning( + this, "Ошибка", + "Пользователь с таким именем уже существует. Пожалуйста, " + "придумайте другое!" + ); + } else { + QMessageBox::information( + this, "Регистрация", + "Вы успешно зарегистрировались! Пожалуйста, выполните вход." + ); + on_switch_mode_clicked(); + } } + } else { + QMessageBox::warning(this, "Ошибка", "Пожалуйста, заполните все поля."); } - } else { - QMessageBox::warning(this, "Ошибка", "Пожалуйста, заполните все поля."); } } \ No newline at end of file diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index 099c58a..ab64112 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -87,13 +87,6 @@ MainWindow::MainWindow( new_project_button_, &QPushButton::clicked, this, &Ui::MainWindow::add_project ); - connect( - new_project_button_, &QPushButton::clicked, this, - &Ui::MainWindow::add_project - ); - connect(switch_theme_button_, &QPushButton::clicked, this, - &MainWindow::on_switch_theme_click - ); connect(ThemeManager::instance(), &ThemeManager::theme_changed, this, &MainWindow::handle_theme_changed); } From c698ca35283bab3e3b349dfdc2c60ea43dc77ca7 Mon Sep 17 00:00:00 2001 From: MuravAna Date: Thu, 8 May 2025 22:27:49 +0300 Subject: [PATCH 08/17] Implement profile and settings windows. Complete profile window, settings in process --- CMakeLists.txt | 6 +- database/include/lr_dao.hpp | 1 + database/src/lr_dao.cpp | 9 + main.cpp | 12 +- ui/authorization-windows/CMakeLists.txt | 3 +- .../include/login_window.h | 22 +- .../include/registration_window.h | 15 +- ui/authorization-windows/src/login_window.cpp | 47 ++- .../src/registration_window.cpp | 9 +- ui/main-window/CMakeLists.txt | 2 + ui/main-window/include/bottombar.h | 20 +- ui/main-window/include/main_window_style.hpp | 77 +++- ui/main-window/include/mainwindow.h | 13 +- ui/main-window/src/bottombar.cpp | 24 +- ui/main-window/src/mainwindow.cpp | 58 ++- ui/profile-window/CMakeLists.txt | 40 ++ ui/profile-window/include/profile_window.h | 46 ++ .../include/profile_window_style_sheet.h | 393 ++++++++++++++++++ ui/profile-window/src/profile_window.cpp | 110 +++++ ui/settings-window/CMakeLists.txt | 39 ++ ui/settings-window/include/settings_window.h | 41 ++ .../include/settings_window_style_sheet.h | 99 +++++ ui/settings-window/src/settings_window.cpp | 87 ++++ 23 files changed, 1085 insertions(+), 88 deletions(-) create mode 100644 ui/profile-window/CMakeLists.txt create mode 100644 ui/profile-window/include/profile_window.h create mode 100644 ui/profile-window/include/profile_window_style_sheet.h create mode 100644 ui/profile-window/src/profile_window.cpp create mode 100644 ui/settings-window/CMakeLists.txt create mode 100644 ui/settings-window/include/settings_window.h create mode 100644 ui/settings-window/include/settings_window_style_sheet.h create mode 100644 ui/settings-window/src/settings_window.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index af92482..fdd1382 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -13,10 +13,12 @@ find_package(Qt6 COMPONENTS Widgets Core Gui Sql REQUIRED) add_subdirectory(scripts) add_subdirectory(database) +add_subdirectory(ui/profile-window) add_subdirectory(ui/main-window) add_subdirectory(ui/authorization-windows) add_subdirectory(ui/note-widget) add_subdirectory(ui/theme-manager) +add_subdirectory(ui/settings-window) add_subdirectory(proto) add_executable(EfficioTaskTracker main.cpp) @@ -29,8 +31,10 @@ target_link_libraries(EfficioTaskTracker PRIVATE efficio-rpc Database Scripts + ThemeManager AuthorizationWindows + ProfileWindow MainWindow NoteWidget - ThemeManager + SettingsWindow ) \ No newline at end of file diff --git a/database/include/lr_dao.hpp b/database/include/lr_dao.hpp index de8d5fb..d4eed41 100644 --- a/database/include/lr_dao.hpp +++ b/database/include/lr_dao.hpp @@ -7,6 +7,7 @@ class LRDao { public: LRDao() = default; static int try_register_user(const QString &login, const QString &password); + static bool try_delete_user(const QString &login); static bool validate_user(const QString &login, const QString &password); static bool add_project_to_user(std::string user_login, int project_id); static bool diff --git a/database/src/lr_dao.cpp b/database/src/lr_dao.cpp index 3107f5b..5c60887 100644 --- a/database/src/lr_dao.cpp +++ b/database/src/lr_dao.cpp @@ -29,6 +29,15 @@ int LRDao::try_register_user(const QString &login, const QString &password) { ); } +bool LRDao::try_delete_user(const QString &login) { + QSqlQuery query; + + return DatabaseManager::get_instance().execute_query( + query, "DELETE FROM users WHERE login = ?", + {login} + ); +} + bool LRDao::validate_user(const QString &login, const QString &password) { QSqlQuery query; diff --git a/main.cpp b/main.cpp index 0321f15..83ba433 100644 --- a/main.cpp +++ b/main.cpp @@ -5,13 +5,14 @@ #include #include "applicationwindow.h" #include "login_window.h" +#include "settings_window.h" #include "mainwindow.h" #include "theme_manager.h" int main(int argc, char *argv[]) { QApplication application(argc, argv); - - ThemeManager* themeManager = ThemeManager::instance(); + application.setApplicationName("EFFICIO"); + application.setApplicationDisplayName("EFFICIO"); QTranslator translator; const QStringList ui_languages = QLocale::system().uiLanguages(); @@ -23,7 +24,10 @@ int main(int argc, char *argv[]) { } } - auto *app_window = new Ui::ApplicationWindow("EFFICIO"); + ThemeManager* themeManager = ThemeManager::instance(); + + QMainWindow *app_window = new QMainWindow(); + app_window->setWindowTitle("EFFICIO"); auto *login_window = new LoginWindow(app_window); app_window->setCentralWidget(login_window); @@ -33,5 +37,5 @@ int main(int argc, char *argv[]) { app_window->move(x, y); app_window->show(); - return QApplication::exec(); + return application.exec(); } diff --git a/ui/authorization-windows/CMakeLists.txt b/ui/authorization-windows/CMakeLists.txt index 4926ac5..6096233 100644 --- a/ui/authorization-windows/CMakeLists.txt +++ b/ui/authorization-windows/CMakeLists.txt @@ -16,6 +16,7 @@ set(CMAKE_AUTOUIC_SEARCH_PATHS ${CMAKE_CURRENT_SOURCE_DIR}/ui) set(UI_FILES ${CMAKE_CURRENT_SOURCE_DIR}/ui/login_window.ui ${CMAKE_CURRENT_SOURCE_DIR}/ui/registration_window.ui + ${CMAKE_CURRENT_BINARY_DIR} ) set(SOURCES @@ -40,4 +41,4 @@ target_include_directories(AuthorizationWindows $ ) -target_link_libraries(AuthorizationWindows PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts MainWindow ThemeManager) \ No newline at end of file +target_link_libraries(AuthorizationWindows PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts MainWindow ThemeManager ProfileWindow) \ No newline at end of file diff --git a/ui/authorization-windows/include/login_window.h b/ui/authorization-windows/include/login_window.h index beeaa8d..b28a491 100644 --- a/ui/authorization-windows/include/login_window.h +++ b/ui/authorization-windows/include/login_window.h @@ -1,27 +1,23 @@ #pragma once -#include -#include -#include -#include #include -#include "database_manager.hpp" -#include "lr_dao.hpp" #include +#include QT_BEGIN_NAMESPACE -namespace Ui { -class LoginWindow; -} + namespace Ui { + class LoginWindow; + } QT_END_NAMESPACE -class LoginWindow : public QWidget { +class LoginWindow : public QWidget +{ Q_OBJECT public: explicit LoginWindow(QWidget *parent = nullptr); - ~LoginWindow(); - + ~LoginWindow() override; + static const std::vector THEMES; void handle_theme_changed(int theme); @@ -31,6 +27,6 @@ private slots: void on_switch_theme_clicked(); private: - Ui::LoginWindow *ui; + std::shared_ptr ui; int counter_on_switch_theme_clicks = 0; }; \ No newline at end of file diff --git a/ui/authorization-windows/include/registration_window.h b/ui/authorization-windows/include/registration_window.h index 2870845..671bd41 100644 --- a/ui/authorization-windows/include/registration_window.h +++ b/ui/authorization-windows/include/registration_window.h @@ -1,26 +1,19 @@ #pragma once -#include -#include #include -#include "database_manager.hpp" -#include "lr_dao.hpp" #include -QT_BEGIN_NAMESPACE - namespace Ui { -class RegistrationWindow; + class RegistrationWindow; } -QT_END_NAMESPACE - class RegistrationWindow : public QWidget { Q_OBJECT public: explicit RegistrationWindow(QWidget *parent = nullptr); - ~RegistrationWindow(); + ~RegistrationWindow() override; + bool is_strong_and_valid_password(const QString &password); static const std::vector THEMES; void handle_theme_changed(int theme); @@ -31,6 +24,6 @@ private slots: void on_switch_theme_clicked(); private: - Ui::RegistrationWindow *ui; + std::shared_ptr ui; int counter_on_switch_theme_clicks = 0; }; \ No newline at end of file diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index cfc462f..485a134 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -18,6 +18,8 @@ #include "login_window_style_sheet.h" #include "theme_manager.h" +#include + const std::vector LoginWindow::THEMES = { Ui::login_window_light_autumn_theme, Ui::login_window_dark_autumn_theme, @@ -52,7 +54,6 @@ LoginWindow::LoginWindow(QWidget *parent) this, &LoginWindow::handle_theme_changed); } - void LoginWindow::handle_theme_changed(int theme) { this->setStyleSheet(THEMES[theme]); } @@ -64,9 +65,7 @@ void LoginWindow::on_switch_theme_clicked() { } } -LoginWindow::~LoginWindow() { - delete ui; -} +LoginWindow::~LoginWindow() = default; void LoginWindow::on_switch_mode_clicked() { QWidget *parent = this->parentWidget(); @@ -109,29 +108,45 @@ void LoginWindow::on_push_enter_clicked() { QMessageBox::information( this, "Вход", "Вы успешно вошли! Добро пожаловать :)" ); - QWidget *parent = this->parentWidget(); - - QMainWindow *app_window = qobject_cast(parent); - - if (QWidget *old = app_window->centralWidget()) { - old->deleteLater(); - } + QMainWindow *app_window = qobject_cast(this->parentWidget()); + this->deleteLater(); project_storage_model::Storage *storage = new project_storage_model::Storage(); Serialization::get_storage(*storage, login.toStdString()); Ui::MainWindow *main_window = new Ui::MainWindow(app_window, login.toStdString(), storage); - + + connect(main_window, &Ui::MainWindow::logout_requested, app_window, [app_window]() { + LoginWindow *login_window = new LoginWindow(app_window); + app_window->setCentralWidget(login_window); + app_window->resize(380, 480); + QRect screenGeometry = + QApplication::primaryScreen()->availableGeometry(); + int x = (screenGeometry.width() - login_window->width()) / 2; + int y = (screenGeometry.height() - login_window->height()) / 2; + app_window->move(x, y); + app_window->show(); + }); + connect(main_window, &Ui::MainWindow::delete_account_requested, app_window, [app_window]() { + RegistrationWindow *registration_window = new RegistrationWindow(app_window); + app_window->setCentralWidget(registration_window); + app_window->resize(380, 480); + QRect screenGeometry = + QApplication::primaryScreen()->availableGeometry(); + int x = (screenGeometry.width() - registration_window->width()) / 2; + int y = (screenGeometry.height() - registration_window->height()) / 2; + app_window->move(x, y); + app_window->show(); + }); app_window->setCentralWidget(main_window); app_window->resize(800, 600); QRect screenGeometry = QApplication::primaryScreen()->availableGeometry(); - int x = (screenGeometry.width() - main_window->width()) / 2; - int y = (screenGeometry.height() - main_window->height()) / 2; + int x = (screenGeometry.width() - 800) / 2; + int y = (screenGeometry.height() - 600) / 2; app_window->move(x, y); - - this->close(); + app_window->show(); } else { QMessageBox::warning( this, "Ошибка ввода данных", "Неверный логин или пароль!" diff --git a/ui/authorization-windows/src/registration_window.cpp b/ui/authorization-windows/src/registration_window.cpp index dcf44e8..2ce13e9 100644 --- a/ui/authorization-windows/src/registration_window.cpp +++ b/ui/authorization-windows/src/registration_window.cpp @@ -4,6 +4,7 @@ #include #include #include +#include #include #include #include "applicationwindow.h" @@ -11,10 +12,9 @@ #include "database_manager.hpp" #include "login_window.h" #include "lr_dao.hpp" -#include "mainwindow.h" #include "notelist.h" -#include "registration_window.h" #include "registration_window_style_sheet.h" +#include "ui_registration_window.h" #include #include "theme_manager.h" @@ -71,9 +71,7 @@ void RegistrationWindow::on_switch_theme_clicked() { } -RegistrationWindow::~RegistrationWindow() { - delete ui; -} +RegistrationWindow::~RegistrationWindow() = default; void RegistrationWindow::on_switch_mode_clicked() { QWidget *parent = this->parentWidget(); @@ -83,7 +81,6 @@ void RegistrationWindow::on_switch_mode_clicked() { if (QWidget *old = app_window->centralWidget()) { old->deleteLater(); } - project_storage_model::Storage storage; LoginWindow *login_window = new LoginWindow(app_window); app_window->setCentralWidget(login_window); diff --git a/ui/main-window/CMakeLists.txt b/ui/main-window/CMakeLists.txt index d2ef5a1..bd562c4 100644 --- a/ui/main-window/CMakeLists.txt +++ b/ui/main-window/CMakeLists.txt @@ -37,4 +37,6 @@ target_link_libraries(MainWindow PRIVATE Database NoteWidget ThemeManager + ProfileWindow + AuthorizationWindows ) \ No newline at end of file diff --git a/ui/main-window/include/bottombar.h b/ui/main-window/include/bottombar.h index cc7945c..3634dfb 100644 --- a/ui/main-window/include/bottombar.h +++ b/ui/main-window/include/bottombar.h @@ -3,21 +3,29 @@ #include #include +#include #include #include namespace Ui { class BottomBar : public QWidget { - QHBoxLayout *main_layout_; - QLabel *project_name_; - QLabel *username_; + Q_OBJECT public: BottomBar( - QWidget *parent_, - std::string username_, - std::string project_name_ + QWidget *parent, + std::string username, + std::string project_name ); + +signals: + void profile_button_clicked(); + +private: + QHBoxLayout *main_layout_; + QLabel *project_name_; + QLabel *username_; + QPushButton *profile_button_; }; } // namespace Ui diff --git a/ui/main-window/include/main_window_style.hpp b/ui/main-window/include/main_window_style.hpp index 58cd8dc..dd6dcb6 100644 --- a/ui/main-window/include/main_window_style.hpp +++ b/ui/main-window/include/main_window_style.hpp @@ -115,6 +115,18 @@ QScrollArea { font-size: 13px; } +#BottomBar QPushButton { + color: white; + font-family: 'Arial'; + font-size: 13px; +} + +#BottomBar QPushButton:hover { + color:rgb(182, 181, 181); + font-family: 'Arial'; + font-size: 13px; +} + #NoteList { border-radius : 8px; background-color: white; @@ -293,6 +305,19 @@ QString main_window_dark_autumn_theme = R"( font-size: 13px; } + #BottomBar QPushButton { + color: #c0c0c0; + font-family: 'Arial'; + font-size: 13px; + } + + #BottomBar QPushButton:hover { + color:rgb(236, 234, 234); + font-family: 'Arial'; + font-size: 13px; + } + + #NoteList { border-radius: 8px; background-color: black; @@ -333,6 +358,10 @@ QString main_window_dark_autumn_theme = R"( background-color:rgb(181, 114, 59); } + QPushButton:pressed { + background-color:rgb(143, 88, 44); + } + QPushButton#switch_theme_button_ { width: 20px; height: 20px; @@ -467,6 +496,20 @@ QScrollArea { font-size: 13px; } +#BottomBar QPushButton { + color: #9882B9; + font-family: 'Arial'; + font-size: 13px; +} + +#BottomBar QPushButton:hover { + color:rgb(208, 193, 231); + font-family: 'Arial'; + font-size: 13px; +} + + + #NoteList { border-radius: 8px; background-color: rgb(221, 210, 238); @@ -507,6 +550,10 @@ QPushButton:hover { background-color:rgb(69, 24, 44); } +QPushButton:pressed { + background-color:rgb(47, 16, 30); +} + QPushButton#switch_theme_button_ { width: 20px; height: 20px; @@ -522,7 +569,7 @@ QPushButton#switch_theme_button_ { } QPushButton::hover#switch_theme_button_ { - background-color: #722548; + background-color:rgb(86, 26, 53); } QPushButton::pressed#switch_theme_button_ { background-color: rgb(80, 27, 51); @@ -641,6 +688,18 @@ QScrollArea { font-size: 13px; } +#BottomBar QPushButton { + color: #9882B9; + font-family: 'Arial'; + font-size: 13px; +} + +#BottomBar QPushButton:hover { + color:rgb(198, 183, 221); + font-family: 'Arial'; + font-size: 13px; +} + #NoteList { border-radius: 8px; background-color: #221932; @@ -680,6 +739,10 @@ QPushButton { QPushButton:hover { background-color: #722548; } + +QPushButton:pressed { + background-color:rgb(79, 24, 49); +} QPushButton#switch_theme_button_ { width: 20px; height: 20px; @@ -815,6 +878,18 @@ QScrollArea { font-size: 13px; } +#BottomBar QPushButton { + color: #BDD1BD; + font-family: 'Arial'; + font-size: 13px; +} + +#BottomBar QPushButton:hover { + color:rgb(238, 242, 238); + font-family: 'Arial'; + font-size: 13px; +} + #NoteList { border-radius: 8px; background-color: #07142B; diff --git a/ui/main-window/include/mainwindow.h b/ui/main-window/include/mainwindow.h index 6268aa9..d02ae82 100644 --- a/ui/main-window/include/mainwindow.h +++ b/ui/main-window/include/mainwindow.h @@ -13,6 +13,11 @@ #include "projectlist.h" #include "storage.hpp" #include +#include "profile_window.h" + +namespace Ui { + class MainWindow; +} namespace Ui { class MainWindow : public QWidget { @@ -26,14 +31,16 @@ class MainWindow : public QWidget { QWidget *content_widget_; QPushButton *new_project_button_; QPushButton *new_note_button_; - QPushButton *switch_theme_button_; project_storage_model::Storage *storage_; friend ProjectList; private slots: void add_project(); void add_note(); - void on_switch_theme_click(); + void on_profile_button_click(); +signals: + void logout_requested(); + void delete_account_requested(); public: explicit MainWindow( @@ -42,6 +49,8 @@ private slots: project_storage_model::Storage *storage = nullptr ); static const std::vector THEMES; + void on_logout_button_click(); + void on_delete_account_button_click(); void handle_theme_changed(int theme); }; } // namespace Ui diff --git a/ui/main-window/src/bottombar.cpp b/ui/main-window/src/bottombar.cpp index ee63c71..0e92c8a 100644 --- a/ui/main-window/src/bottombar.cpp +++ b/ui/main-window/src/bottombar.cpp @@ -1,8 +1,7 @@ #include "bottombar.h" #include #include -#include -#include +#include namespace Ui { BottomBar::BottomBar( @@ -12,20 +11,23 @@ BottomBar::BottomBar( ) : QWidget(parent), main_layout_(new QHBoxLayout()), - username_(new QLabel(username.c_str())), - project_name_(new QLabel(project_name.c_str())) { + project_name_(new QLabel(project_name.c_str())), + profile_button_(new QPushButton(username.c_str())) +{ this->setObjectName("BottomBar"); this->setLayout(main_layout_); this->setFixedHeight(40); - project_name_->setAlignment(Qt::AlignLeft | Qt::AlignVCenter); - username_->setAlignment(Qt::AlignVCenter | Qt::AlignRight); - - this->setSizePolicy( - QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Maximum) - ); + profile_button_->setObjectName("profile_button"); + profile_button_->setStyleSheet("background-color: transparent; text-align: right;"); + project_name_->setAlignment(Qt::AlignLeft | Qt::AlignVCenter); + main_layout_->addWidget(project_name_); - main_layout_->addWidget(username_); + main_layout_->addStretch(); + main_layout_->addWidget(profile_button_); + + connect(profile_button_, &QPushButton::clicked, + this, &BottomBar::profile_button_clicked); } } // namespace Ui \ No newline at end of file diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index ab64112..5bcf480 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -4,11 +4,15 @@ #include #include #include +#include +#include #include #include #include #include #include +#include +#include "applicationwindow.h" #include "bottombar.h" #include "lr_dao.hpp" #include "main_window_style.hpp" @@ -19,6 +23,8 @@ #include "projectitem.h" #include "projectlist.h" #include "theme_manager.h" +#include "registration_window.h" +#include "login_window.h" namespace Ui { @@ -44,13 +50,10 @@ MainWindow::MainWindow( note_list_(new NoteList(this)), content_widget_(new QWidget(this)), new_project_button_(new QPushButton("Новый проект", this)), - switch_theme_button_(new QPushButton(this)), new_note_button_(new QPushButton("Новая заметка", this)), storage_(storage) { this->setObjectName("main-window"); this->setAttribute(Qt::WA_StyledBackground); - this->setMinimumSize(QSize(800, 600)); - main_layout_->addWidget(top_bar_, Qt::AlignTop); main_layout_->setAlignment(Qt::AlignCenter); main_layout_->addWidget(content_widget_); @@ -66,10 +69,6 @@ MainWindow::MainWindow( content_layout_->addLayout(right_layout); main_layout_->addWidget(content_widget_); this->setLayout(main_layout_); - - switch_theme_button_->setObjectName("switch_theme_button_"); - right_layout->addWidget(switch_theme_button_, 0, Qt::AlignRight | Qt::AlignBottom); - handle_theme_changed(ThemeManager::instance()->current_theme()); this->project_list_->load_projects(storage); connect( @@ -79,25 +78,52 @@ MainWindow::MainWindow( connect( new_note_button_, &QPushButton::clicked, this, &Ui::MainWindow::add_note ); - connect( - switch_theme_button_, &QPushButton::clicked, this, - &Ui::MainWindow::on_switch_theme_click - ); connect( new_project_button_, &QPushButton::clicked, this, &Ui::MainWindow::add_project ); - connect(ThemeManager::instance(), &ThemeManager::theme_changed, - this, &MainWindow::handle_theme_changed); + connect( + top_bar_, &Ui::BottomBar::profile_button_clicked, + this, &MainWindow::on_profile_button_click + ); + connect( + ThemeManager::instance(), &ThemeManager::theme_changed, + this, &MainWindow::handle_theme_changed + ); + handle_theme_changed(ThemeManager::instance()->current_theme()); +} + +void MainWindow::on_delete_account_button_click() { + this->deleteLater(); + emit delete_account_requested(); +} + +void MainWindow::on_logout_button_click() { + this->deleteLater(); + emit logout_requested(); } void MainWindow::handle_theme_changed(int theme) { this->setStyleSheet(THEMES[theme]); } -void MainWindow::on_switch_theme_click() { - int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; - ThemeManager::instance()->apply_theme(next_theme); +void MainWindow::on_profile_button_click() { + this->setEnabled(false); + ProfileWindow *new_profile_window = new ProfileWindow(QString::fromStdString(this->username), this->parentWidget()); + new_profile_window->setAttribute(Qt::WA_DeleteOnClose); + connect( + new_profile_window, &ProfileWindow::logout_requested, + this, &MainWindow::on_logout_button_click + ); + connect( + new_profile_window, &ProfileWindow::delete_account_requested, + this, &MainWindow::on_delete_account_button_click + ); + connect(new_profile_window, &ProfileWindow::destroyed, + this, [this]() { this->setEnabled(true); }); + new_profile_window->show(); + new_profile_window->raise(); + new_profile_window->activateWindow(); } void MainWindow::add_project() { diff --git a/ui/profile-window/CMakeLists.txt b/ui/profile-window/CMakeLists.txt new file mode 100644 index 0000000..533cead --- /dev/null +++ b/ui/profile-window/CMakeLists.txt @@ -0,0 +1,40 @@ +cmake_minimum_required(VERSION 3.16) + +project(ProfileWindow LANGUAGES CXX) + +set(CMAKE_CXX_STANDARD 20) +set(CMAKE_CXX_STANDARD_REQUIRED ON) + +find_package(Qt6 COMPONENTS Widgets Core Gui Sql REQUIRED) + +set(CMAKE_AUTOMOC ON) +set(CMAKE_AUTOUIC ON) +set(CMAKE_AUTORCC ON) + +set(SOURCES + src/profile_window.cpp +) + +set(HEADERS + include/profile_window.h + include/profile_window_style_sheet.h +) + +add_library(ProfileWindow STATIC ${SOURCES} ${HEADERS} ${UI_FILES}) + +target_include_directories(ProfileWindow + PUBLIC + $ + $ +) + +target_link_libraries(ProfileWindow PRIVATE + Qt6::Widgets + Qt6::Core + Qt6::Gui + Qt6::Sql + Database + ThemeManager + AuthorizationWindows + SettingsWindow +) \ No newline at end of file diff --git a/ui/profile-window/include/profile_window.h b/ui/profile-window/include/profile_window.h new file mode 100644 index 0000000..7f34b89 --- /dev/null +++ b/ui/profile-window/include/profile_window.h @@ -0,0 +1,46 @@ +#pragma once + +#include +#include +#include +#include +#include +#include "theme_manager.h" +#include + +QT_BEGIN_NAMESPACE +namespace Ui { + +class ProfileWindow : public QDialog { + Q_OBJECT + + QVBoxLayout* main_layout; + QPushButton* logout_button; + QPushButton* delete_button; + QPushButton* stats_button; + QPushButton* settings_button; + QString current_username; + + void setup_ui(QDialog* profile_window); + +public: + explicit ProfileWindow(const QString& username, QWidget* parent = nullptr); + ~ProfileWindow() = default; + + static const std::vector themes; + void handle_theme_changed(int theme); + friend class MainWindow; + +signals: + void logout_requested(); + void delete_account_requested(); + +private slots: + void on_logout_clicked(); + void on_delete_account_clicked(); + void on_stats_clicked(); + void on_settings_clicked(); +}; + +} // namespace Ui +QT_END_NAMESPACE \ No newline at end of file diff --git a/ui/profile-window/include/profile_window_style_sheet.h b/ui/profile-window/include/profile_window_style_sheet.h new file mode 100644 index 0000000..8796abc --- /dev/null +++ b/ui/profile-window/include/profile_window_style_sheet.h @@ -0,0 +1,393 @@ +#ifndef PROFILE_WINDOW_STYLE_HPP +#define PROFILE_WINDOW_STYLE_HPP + +#include + +namespace Ui { + +QString profile_window_light_autumn_theme = R"( + QDialog { + background-color: #f5f5f5; + } + + QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + padding: 5px 10px; + width: 60px; + height: 25px; + } + + QPushButton#logout_button { + background-color: #fea36b; + color: white; + } + + QPushButton#logout_button:hover { + background-color:rgb(245, 148, 89); + } + + QPushButton#logout_button:pressed { + background-color:rgb(238, 122, 50); + } + + QPushButton#delete_button { + background-color: #fea36b; + color: white; + } + + QPushButton#delete_button:hover { + background-color:rgb(245, 148, 89); + } + + QPushButton#delete_button:pressed { + background-color:rgb(238, 122, 50); + } + + QPushButton#stats_button { + background-color: #089083; + color: #f5f5f5; + border: none; + padding: 10px; + margin: 2px; + } + + QPushButton#stats_button:hover { + background-color:rgb(8, 82, 74); + } + + QPushButton#stats_button:pressed { + background-color: #089083; + } + + QPushButton#settings_button { + background-color: rgb(33, 44, 50); + color: #f5f5f5; + padding: 2px; + font-size: 35px; + border-radius: 15px; + width: 30px; + height: 30px; + } + + QPushButton#settings_button:hover { + background-color: rgb(14, 17, 19); + } + + QPushButton#settings_button:pressed { + background-color: rgb(4, 4, 5); + } +)"; + +QString profile_window_dark_autumn_theme = R"( + QDialog { + background-color:rgb(43, 43, 43); + } + + QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + padding: 5px 10px; + width: 60px; + height: 25px; + } + + QPushButton#logout_button { + background-color:rgb(211, 139, 95); + color: #263238; + } + + QPushButton#logout_button:hover { + background-color:rgb(181, 114, 59); + } + + QPushButton#logout_button:pressed { + background-color:rgb(158, 94, 45); + } + + QPushButton#delete_button { + background-color:rgb(211, 139, 95); + color: #263238; + } + + QPushButton#delete_button:hover { + background-color:rgb(181, 114, 59); + } + + QPushButton#delete_button:pressed { + background-color:rgb(158, 94, 45); + } + + QPushButton#stats_button { + background-color: #089083; + color: #f5f5f5; + border: none; + padding: 10px; + margin: 2px; + } + + QPushButton#stats_button:hover { + background-color:rgb(12, 114, 104); + } + + QPushButton#stats_button:pressed { + background-color:rgb(14, 101, 92); + } + + QPushButton#settings_button { + background-color:rgb(0, 0, 0); + color: #f5f5f5; + padding: 2px; + font-size: 35px; + border-radius: 15px; + width: 30px; + height: 30px; + } + + QPushButton#settings_button:hover { + background-color:rgb(54, 54, 54); + } + + QPushButton#settings_button:pressed { + background-color: rgb(99, 99, 99); + } +)"; + +QString profile_window_light_purple_theme = R"( + QDialog { + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, + stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(103, 88, 126)); + } + + QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + padding: 5px 10px; + width: 60px; + height: 25px; + } + + QPushButton#logout_button { + background-color: #722548; + color: #9882B9; + } + + QPushButton#logout_button:hover { + background-color:rgb(82, 27, 51); + } + + QPushButton#logout_button:pressed { + background-color:rgb(64, 21, 40); + } + + QPushButton#delete_button { + background-color: #722548; + color: #9882B9; + } + + QPushButton#delete_button:hover { + background-color:rgb(84, 27, 53); + } + + QPushButton#delete_button:pressed { + background-color:rgb(64, 21, 40); + } + + QPushButton#stats_button { + background-color: rgb(42, 10, 25); + color: rgb(163, 148, 184); + border: none; + padding: 10px; + margin: 2px; + } + + QPushButton#stats_button:hover { + background-color: rgb(19, 5, 11); + } + + QPushButton#stats_button:pressed { + background-color:rgb(42, 10, 25); + } + + QPushButton#settings_button { + background-color: rgb(221, 210, 238); + color: rgb(42, 10, 25); + padding: 2px; + font-size: 35px; + border-radius: 15px; + width: 30px; + height: 30px; + } + + QPushButton#settings_button:hover { + background-color: rgb(177, 166, 194); + } + + QPushButton#settings_button:pressed { + background-color: rgb(152, 140, 170); + } +)"; + +QString profile_window_dark_purple_theme = R"( + QDialog { + background-color: rgb(9, 6, 10); + } + + QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + padding: 5px 10px; + width: 60px; + height: 25px; + } + + QPushButton#logout_button { + background-color: #722548; + color: #060407; + } + + QPushButton#logout_button:hover { + background-color: #722548; + } + + QPushButton#logout_button:pressed { + background-color:rgb(79, 24, 49); + } + + QPushButton#delete_button { + background-color: #722548; + color: #060407; + } + + QPushButton#delete_button:hover { + background-color: #722548; + } + + QPushButton#delete_button:pressed { + background-color:rgb(79, 24, 49); + } + + QPushButton#stats_button { + background-color: rgb(42, 10, 25); + color: #9882B9; + border: none; + padding: 10px; + margin: 2px; + } + + QPushButton#stats_button:hover { + background-color:rgb(22, 5, 13); + } + + QPushButton#stats_button:pressed { + background-color:rgb(11, 3, 7); + } + + QPushButton#settings_button { + background-color: #221932; + color: #9882B9; + padding: 2px; + font-size: 35px; + border-radius: 15px; + width: 30px; + height: 30px; + } + + QPushButton#settings_button:hover { + background-color:rgb(21, 16, 31); + } + + QPushButton#settings_button:pressed { + background-color:rgb(4, 3, 5); + } +)"; + +QString profile_window_blue_theme = R"( + QDialog { + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, + stop:0 #173C4C, stop:0.5 #326D6C, stop:1 #07142B); + } + + QPushButton { + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + border-radius: 10px; + padding: 5px 10px; + width: 60px; + height: 25px; + border: none; + } + + QPushButton#logout_button { + background-color: #BDD1BD; + color: #173C4C; + } + + QPushButton#logout_button:hover { + background-color:rgb(158, 176, 158); + } + + QPushButton#logout_button:pressed { + background-color:rgb(141, 157, 141); + } + + QPushButton#delete_button { + background-color: #BDD1BD; + color: #173C4C; + } + + QPushButton#delete_button:hover { + background-color:rgb(158, 176, 158); + } + + QPushButton#delete_button:pressed { + background-color:rgb(141, 157, 141); + } + + QPushButton#stats_button { + background-color: #326D6C; + color: #BDD1BD; + border: none; + padding: 10px; + margin: 2px; + } + + QPushButton#stats_button:hover { + background-color:rgb(47, 89, 89); + } + + QPushButton#stats_button:pressed { + background-color:rgb(31, 69, 85); + } + + QPushButton#settings_button { + background-color: #07142B; + color: #BDD1BD; + padding: 2px; + font-size: 35px; + border-radius: 15px; + width: 30px; + height: 30px; + } + + QPushButton#settings_button:hover { + background-color:rgb(4, 12, 26); + } + + QPushButton#settings_button:pressed { + background-color:rgb(2, 3, 5); + } +)"; + +} // namespace Ui + +#endif // PROFILE_WINDOW_STYLE_HPP \ No newline at end of file diff --git a/ui/profile-window/src/profile_window.cpp b/ui/profile-window/src/profile_window.cpp new file mode 100644 index 0000000..21f4790 --- /dev/null +++ b/ui/profile-window/src/profile_window.cpp @@ -0,0 +1,110 @@ +#include "profile_window.h" +#include "profile_window_style_sheet.h" +#include +#include "database_manager.hpp" +#include "lr_dao.hpp" +#include "settings_window.h" + +namespace Ui { + +const std::vector ProfileWindow::themes = { + profile_window_light_autumn_theme, + profile_window_dark_autumn_theme, + profile_window_dark_purple_theme, + profile_window_light_purple_theme, + profile_window_blue_theme +}; + +void ProfileWindow::setup_ui(QDialog* profile_window) { + main_layout = new QVBoxLayout(profile_window); + + logout_button = new QPushButton("Выйти из аккаунта", profile_window); + logout_button->setObjectName("logout_button"); + main_layout->addWidget(logout_button); + + delete_button = new QPushButton("Удалить аккаунт", profile_window); + delete_button->setObjectName("delete_button"); + main_layout->addWidget(delete_button); + + QHBoxLayout* bottom_layout = new QHBoxLayout(); + + stats_button = new QPushButton("Моя статистика", profile_window); + stats_button->setObjectName("stats_button"); + bottom_layout->addWidget(stats_button); + + settings_button = new QPushButton("⚙", profile_window); + settings_button->setObjectName("settings_button"); + settings_button->setFixedSize(45, 45); + bottom_layout->addWidget(settings_button); + + main_layout->addLayout(bottom_layout); +} + +ProfileWindow::ProfileWindow(const QString& username, QWidget* parent) + : QDialog(parent), current_username(username) { + setup_ui(this); + setFixedSize(250, 160); + + connect( + logout_button, &QPushButton::clicked, + this, &Ui::ProfileWindow::on_logout_clicked + ); + connect( + delete_button, &QPushButton::clicked, + this, &Ui::ProfileWindow::on_delete_account_clicked + ); + connect( + stats_button, &QPushButton::clicked, + this, &Ui::ProfileWindow::on_stats_clicked + ); + connect(settings_button, &QPushButton::clicked, + this, &Ui::ProfileWindow::on_settings_clicked + ); + connect(ThemeManager::instance(), &ThemeManager::theme_changed, + this, &Ui::ProfileWindow::handle_theme_changed + ); + handle_theme_changed(ThemeManager::instance()->current_theme()); +} + +void ProfileWindow::handle_theme_changed(int theme) { + setStyleSheet(themes[theme]); +} + +void ProfileWindow::on_logout_clicked() { + emit logout_requested(); + this->deleteLater(); +} + +void ProfileWindow::on_delete_account_clicked() { + QMessageBox::StandardButton reply = QMessageBox::question( + this, + "Удаление аккаунта", + "Вы уверены, что хотите удалить аккаунт? Все данные будут потеряны!", + QMessageBox::Yes | QMessageBox::No + ); + + if (reply == QMessageBox::Yes && LRDao::try_delete_user(current_username)) { + QMessageBox::information(this, "Успех", "Аккаунт успешно удалён"); + emit delete_account_requested(); + this->deleteLater(); + } else if (reply == QMessageBox::Yes) { + QMessageBox::critical(this, "Ошибка", "Не удалось удалить аккаунт"); + } +} + +void ProfileWindow::on_stats_clicked() { + QMessageBox::information(this, "Статистика", "Статистика в разработке 🛠"); +} + +void ProfileWindow::on_settings_clicked() { + this->setEnabled(false); + SettingsWindow *new_settings_window = new SettingsWindow(this->parentWidget()); + new_settings_window->setAttribute(Qt::WA_DeleteOnClose); + connect(new_settings_window, &SettingsWindow::destroyed, + this, [this]() { this->setEnabled(true); }); + new_settings_window->show(); + new_settings_window->raise(); + new_settings_window->activateWindow(); +} + +} // namespace Ui \ No newline at end of file diff --git a/ui/settings-window/CMakeLists.txt b/ui/settings-window/CMakeLists.txt new file mode 100644 index 0000000..bac1da2 --- /dev/null +++ b/ui/settings-window/CMakeLists.txt @@ -0,0 +1,39 @@ +cmake_minimum_required(VERSION 3.16) + +project(SettingsWindow LANGUAGES CXX) + +set(CMAKE_CXX_STANDARD 20) +set(CMAKE_CXX_STANDARD_REQUIRED ON) + +find_package(Qt6 COMPONENTS Widgets Core Gui Sql REQUIRED) + +set(CMAKE_AUTOMOC ON) +set(CMAKE_AUTOUIC ON) +set(CMAKE_AUTORCC ON) + +set(SOURCES + src/settings_window.cpp +) + +set(HEADERS + include/settings_window.h + include/settings_window_style_sheet.h +) + +add_library(SettingsWindow STATIC ${SOURCES} ${HEADERS} ${UI_FILES}) + +target_include_directories(SettingsWindow + PUBLIC + $ + $ +) + +target_link_libraries(SettingsWindow PRIVATE + Qt6::Widgets + Qt6::Core + Qt6::Gui + Qt6::Sql + Database + ThemeManager + AuthorizationWindows +) \ No newline at end of file diff --git a/ui/settings-window/include/settings_window.h b/ui/settings-window/include/settings_window.h new file mode 100644 index 0000000..ca6cb91 --- /dev/null +++ b/ui/settings-window/include/settings_window.h @@ -0,0 +1,41 @@ +#ifndef SETTINGS_WINDOW_H +#define SETTINGS_WINDOW_H + +#include +#include +#include +#include +#include +#include +#include +#include + +class SettingsWindow : public QWidget { + Q_OBJECT + +public: + explicit SettingsWindow(QWidget *parent = nullptr); + void handle_theme_changed(int theme); + static const std::vector THEMES; + +private slots: + void toggle_language(); + void toggle_theme(); + void set_small_font(); + void set_medium_font(); + void set_large_font(); + +private: + void update_ui_text(); + + QVBoxLayout* main_layout; + QPushButton *language_button; + QPushButton *theme_button; + QLabel *title_label; + QLabel *font_size_label; + QRadioButton *small_font_radio; + QRadioButton *medium_font_radio; + QRadioButton *large_font_radio; +}; + +#endif // SETTINGS_WINDOW_H \ No newline at end of file diff --git a/ui/settings-window/include/settings_window_style_sheet.h b/ui/settings-window/include/settings_window_style_sheet.h new file mode 100644 index 0000000..961fe3d --- /dev/null +++ b/ui/settings-window/include/settings_window_style_sheet.h @@ -0,0 +1,99 @@ +#pragma once + +#include + +namespace Ui { + QString settings_window_light_autumn_theme = R"( + QWidget { + background-color: white; + } + + QLabel { + font-weight: bold; + font-family: 'Arial'; + color: #089083; + background-color: transparent; + } + + QLabel#font_size_label { + font-size: 30px; + } + + QLabel#title_label { + font-size: 20px; + } + + QPushButton#language_button { + background-color: rgb(33, 44, 50); + color: #f5f5f5; + padding: 2px; + font-size: 20px; + border-radius: 7px; + width: 40px; + height: 30px; + } + + QPushButton#language_button:hover { + background-color: rgb(14, 17, 19); + } + QPushButton#language_button:pressed { + background-color: rgb(4, 4, 5); + } + + QPushButton#theme_button { + width: 40px; + height: 30px; + color: #089083; + font-size: 15px; + border-radius: 7px; + padding: 0; + margin-bottom: 2px; + background-color: transparent; + border: 2px solid #089083; + } + QPushButton#theme_button:hover { + background-color: #089083; + color: white; + } + + QPushButton::pressed#switch_theme { + background-color:rgb(7, 110, 100); + color: white; + } + + QRadioButton { + font-family: 'Arial'; + color: #727272; + spacing: 5px; + background-color: transparent; + } + QRadioButton::indicator { + width: 16px; + height: 16px; + border-radius: 3px; + border: 1px solid #727272; + background-color: #ffffff; + } + QRadioButton::indicator:hover { + border: 1px solid #fea36b; + } + QRadioButton::indicator:checked { + background-color: #fea36b; + border: 1px solid #fea36b; + } + )"; + + QString settings_window_dark_autumn_theme = R"( + + )"; + QString settings_window_dark_purple_theme = R"( + + )"; + QString settings_window_light_purple_theme = R"( + + )"; + QString settings_window_blue_theme = R"( + + )"; + +} // namespace Ui \ No newline at end of file diff --git a/ui/settings-window/src/settings_window.cpp b/ui/settings-window/src/settings_window.cpp new file mode 100644 index 0000000..c8651a3 --- /dev/null +++ b/ui/settings-window/src/settings_window.cpp @@ -0,0 +1,87 @@ +#include "settings_window.h" +#include "settings_window_style_sheet.h" +#include "theme_manager.h" + +const std::vector SettingsWindow::THEMES = { + Ui::settings_window_light_autumn_theme, + Ui::settings_window_dark_autumn_theme, + Ui::settings_window_dark_purple_theme, + Ui::settings_window_light_purple_theme, + Ui::settings_window_blue_theme +}; + +SettingsWindow::SettingsWindow(QWidget *parent) : QWidget(parent) { + main_layout = new QVBoxLayout(this); + + title_label = new QLabel("Настройки", this); + title_label->setObjectName("title_label"); + title_label->setAlignment(Qt::AlignCenter); + main_layout->addWidget(title_label); + + QHBoxLayout *buttons_layout = new QHBoxLayout(); + + language_button = new QPushButton("RU", this); + language_button->setObjectName("language_button"); + + theme_button = new QPushButton("Тема", this); + theme_button->setObjectName("theme_button"); + + buttons_layout->addWidget(language_button); + buttons_layout->addWidget(theme_button); + main_layout->addLayout(buttons_layout); + + font_size_label = new QLabel("Размер шрифта", this); + main_layout->addWidget(font_size_label); + + QButtonGroup *font_group = new QButtonGroup(this); + small_font_radio = new QRadioButton("Мелкий", this); + medium_font_radio = new QRadioButton("Средний", this); + large_font_radio = new QRadioButton("Крупный", this); + + font_group->addButton(small_font_radio); + font_group->addButton(medium_font_radio); + font_group->addButton(large_font_radio); + medium_font_radio->setChecked(true); + + QVBoxLayout *font_layout = new QVBoxLayout(); + font_layout->addWidget(small_font_radio); + font_layout->addWidget(medium_font_radio); + font_layout->addWidget(large_font_radio); + main_layout->addLayout(font_layout); + + connect(language_button, &QPushButton::clicked, this, &SettingsWindow::toggle_language); + connect(theme_button, &QPushButton::clicked, this, &SettingsWindow::toggle_theme); + connect(small_font_radio, &QRadioButton::clicked, this, &SettingsWindow::set_small_font); + connect(medium_font_radio, &QRadioButton::clicked, this, &SettingsWindow::set_medium_font); + connect(large_font_radio, &QRadioButton::clicked, this, &SettingsWindow::set_large_font); + connect(ThemeManager::instance(), &ThemeManager::theme_changed, + this, &SettingsWindow::handle_theme_changed); + + title_label->setText("Настройки"); + font_size_label->setText("Размер шрифта"); + theme_button->setText("Тема"); + small_font_radio->setText("Мелкий"); + medium_font_radio->setText("Средний"); + large_font_radio->setText("Крупный"); + + setLayout(main_layout); + setFixedSize(140, 250); + handle_theme_changed(ThemeManager::instance()->current_theme()); +} + +void SettingsWindow::handle_theme_changed(int theme) { + this->setStyleSheet(THEMES[theme]); +} + +void SettingsWindow::toggle_language() { + +} + +void SettingsWindow::toggle_theme() { + int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; + ThemeManager::instance()->apply_theme(next_theme); +} + +void SettingsWindow::set_small_font() { qApp->setStyleSheet("QWidget { font-size: 12px; }"); } +void SettingsWindow::set_medium_font() { qApp->setStyleSheet("QWidget { font-size: 16px; }"); } +void SettingsWindow::set_large_font() { qApp->setStyleSheet("QWidget { font-size: 20px; }"); } \ No newline at end of file From 8f2ec58e9a5ca6aff9cd5d809b9cee06c1a15cb7 Mon Sep 17 00:00:00 2001 From: MuravAna Date: Mon, 12 May 2025 15:11:00 +0300 Subject: [PATCH 09/17] Add part-realization of analytics window --- CMakeLists.txt | 2 + ui/analytics-window/CMakeLists.txt | 39 ++ .../include/analytics_window.h | 31 ++ .../include/analytics_window_style_sheet.h | 0 ui/analytics-window/src/analytics_window.cpp | 121 +++++++ ui/authorization-windows/src/login_window.cpp | 61 ++-- ui/main-window/include/main_window_style.hpp | 4 +- ui/profile-window/CMakeLists.txt | 1 + .../include/profile_window_style_sheet.h | 10 +- ui/profile-window/src/profile_window.cpp | 30 +- ui/settings-window/include/settings_window.h | 4 +- .../include/settings_window_style_sheet.h | 339 ++++++++++++++++-- ui/settings-window/src/settings_window.cpp | 4 +- 13 files changed, 568 insertions(+), 78 deletions(-) create mode 100644 ui/analytics-window/CMakeLists.txt create mode 100644 ui/analytics-window/include/analytics_window.h create mode 100644 ui/analytics-window/include/analytics_window_style_sheet.h create mode 100644 ui/analytics-window/src/analytics_window.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index fdd1382..8ccf76e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -19,6 +19,7 @@ add_subdirectory(ui/authorization-windows) add_subdirectory(ui/note-widget) add_subdirectory(ui/theme-manager) add_subdirectory(ui/settings-window) +add_subdirectory(ui/analytics-window) add_subdirectory(proto) add_executable(EfficioTaskTracker main.cpp) @@ -37,4 +38,5 @@ target_link_libraries(EfficioTaskTracker PRIVATE MainWindow NoteWidget SettingsWindow + AnalyticsWindow ) \ No newline at end of file diff --git a/ui/analytics-window/CMakeLists.txt b/ui/analytics-window/CMakeLists.txt new file mode 100644 index 0000000..1e40142 --- /dev/null +++ b/ui/analytics-window/CMakeLists.txt @@ -0,0 +1,39 @@ +cmake_minimum_required(VERSION 3.16) + +project(AnalyticsWindow LANGUAGES CXX) + +set(CMAKE_CXX_STANDARD 20) +set(CMAKE_CXX_STANDARD_REQUIRED ON) + +find_package(Qt6 COMPONENTS Widgets Core Gui Sql Charts REQUIRED) + +set(CMAKE_AUTOMOC ON) +set(CMAKE_AUTOUIC ON) +set(CMAKE_AUTORCC ON) + +set(SOURCES + src/analytics_window.cpp +) + +set(HEADERS + include/analytics_window.h + include/analytics_window_style_sheet.h +) + +add_library(AnalyticsWindow STATIC ${SOURCES} ${HEADERS}) + +target_include_directories(AnalyticsWindow + PUBLIC + $ + $ +) + +target_link_libraries(AnalyticsWindow PRIVATE + Qt6::Widgets + Qt6::Core + Qt6::Gui + Qt6::Sql + Qt6::Charts + Database + ThemeManager +) \ No newline at end of file diff --git a/ui/analytics-window/include/analytics_window.h b/ui/analytics-window/include/analytics_window.h new file mode 100644 index 0000000..f93d900 --- /dev/null +++ b/ui/analytics-window/include/analytics_window.h @@ -0,0 +1,31 @@ +#ifndef ANALYTICS_DIALOG_H +#define ANALYTICS_DIALOG_H + +#include +#include +#include +#include +#include + +class AnalyticsWindow : public QDialog +{ + Q_OBJECT + +public: + explicit AnalyticsWindow(QWidget *parent = nullptr); + ~AnalyticsWindow(); + + void setTasksData(int created, int completed, int overdue); + void setProjectsData(const QMap& projects); + +private: + QTabWidget *tab_widget; + QVBoxLayout *tasks_layout; + QVBoxLayout *projects_layout; + QDialogButtonBox *button_box; + + QChart *createTasksChart(int created, int completed, int overdue); + QChart *createProjectsChart(const QMap& projects); +}; + +#endif // ANALYTICS_DIALOG_H \ No newline at end of file diff --git a/ui/analytics-window/include/analytics_window_style_sheet.h b/ui/analytics-window/include/analytics_window_style_sheet.h new file mode 100644 index 0000000..e69de29 diff --git a/ui/analytics-window/src/analytics_window.cpp b/ui/analytics-window/src/analytics_window.cpp new file mode 100644 index 0000000..11f3a82 --- /dev/null +++ b/ui/analytics-window/src/analytics_window.cpp @@ -0,0 +1,121 @@ +#include "analytics_dialog.h" + +AnalyticsWindow::AnalyticsWindow(QWidget *parent) + : QDialog(parent) +{ + QVBoxLayout *main_layout = new QVBoxLayout(this); + + tab_widget = new Qtab_widget(this); + + QWidget *tasks_tab = new QWidget(); + tasks_layout = new QVBoxLayout(tasks_tab); + tab_widget->addTab(tasks_tab, "Статистика задач"); + + QWidget *projects_tab = new QWidget(); + projects_layout = new QVBoxLayout(projects_tab); + tab_widget->addTab(projects_tab, "Распределение по проектам"); + + button_box = new QDialogbutton_box(QDialogbutton_box::Close, this); + connect(button_box, &QDialogbutton_box::rejected, this, &QDialog::reject); + + main_layout->addWidget(tab_widget); + main_layout->addWidget(button_box); + + setWindowTitle("Аналитическая панель"); + resize(800, 600); + + setTasksData(0, 0, 0); + + QMap projects; + setProjectsData(projects); +} + +AnalyticsWindow::~AnalyticsWindow() +{ + delete this; +} + +void AnalyticsWindow::setTasksData(int created, int completed, int overdue) +{ + QLayoutItem *child; + while (child = tasks_layout->takeAt(0)) { + delete child->widget(); + delete child; + } + + QChart *chart = createTasksChart(created, completed, overdue); + tasks_layout->addWidget(new QChartView(chart)); +} + +void AnalyticsWindow::setProjectsData(const QMap& projects) +{ + QLayoutItem *child; + while (child = projects_layout->takeAt(0)) { + delete child->widget(); + delete child; + } + + QChart *chart = createProjectsChart(projects); + projects_layout->addWidget(new QChartView(chart)); +} + +QChart* AnalyticsWindow::createTasksChart(int created, int completed, int overdue) +{ + QBarSet *created_set = new QBarSet("Создано"); + *created_set << created; + + QBarSet *completed_set = new QBarSet("Завершено"); + *completed_set << completed; + + QBarSet *overdue_set = new QBarSet("Просрочено"); + *overdue_set << overdue; + + QBarSeries *series = new QBarSeries(); + series->append(created_set); + series->append(completed_set); + series->append(overdue_set); + + QChart *chart = new QChart(); + chart->addSeries(series); + chart->setTitle("Статистика задач за период"); + chart->setAnimationOptions(QChart::SeriesAnimations); + + QBarCategoryAxis *axisX = new QBarCategoryAxis(); + axisX->append("Тип задач"); + chart->addAxis(axisX, Qt::AlignBottom); + series->attachAxis(axisX); + + QValueAxis *axisY = new QValueAxis(); + int maxValue = qMax(created, qMax(completed, overdue)); + axisY->setRange(0, maxValue + (maxValue * 0.1)); // +10% отмакс. значения + axisY->setTitleText("Количество"); + chart->addAxis(axisY, Qt::AlignLeft); + series->attachAxis(axisY); + + return chart; +} + +QChart* AnalyticsWindow::createProjectsChart(const QMap& projects) +{ + QPieSeries *series = new QPieSeries(); + + int total = 0; + for (auto it = projects.begin(); it != projects.end(); ++it) { + series->append(it.key(), it.value()); + total += it.value(); + } + + series->setLabelsVisible(); + foreach(QPieSlice *slice, series->slices()) { + slice->setLabel(QString("%1 (%2%)") + .arg(slice->label()) + .arg(100 * slice->percentage(), 0, 'f', 1)); + } + + QChart *chart = new QChart(); + chart->addSeries(series); + chart->setTitle(QString("Распределение задач (%1 всего)").arg(total)); + chart->legend()->setAlignment(Qt::AlignRight); + + return chart; +} \ No newline at end of file diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index 485a134..7a0d220 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -89,29 +89,30 @@ void LoginWindow::on_switch_mode_clicked() { } void LoginWindow::on_push_enter_clicked() { - if ((this->counter_on_switch_theme_clicks++)%2){ - QString login = ui->input_login->text(); - QString password = ui->input_password->text(); - - if (!login.isEmpty() && !password.isEmpty()) { - if (login.size() > 50) { - QMessageBox::warning( - this, "Ошибка", - "Длина логина не должна превышать пятидесяти символов" - ); - } else if (password.size() > 50) { - QMessageBox::warning( - this, "Ошибка", - "Длина пароля не должна превышать пятидесяти символов" - ); - } else if (LRDao::validate_user(login, password)) { - QMessageBox::information( - this, "Вход", "Вы успешно вошли! Добро пожаловать :)" - ); + // if ((this->counter_on_switch_theme_clicks++)%2){ + // QString login = ui->input_login->text(); + // QString password = ui->input_password->text(); + + // if (!login.isEmpty() && !password.isEmpty()) { + // if (login.size() > 50) { + // QMessageBox::warning( + // this, "Ошибка", + // "Длина логина не должна превышать пятидесяти символов" + // ); + // } else if (password.size() > 50) { + // QMessageBox::warning( + // this, "Ошибка", + // "Длина пароля не должна превышать пятидесяти символов" + // ); + // } else if (LRDao::validate_user(login, password)) { + // QMessageBox::information( + // this, "Вход", "Вы успешно вошли! Добро пожаловать :)" + // ); QMainWindow *app_window = qobject_cast(this->parentWidget()); this->deleteLater(); project_storage_model::Storage *storage = new project_storage_model::Storage(); + QString login = "user"; Serialization::get_storage(*storage, login.toStdString()); Ui::MainWindow *main_window = @@ -147,15 +148,15 @@ void LoginWindow::on_push_enter_clicked() { int y = (screenGeometry.height() - 600) / 2; app_window->move(x, y); app_window->show(); - } else { - QMessageBox::warning( - this, "Ошибка ввода данных", "Неверный логин или пароль!" - ); - } - } else { - QMessageBox::warning( - this, "Ошибка ввода данных", "Пожалуйста, заполните все поля!" - ); - } - } + // } else { + // QMessageBox::warning( + // this, "Ошибка ввода данных", "Неверный логин или пароль!" + // ); + // } + // } else { + // QMessageBox::warning( + // this, "Ошибка ввода данных", "Пожалуйста, заполните все поля!" + // ); + // } + // } } \ No newline at end of file diff --git a/ui/main-window/include/main_window_style.hpp b/ui/main-window/include/main_window_style.hpp index dd6dcb6..76ea0f0 100644 --- a/ui/main-window/include/main_window_style.hpp +++ b/ui/main-window/include/main_window_style.hpp @@ -737,11 +737,11 @@ QPushButton { } QPushButton:hover { - background-color: #722548; + background-color: rgb(79, 25, 50); } QPushButton:pressed { - background-color:rgb(79, 24, 49); + background-color:rgb(59, 16, 35); } QPushButton#switch_theme_button_ { width: 20px; diff --git a/ui/profile-window/CMakeLists.txt b/ui/profile-window/CMakeLists.txt index 533cead..b378586 100644 --- a/ui/profile-window/CMakeLists.txt +++ b/ui/profile-window/CMakeLists.txt @@ -37,4 +37,5 @@ target_link_libraries(ProfileWindow PRIVATE ThemeManager AuthorizationWindows SettingsWindow + AnalyticsWindow ) \ No newline at end of file diff --git a/ui/profile-window/include/profile_window_style_sheet.h b/ui/profile-window/include/profile_window_style_sheet.h index 8796abc..63aba3e 100644 --- a/ui/profile-window/include/profile_window_style_sheet.h +++ b/ui/profile-window/include/profile_window_style_sheet.h @@ -59,7 +59,7 @@ QString profile_window_light_autumn_theme = R"( } QPushButton#stats_button:pressed { - background-color: #089083; + background-color:rgb(3, 58, 54); } QPushButton#settings_button { @@ -255,11 +255,11 @@ QString profile_window_dark_purple_theme = R"( } QPushButton#logout_button:hover { - background-color: #722548; + background-color: rgb(79, 25, 50); } QPushButton#logout_button:pressed { - background-color:rgb(79, 24, 49); + background-color:rgb(59, 16, 35); } QPushButton#delete_button { @@ -268,11 +268,11 @@ QString profile_window_dark_purple_theme = R"( } QPushButton#delete_button:hover { - background-color: #722548; + background-color:rgb(79, 25, 50); } QPushButton#delete_button:pressed { - background-color:rgb(79, 24, 49); + background-color:rgb(59, 16, 35); } QPushButton#stats_button { diff --git a/ui/profile-window/src/profile_window.cpp b/ui/profile-window/src/profile_window.cpp index 21f4790..9f59435 100644 --- a/ui/profile-window/src/profile_window.cpp +++ b/ui/profile-window/src/profile_window.cpp @@ -4,6 +4,7 @@ #include "database_manager.hpp" #include "lr_dao.hpp" #include "settings_window.h" +#include "analytics_window.h" namespace Ui { @@ -15,34 +16,30 @@ const std::vector ProfileWindow::themes = { profile_window_blue_theme }; -void ProfileWindow::setup_ui(QDialog* profile_window) { - main_layout = new QVBoxLayout(profile_window); - - logout_button = new QPushButton("Выйти из аккаунта", profile_window); +ProfileWindow::ProfileWindow(const QString& username, QWidget* parent) + : QDialog(parent), current_username(username) { + main_layout = new QVBoxLayout(this); + + logout_button = new QPushButton("Выйти из аккаунта", this); logout_button->setObjectName("logout_button"); main_layout->addWidget(logout_button); - delete_button = new QPushButton("Удалить аккаунт", profile_window); + delete_button = new QPushButton("Удалить аккаунт", this); delete_button->setObjectName("delete_button"); main_layout->addWidget(delete_button); QHBoxLayout* bottom_layout = new QHBoxLayout(); - stats_button = new QPushButton("Моя статистика", profile_window); + stats_button = new QPushButton("Моя статистика", this); stats_button->setObjectName("stats_button"); bottom_layout->addWidget(stats_button); - settings_button = new QPushButton("⚙", profile_window); + settings_button = new QPushButton("⚙", this); settings_button->setObjectName("settings_button"); settings_button->setFixedSize(45, 45); bottom_layout->addWidget(settings_button); main_layout->addLayout(bottom_layout); -} - -ProfileWindow::ProfileWindow(const QString& username, QWidget* parent) - : QDialog(parent), current_username(username) { - setup_ui(this); setFixedSize(250, 160); connect( @@ -93,7 +90,14 @@ void ProfileWindow::on_delete_account_clicked() { } void ProfileWindow::on_stats_clicked() { - QMessageBox::information(this, "Статистика", "Статистика в разработке 🛠"); + this->setEnabled(false); + AnalyticsWindow *new_analytics_window = new AnalyticsWindow(this->parentWidget()); + new_analytics_window->setAttribute(Qt::WA_DeleteOnClose); + connect(new_analytics_window, &AnalyticsWindow::destroyed, + this, [this]() { this->setEnabled(true); }); + new_analytics_window->show(); + new_analytics_window->raise(); + new_analytics_window->activateWindow(); } void ProfileWindow::on_settings_clicked() { diff --git a/ui/settings-window/include/settings_window.h b/ui/settings-window/include/settings_window.h index ca6cb91..f06da7e 100644 --- a/ui/settings-window/include/settings_window.h +++ b/ui/settings-window/include/settings_window.h @@ -1,7 +1,7 @@ #ifndef SETTINGS_WINDOW_H #define SETTINGS_WINDOW_H -#include +#include #include #include #include @@ -10,7 +10,7 @@ #include #include -class SettingsWindow : public QWidget { +class SettingsWindow : public QDialog { Q_OBJECT public: diff --git a/ui/settings-window/include/settings_window_style_sheet.h b/ui/settings-window/include/settings_window_style_sheet.h index 961fe3d..55aacc5 100644 --- a/ui/settings-window/include/settings_window_style_sheet.h +++ b/ui/settings-window/include/settings_window_style_sheet.h @@ -14,51 +14,125 @@ namespace Ui { color: #089083; background-color: transparent; } + + QLabel#title_label { + font-size: 20px; + } QLabel#font_size_label { - font-size: 30px; + font-size: 35px; + } + + QPushButton#language_button { + background-color: #fea36b; + width: 50px; + height: 30px; + color: #f5f5f5; + padding: 2px; + font-size: 20px; + border-radius: 7px; + } + + QPushButton#language_button:hover { + background-color:rgb(245, 148, 89); + } + QPushButton#language_button:pressed { + background-color:rgb(238, 122, 50); + } + + QPushButton#theme_button { + background-color: #089083; + width: 50px; + height: 30px; + color: #f5f5f5; + padding: 2px; + font-size: 15px; + border-radius: 7px; + } + QPushButton#theme_button:hover { + background-color: rgb(8, 82, 74); + color: #f5f5f5; + } + + QPushButton::pressed#switch_theme { + background-color:rgb(3, 58, 54); + color: #f5f5f5; } + QRadioButton { + font-family: 'Arial'; + color: #727272; + spacing: 5px; + background-color: transparent; + } + QRadioButton::indicator { + width: 16px; + height: 16px; + border-radius: 3px; + border: 1px solid #727272; + background-color: transparent; + } + QRadioButton::indicator:hover { + border: 1px solid #fea36b; + } + QRadioButton::indicator:checked { + background-color: #fea36b; + border: 1px solid #fea36b; + } + )"; + + QString settings_window_dark_autumn_theme = R"( + QWidget { + background-color: #202020; + } + + QLabel { + font-weight: bold; + font-family: 'Arial'; + color: #089083; + background-color: transparent; + } + QLabel#title_label { font-size: 20px; } + QLabel#font_size_label { + font-size: 35px; + } + QPushButton#language_button { - background-color: rgb(33, 44, 50); - color: #f5f5f5; + background-color: #fea36b; + width: 50px; + height: 30px; + color: #263238; padding: 2px; font-size: 20px; border-radius: 7px; - width: 40px; - height: 30px; } QPushButton#language_button:hover { - background-color: rgb(14, 17, 19); + background-color: #d58745; } QPushButton#language_button:pressed { - background-color: rgb(4, 4, 5); + background-color: #b87338; } - QPushButton#theme_button { - width: 40px; + QPushButton#theme_button { + background-color: #089083; + color: #f5f5f5; + width: 50px; height: 30px; - color: #089083; + padding: 2px; font-size: 15px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #089083; + border-radius: 7px; } QPushButton#theme_button:hover { - background-color: #089083; - color: white; + background-color:rgb(8, 82, 74); } QPushButton::pressed#switch_theme { - background-color:rgb(7, 110, 100); - color: white; + background-color: #089083; } QRadioButton { @@ -72,7 +146,7 @@ namespace Ui { height: 16px; border-radius: 3px; border: 1px solid #727272; - background-color: #ffffff; + background-color: transparent; } QRadioButton::indicator:hover { border: 1px solid #fea36b; @@ -80,20 +154,237 @@ namespace Ui { QRadioButton::indicator:checked { background-color: #fea36b; border: 1px solid #fea36b; - } + } )"; - QString settings_window_dark_autumn_theme = R"( + QString settings_window_light_purple_theme = R"( + QWidget { + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, + stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(125, 109, 148)); + } + QLabel { + font-weight: bold; + font-family: 'Arial'; + color: rgb(42, 10, 25); + background-color: transparent; + } + + QLabel#title_label { + font-size: 20px; + } + + QLabel#font_size_label { + font-size: 35px; + } + + QPushButton#language_button { + background-color: #722548; + width: 50px; + height: 30px; + color: rgb(206, 193, 224); + padding: 2px; + font-size: 20px; + border-radius: 7px; + } + + QPushButton#language_button:hover { + background-color: rgb(98, 27, 59); + } + QPushButton#language_button:pressed { + background-color: rgb(78, 21, 47); + } + + QPushButton#theme_button { + background-color: rgb(42, 10, 25); + color: rgb(163, 148, 184); + width: 50px; + height: 30px; + padding: 2px; + font-size: 15px; + border-radius: 7px; + } + QPushButton#theme_button:hover { + background-color: rgb(21, 5, 12); + } + + QPushButton#theme_button:pressed{ + background-color: rgb(2, 0, 1); + } + + QRadioButton { + font-family: 'Arial'; + color: rgb(218, 207, 235); + spacing: 5px; + background-color: transparent; + } + QRadioButton::indicator { + width: 16px; + height: 16px; + border-radius: 3px; + border: 1px solid rgb(218, 207, 235); + background-color: transparent; + } + QRadioButton::indicator:hover { + border: 1px solid #722548; + } + QRadioButton::indicator:checked { + background-color: #722548; + border: 1px solid #722548; + } )"; + QString settings_window_dark_purple_theme = R"( + QWidget { + background-color: rgb(9, 6, 10); + } - )"; - QString settings_window_light_purple_theme = R"( + QLabel { + font-weight: bold; + font-family: 'Arial'; + color: #9882B9; + background-color: transparent; + } + + QLabel#title_label { + font-size: 20px; + } + + QLabel#font_size_label { + font-size: 35px; + } + QPushButton#language_button { + background-color: #722548; + color: #060407; + width: 50px; + height: 30px; + padding: 2px; + font-size: 20px; + border-radius: 7px; + } + + QPushButton#language_button:hover { + background-color: rgb(79, 25, 50); + } + QPushButton#language_button:pressed { + background-color:rgb(59, 16, 35); + } + + QPushButton#theme_button { + background-color: rgb(42, 10, 25); + color: #9882B9; + width: 50px; + height: 30px; + padding: 2px; + font-size: 15px; + border-radius: 7px; + } + QPushButton#theme_button:hover { + background-color:rgb(22, 5, 13); + } + + QPushButton#theme_button:pressed { + background-color:rgb(11, 3, 7); + } + + QRadioButton { + font-family: 'Arial'; + color: #9882B9; + spacing: 5px; + background-color: transparent; + } + QRadioButton::indicator { + width: 16px; + height: 16px; + border-radius: 3px; + border: 1px solid #9882B9; + background-color: transparent; + } + QRadioButton::indicator:hover { + border: 1px solid #722548; + } + QRadioButton::indicator:checked { + background-color: #722548; + border: 1px solid #722548; + } )"; + QString settings_window_blue_theme = R"( + QWidget { + background: #173C4C; + } + + QLabel { + font-weight: bold; + font-family: 'Arial'; + color: #BDD1BD; + background-color: transparent; + } + + QLabel#title_label { + font-size: 20px; + } + + QLabel#font_size_label { + font-size: 35px; + } + + QPushButton#language_button { + background-color: #BDD1BD; + color: #173C4C; + width: 50px; + height: 30px; + padding: 2px; + font-size: 20px; + border-radius: 7px; + } + QPushButton#language_button:hover { + background-color:rgb(158, 176, 158); + } + QPushButton#language_button:pressed { + background-color:rgb(141, 157, 141); + } + + QPushButton#theme_button { + background-color: #326D6C; + color: #BDD1BD; + width: 50px; + height: 30px; + color: #BDD1BD; + padding: 2px; + font-size: 15px; + border-radius: 7px; + } + QPushButton#theme_button:hover { + background-color:rgb(47, 89, 89); + } + + QPushButton#theme_button:pressed { + background-color:rgb(31, 69, 85); + } + + QRadioButton { + font-family: 'Arial'; + color: #BDD1BD; + spacing: 5px; + background-color: transparent; + } + QRadioButton::indicator { + width: 16px; + height: 16px; + border-radius: 3px; + border: 1px solid #BDD1BD; + background-color: transparent; + } + QRadioButton::indicator:hover { + border: 1px solid #568F7C; + } + QRadioButton::indicator:checked { + background-color: #568F7C; + border: 1px solid #568F7C; + } )"; } // namespace Ui \ No newline at end of file diff --git a/ui/settings-window/src/settings_window.cpp b/ui/settings-window/src/settings_window.cpp index c8651a3..5bb4b40 100644 --- a/ui/settings-window/src/settings_window.cpp +++ b/ui/settings-window/src/settings_window.cpp @@ -10,7 +10,7 @@ const std::vector SettingsWindow::THEMES = { Ui::settings_window_blue_theme }; -SettingsWindow::SettingsWindow(QWidget *parent) : QWidget(parent) { +SettingsWindow::SettingsWindow(QWidget *parent) : QDialog(parent) { main_layout = new QVBoxLayout(this); title_label = new QLabel("Настройки", this); @@ -65,7 +65,7 @@ SettingsWindow::SettingsWindow(QWidget *parent) : QWidget(parent) { large_font_radio->setText("Крупный"); setLayout(main_layout); - setFixedSize(140, 250); + setFixedSize(240, 260); handle_theme_changed(ThemeManager::instance()->current_theme()); } From 9fffd9ace96b64fc614c6c554efda0d927b40f55 Mon Sep 17 00:00:00 2001 From: MuravAna Date: Fri, 16 May 2025 14:07:28 +0300 Subject: [PATCH 10/17] Add analytics window (raw yet). Fix bugs in style, add base for translations --- CMakeLists.txt | 16 +- main.cpp | 41 +- ui/analytics-window/CMakeLists.txt | 18 +- .../include/analytics_window.h | 5 + .../include/analytics_window_style_sheet.h | 380 +++++++++++++++ ui/analytics-window/src/analytics_window.cpp | 35 +- .../include/login_window.h | 4 + ui/authorization-windows/src/login_window.cpp | 205 ++++---- .../src/registration_window.cpp | 194 ++++---- ui/main-window/include/bottombar.h | 5 +- ui/main-window/include/main_window_style.hpp | 20 + ui/main-window/src/bottombar.cpp | 11 +- ui/main-window/src/mainwindow.cpp | 13 +- ui/main-window/src/notewidget.cpp | 10 +- .../include/note_edit_dialog_styles.h | 13 +- ui/note-widget/include/tags_dialog.h | 5 + ui/note-widget/include/tags_dialog_styles.h | 444 +++++++++++++++++- ui/note-widget/src/tags_dialog.cpp | 18 +- ui/profile-window/include/profile_window.h | 1 + .../include/profile_window_style_sheet.h | 2 +- ui/profile-window/src/profile_window.cpp | 43 +- .../include/settings_window_style_sheet.h | 39 +- ui/settings-window/src/settings_window.cpp | 39 +- 23 files changed, 1223 insertions(+), 338 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 8ccf76e..b495766 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -9,7 +9,19 @@ set(CMAKE_AUTOUIC ON) set(CMAKE_CXX_STANDARD 20) set(CMAKE_CXX_STANDARD_REQUIRED ON) -find_package(Qt6 COMPONENTS Widgets Core Gui Sql REQUIRED) +find_package(Qt6 COMPONENTS Widgets LinguistTools Core Gui Sql REQUIRED) + +set(TS_FILES + translations/app_ru.ts + translations/app_en.ts +) + +qt_add_translation(QM_FILES ${TS_FILES}) + +qt_add_resources(PROJECT_RESOURCES + PREFIX "/translations" + FILES ${QM_FILES} +) add_subdirectory(scripts) add_subdirectory(database) @@ -39,4 +51,4 @@ target_link_libraries(EfficioTaskTracker PRIVATE NoteWidget SettingsWindow AnalyticsWindow -) \ No newline at end of file +) diff --git a/main.cpp b/main.cpp index 83ba433..6b77343 100644 --- a/main.cpp +++ b/main.cpp @@ -1,30 +1,36 @@ #include #include #include -#include #include +#include #include "applicationwindow.h" #include "login_window.h" -#include "settings_window.h" -#include "mainwindow.h" #include "theme_manager.h" +#include int main(int argc, char *argv[]) { - QApplication application(argc, argv); - application.setApplicationName("EFFICIO"); - application.setApplicationDisplayName("EFFICIO"); + QApplication app(argc, argv); + + app.setApplicationName("EFFICIO"); + app.setApplicationDisplayName("EFFICIO"); + app.setOrganizationName("EFFICIO"); + app.setWindowIcon(QIcon(":/icons/app_icon.png")); - QTranslator translator; - const QStringList ui_languages = QLocale::system().uiLanguages(); - for (const QString &locale : ui_languages) { - const QString base_name = "MainWindow_" + QLocale(locale).name(); - if (translator.load(":/i18n/" + base_name)) { - QApplication::installTranslator(&translator); - break; - } + QTranslator appTranslator; + QTranslator qtTranslator; + + QSettings settings; + QString language = settings.value("Language", QLocale::system().name()).toString(); + + if (appTranslator.load(":/translations/app_" + language + ".qm")) { + app.installTranslator(&appTranslator); + } + + if (qtTranslator.load("qt_" + language, QLibraryInfo::path(QLibraryInfo::TranslationsPath))) { + app.installTranslator(&qtTranslator); } - ThemeManager* themeManager = ThemeManager::instance(); + ThemeManager* themeManager = ThemeManager::instance(); QMainWindow *app_window = new QMainWindow(); app_window->setWindowTitle("EFFICIO"); @@ -37,5 +43,6 @@ int main(int argc, char *argv[]) { app_window->move(x, y); app_window->show(); - return application.exec(); -} + return app.exec(); + +} \ No newline at end of file diff --git a/ui/analytics-window/CMakeLists.txt b/ui/analytics-window/CMakeLists.txt index 1e40142..6d49ed1 100644 --- a/ui/analytics-window/CMakeLists.txt +++ b/ui/analytics-window/CMakeLists.txt @@ -28,12 +28,14 @@ target_include_directories(AnalyticsWindow $ ) -target_link_libraries(AnalyticsWindow PRIVATE - Qt6::Widgets - Qt6::Core - Qt6::Gui - Qt6::Sql - Qt6::Charts - Database - ThemeManager +target_link_libraries(AnalyticsWindow + PRIVATE + Qt6::Core + Qt6::Gui + Qt6::Sql + Database + ThemeManager + PUBLIC + Qt6::Widgets + Qt6::Charts ) \ No newline at end of file diff --git a/ui/analytics-window/include/analytics_window.h b/ui/analytics-window/include/analytics_window.h index f93d900..b052775 100644 --- a/ui/analytics-window/include/analytics_window.h +++ b/ui/analytics-window/include/analytics_window.h @@ -6,6 +6,7 @@ #include #include #include +#include class AnalyticsWindow : public QDialog { @@ -17,6 +18,10 @@ class AnalyticsWindow : public QDialog void setTasksData(int created, int completed, int overdue); void setProjectsData(const QMap& projects); + void handle_theme_changed(int theme); + void on_switch_theme_clicked(); + + static const std::vector THEMES; private: QTabWidget *tab_widget; diff --git a/ui/analytics-window/include/analytics_window_style_sheet.h b/ui/analytics-window/include/analytics_window_style_sheet.h index e69de29..124c75a 100644 --- a/ui/analytics-window/include/analytics_window_style_sheet.h +++ b/ui/analytics-window/include/analytics_window_style_sheet.h @@ -0,0 +1,380 @@ +#ifndef ANALYTICS_WINDOW_STYLE_SHEET_H +#define ANALYTICS_WINDOW_STYLE_SHEET_H + +#include + +namespace Ui { + +const QString analytics_window_light_autumn_theme = R"( +#AnalyticsWindow { + background-color: #f5f5f5; + color: #444444; + font-family: "Segoe UI"; +} + +QTabWidget::pane { + border: 1px solid #d0d0d0; + border-radius: 4px; + margin: 5px; + background: #ffffff; +} + +QTabBar::tab { + background: #e0e0e0; + color: #666666; + border: 1px solid #d0d0d0; + border-bottom: none; + border-top-left-radius: 4px; + border-top-right-radius: 4px; + padding: 8px 15px; + margin-right: 2px; +} + +QTabBar::tab:selected { + background: #ffffff; + color: #222222; + border-color: #d0d0d0; + font-weight: bold; +} + +QTabBar::tab:hover { + background: #f0f0f0; +} + +QDialogButtonBox { + border-top: 1px solid #d0d0d0; + padding-top: 10px; +} + +QDialogButtonBox QPushButton { + background-color: #fea36b; + color: white; + border: 1px solid #e08c52; + border-radius: 3px; + padding: 5px 15px; + min-width: 80px; +} + +QDialogButtonBox QPushButton:hover { + background-color: #f58c50; +} + +QDialogButtonBox QPushButton:pressed { + background-color: #e07c40; +} + +QChartView { + background-color: #ffffff; + border-radius: 5px; + border: 1px solid #d0d0d0; + margin: 10px; +} + +QLegend::label { + color: #666666; +} + +QAbstractAxis { + color: #888888; +} +)"; + +const QString analytics_window_dark_autumn_theme = R"( +#AnalyticsWindow { + background-color: #202020; + color: #BDD1BD; + font-family: "Segoe UI"; +} + +QTabWidget::pane { + border: 1px solid #333333; + border-radius: 4px; + margin: 5px; + background: #282828; +} + +QTabBar::tab { + background: #323232; + color: #8a8a8a; + border: 1px solid #333333; + border-bottom: none; + border-top-left-radius: 4px; + border-top-right-radius: 4px; + padding: 8px 15px; + margin-right: 2px; +} + +QTabBar::tab:selected { + background: #3a3a3a; + color: #BDD1BD; + border-color: #333333; + font-weight: bold; +} + +QTabBar::tab:hover { + background: #363636; +} + +QDialogButtonBox { + border-top: 1px solid #333333; + padding-top: 10px; +} + +QDialogButtonBox QPushButton { + background-color: #d38b5f; + color: #263238; + border: 1px solid #b3754d; + border-radius: 3px; + padding: 5px 15px; + min-width: 80px; +} + +QDialogButtonBox QPushButton:hover { + background-color: #c07b4f; +} + +QDialogButtonBox QPushButton:pressed { + background-color: #a86b3f; +} + +QChartView { + background-color: #282828; + border-radius: 5px; + border: 1px solid #333333; + margin: 10px; +} + +QLegend::label { + color: #a0a0a0; +} + +QAbstractAxis { + color: #8a8a8a; +} +)"; + +const QString analytics_window_light_purple_theme = R"( +#AnalyticsWindow { + background-color: #9882B9; + color: rgb(42, 10, 25); + font-family: "Segoe UI"; +} + +QTabWidget::pane { + border: 1px solid #7a5d9b; + border-radius: 4px; + margin: 5px; + background: #b9a2d9; +} + +QTabBar::tab { + background: #a992c9; + color: rgb(62, 20, 35); + border: 1px solid #7a5d9b; + border-bottom: none; + border-top-left-radius: 4px; + border-top-right-radius: 4px; + padding: 8px 15px; + margin-right: 2px; +} + +QTabBar::tab:selected { + background: #d9c2f9; + color: rgb(42, 10, 25); + border-color: #7a5d9b; + font-weight: bold; +} + +QTabBar::tab:hover { + background: #c9b2e9; +} + +QDialogButtonBox { + border-top: 1px solid #7a5d9b; + padding-top: 10px; +} + +QDialogButtonBox QPushButton { + background-color: #722548; + color: #f5e5ff; + border: 1px solid #5a1538; + border-radius: 3px; + padding: 5px 15px; + min-width: 80px; +} + +QDialogButtonBox QPushButton:hover { + background-color: #5a1538; +} + +QDialogButtonBox QPushButton:pressed { + background-color: #4a0528; +} + +QChartView { + background-color: #d9c2f9; + border-radius: 5px; + border: 1px solid #7a5d9b; + margin: 10px; +} + +QLegend::label { + color: rgb(62, 20, 35); +} + +QAbstractAxis { + color: rgb(82, 40, 55); +} +)"; + +const QString analytics_window_dark_purple_theme = R"( +#AnalyticsWindow { + background-color: #221932; + color: #9882B9; + font-family: "Segoe UI"; +} + +QTabWidget::pane { + border: 1px solid #3a2a4a; + border-radius: 4px; + margin: 5px; + background: #2a1f3a; +} + +QTabBar::tab { + background: #322242; + color: #7a6a9a; + border: 1px solid #3a2a4a; + border-bottom: none; + border-top-left-radius: 4px; + border-top-right-radius: 4px; + padding: 8px 15px; + margin-right: 2px; +} + +QTabBar::tab:selected { + background: #4a3a5a; + color: #c9b2e9; + border-color: #5a4a6a; + font-weight: bold; +} + +QTabBar::tab:hover { + background: #3a2a4a; +} + +QDialogButtonBox { + border-top: 1px solid #3a2a4a; + padding-top: 10px; +} + +QDialogButtonBox QPushButton { + background-color: #722548; + color: #d9c2f9; + border: 1px solid #5a1538; + border-radius: 3px; + padding: 5px 15px; + min-width: 80px; +} + +QDialogButtonBox QPushButton:hover { + background-color: #5a1538; +} + +QDialogButtonBox QPushButton:pressed { + background-color: #4a0528; +} + +QChartView { + background-color: #322242; + border-radius: 5px; + border: 1px solid #3a2a4a; + margin: 10px; +} + +QLegend::label { + color: #9a82b9; +} + +QAbstractAxis { + color: #8a7aa9; +} +)"; + +const QString analytics_window_blue_theme = R"( +#AnalyticsWindow { + background-color: #07142B; + color: #BDD1BD; + font-family: "Segoe UI"; +} + +QTabWidget::pane { + border: 1px solid #1a2c4b; + border-radius: 4px; + margin: 5px; + background: #0f1c35; +} + +QTabBar::tab { + background: #173C4C; + color: #8dacbd; + border: 1px solid #1a2c4b; + border-bottom: none; + border-top-left-radius: 4px; + border-top-right-radius: 4px; + padding: 8px 15px; + margin-right: 2px; +} + +QTabBar::tab:selected { + background: #1f4c5c; + color: #BDD1BD; + border-color: #1a2c4b; + font-weight: bold; +} + +QTabBar::tab:hover { + background: #1b4454; +} + +QDialogButtonBox { + border-top: 1px solid #1a2c4b; + padding-top: 10px; +} + +QDialogButtonBox QPushButton { + background-color: #568F7C; + color: #07142B; + border: 1px solid #3a6f5c; + border-radius: 3px; + padding: 5px 15px; + min-width: 80px; +} + +QDialogButtonBox QPushButton:hover { + background-color: #3a6f5c; +} + +QDialogButtonBox QPushButton:pressed { + background-color: #2a5f4c; +} + +QChartView { + background-color: #0f1c35; + border-radius: 5px; + border: 1px solid #1a2c4b; + margin: 10px; +} + +QLegend::label { + color: #9dbdcd; +} + +QAbstractAxis { + color: #7d9cad; +} +)"; + +} // namespace Ui + +#endif // ANALYTICS_WINDOW_STYLE_SHEET_H \ No newline at end of file diff --git a/ui/analytics-window/src/analytics_window.cpp b/ui/analytics-window/src/analytics_window.cpp index 11f3a82..69f1d3e 100644 --- a/ui/analytics-window/src/analytics_window.cpp +++ b/ui/analytics-window/src/analytics_window.cpp @@ -1,11 +1,22 @@ -#include "analytics_dialog.h" +#include "analytics_window.h" +#include "theme_manager.h" +#include "analytics_window_style_sheet.h" +#include + +const std::vector AnalyticsWindow::THEMES = { + Ui::analytics_window_light_autumn_theme, + Ui::analytics_window_dark_autumn_theme, + Ui::analytics_window_dark_purple_theme, + Ui::analytics_window_light_purple_theme, + Ui::analytics_window_blue_theme +}; AnalyticsWindow::AnalyticsWindow(QWidget *parent) : QDialog(parent) { QVBoxLayout *main_layout = new QVBoxLayout(this); - tab_widget = new Qtab_widget(this); + tab_widget = new QTabWidget(this); QWidget *tasks_tab = new QWidget(); tasks_layout = new QVBoxLayout(tasks_tab); @@ -15,8 +26,8 @@ AnalyticsWindow::AnalyticsWindow(QWidget *parent) projects_layout = new QVBoxLayout(projects_tab); tab_widget->addTab(projects_tab, "Распределение по проектам"); - button_box = new QDialogbutton_box(QDialogbutton_box::Close, this); - connect(button_box, &QDialogbutton_box::rejected, this, &QDialog::reject); + button_box = new QDialogButtonBox(QDialogButtonBox::Close, this); + connect(button_box, &QDialogButtonBox::rejected, this, &QDialog::reject); main_layout->addWidget(tab_widget); main_layout->addWidget(button_box); @@ -28,13 +39,23 @@ AnalyticsWindow::AnalyticsWindow(QWidget *parent) QMap projects; setProjectsData(projects); + + connect(ThemeManager::instance(), &ThemeManager::theme_changed, + this, &AnalyticsWindow::handle_theme_changed); + handle_theme_changed(ThemeManager::instance()->current_theme()); } -AnalyticsWindow::~AnalyticsWindow() -{ - delete this; +void AnalyticsWindow::handle_theme_changed(int theme) { + this->setStyleSheet(THEMES[theme]); } +void AnalyticsWindow::on_switch_theme_clicked() { + int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; + ThemeManager::instance()->apply_theme(next_theme); +} + +AnalyticsWindow::~AnalyticsWindow(){} + void AnalyticsWindow::setTasksData(int created, int completed, int overdue) { QLayoutItem *child; diff --git a/ui/authorization-windows/include/login_window.h b/ui/authorization-windows/include/login_window.h index b28a491..2c5d7e3 100644 --- a/ui/authorization-windows/include/login_window.h +++ b/ui/authorization-windows/include/login_window.h @@ -2,6 +2,7 @@ #include #include +#include #include QT_BEGIN_NAMESPACE @@ -29,4 +30,7 @@ private slots: private: std::shared_ptr ui; int counter_on_switch_theme_clicks = 0; + void switch_window(QMainWindow *app_window, QWidget *new_window, int width, int height); + void switch_to_login_window(QMainWindow *app_window); + void switch_to_registration_window(QMainWindow *app_window); }; \ No newline at end of file diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index 7a0d220..2662084 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -1,24 +1,13 @@ #include "login_window.h" -#include -#include -#include -#include -#include -#include -#include -#include #include "applicationwindow.h" -#include "bottombar.h" -#include "database_manager.hpp" #include "lr_dao.hpp" #include "mainwindow.h" -#include "notelist.h" #include "registration_window.h" -#include "serialization.hpp" #include "login_window_style_sheet.h" +#include "serialization.hpp" #include "theme_manager.h" - -#include +#include +#include const std::vector LoginWindow::THEMES = { Ui::login_window_light_autumn_theme, @@ -33,25 +22,20 @@ LoginWindow::LoginWindow(QWidget *parent) ui->setupUi(this); setFixedSize(380, 480); - ui->input_login->setPlaceholderText("Введите логин:"); - ui->input_password->setPlaceholderText("Введите пароль:"); - + ui->input_login->setPlaceholderText(tr("Введите логин:")); + ui->input_password->setPlaceholderText(tr("Введите пароль:")); ui->input_password->setEchoMode(QLineEdit::Password); - handle_theme_changed(ThemeManager::instance()->current_theme()); - - connect( - ui->switch_theme, &QPushButton::clicked, this, - &LoginWindow::on_switch_theme_clicked - , Qt::UniqueConnection); - connect( - ui->switch_mode, &QPushButton::clicked, this, + connect(ui->switch_theme, &QPushButton::clicked, this, + &LoginWindow::on_switch_theme_clicked, Qt::UniqueConnection); + connect(ui->switch_mode, &QPushButton::clicked, this, &LoginWindow::on_switch_mode_clicked); - connect( - ui->push_enter, &QPushButton::clicked, this, + connect(ui->push_enter, &QPushButton::clicked, this, &LoginWindow::on_push_enter_clicked); connect(ThemeManager::instance(), &ThemeManager::theme_changed, this, &LoginWindow::handle_theme_changed); + + handle_theme_changed(ThemeManager::instance()->current_theme()); } void LoginWindow::handle_theme_changed(int theme) { @@ -59,7 +43,7 @@ void LoginWindow::handle_theme_changed(int theme) { } void LoginWindow::on_switch_theme_clicked() { - if ((this->counter_on_switch_theme_clicks++)%2){ + if ((this->counter_on_switch_theme_clicks++) % 2) { int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; ThemeManager::instance()->apply_theme(next_theme); } @@ -68,95 +52,94 @@ void LoginWindow::on_switch_theme_clicked() { LoginWindow::~LoginWindow() = default; void LoginWindow::on_switch_mode_clicked() { - QWidget *parent = this->parentWidget(); + if (QMainWindow *app_window = qobject_cast(this->parentWidget())) { + RegistrationWindow *registration_window = new RegistrationWindow(app_window); + switch_window(app_window, registration_window, 380, 480); + this->close(); + } +} - QMainWindow *app_window = qobject_cast(parent); +void LoginWindow::on_push_enter_clicked() { + if ((this->counter_on_switch_theme_clicks++) % 2) { + // QString login = ui->input_login->text().trimmed(); + // QString password = ui->input_password->text(); + + // if (login.isEmpty() || password.isEmpty()) { + // QMessageBox::warning(this, + // tr("Ошибка ввода данных"), + // tr("Пожалуйста, заполните все поля!")); + // return; + // } + + // if (login.size() > 50) { + // QMessageBox::warning(this, + // tr("Ошибка"), + // tr("Длина логина не должна превышать пятидесяти символов")); + // return; + // } + + // if (password.size() > 50) { + // QMessageBox::warning(this, + // tr("Ошибка"), + // tr("Длина пароля не должна превышать пятидесяти символов")); + // return; + // } + + // if (!LRDao::validate_user(login, password)) { + // QMessageBox::warning(this, + // tr("Ошибка ввода данных"), + // tr("Неверный логин или пароль!")); + // return; + // } + + // QMessageBox::information(this, + // tr("Вход"), + // tr("Вы успешно вошли! Добро пожаловать :)")); + QString login = "user"; + if (QMainWindow *app_window = qobject_cast(this->parentWidget())) { + this->deleteLater(); + project_storage_model::Storage *storage = new project_storage_model::Storage(); + Serialization::get_storage(*storage, login.toStdString()); + + Ui::MainWindow *main_window = new Ui::MainWindow(app_window, login.toStdString(), storage); + + connect(main_window, &Ui::MainWindow::logout_requested, app_window, [app_window, this]() { + switch_to_login_window(app_window); + }); + + connect(main_window, &Ui::MainWindow::delete_account_requested, app_window, [app_window, this]() { + switch_to_registration_window(app_window); + }); + + switch_window(app_window, main_window, 800, 600); + } + } +} +void LoginWindow::switch_window(QMainWindow *app_window, QWidget *new_window, int width, int height) { if (QWidget *old = app_window->centralWidget()) { old->deleteLater(); } - project_storage_model::Storage storage; - RegistrationWindow *registration_window = - new RegistrationWindow(app_window); - - app_window->setCentralWidget(registration_window); - QRect screenGeometry = QApplication::primaryScreen()->availableGeometry(); - int x = (screenGeometry.width() - registration_window->width()) / 2; - int y = (screenGeometry.height() - registration_window->height()) / 2; - app_window->move(x, y); + + app_window->setCentralWidget(new_window); + if (width > 0 && height > 0) { + app_window->resize(width, height); + } + + QRect screen_geometry = QApplication::primaryScreen()->availableGeometry(); + app_window->move( + (screen_geometry.width() - width) / 2, + (screen_geometry.height() - height) / 2 + ); + app_window->show(); +} - this->close(); +void LoginWindow::switch_to_login_window(QMainWindow *app_window) { + LoginWindow *login_window = new LoginWindow(app_window); + switch_window(app_window, login_window, 380, 480); } -void LoginWindow::on_push_enter_clicked() { - // if ((this->counter_on_switch_theme_clicks++)%2){ - // QString login = ui->input_login->text(); - // QString password = ui->input_password->text(); - - // if (!login.isEmpty() && !password.isEmpty()) { - // if (login.size() > 50) { - // QMessageBox::warning( - // this, "Ошибка", - // "Длина логина не должна превышать пятидесяти символов" - // ); - // } else if (password.size() > 50) { - // QMessageBox::warning( - // this, "Ошибка", - // "Длина пароля не должна превышать пятидесяти символов" - // ); - // } else if (LRDao::validate_user(login, password)) { - // QMessageBox::information( - // this, "Вход", "Вы успешно вошли! Добро пожаловать :)" - // ); - QMainWindow *app_window = qobject_cast(this->parentWidget()); - this->deleteLater(); - project_storage_model::Storage *storage = - new project_storage_model::Storage(); - QString login = "user"; - Serialization::get_storage(*storage, login.toStdString()); - - Ui::MainWindow *main_window = - new Ui::MainWindow(app_window, login.toStdString(), storage); - - connect(main_window, &Ui::MainWindow::logout_requested, app_window, [app_window]() { - LoginWindow *login_window = new LoginWindow(app_window); - app_window->setCentralWidget(login_window); - app_window->resize(380, 480); - QRect screenGeometry = - QApplication::primaryScreen()->availableGeometry(); - int x = (screenGeometry.width() - login_window->width()) / 2; - int y = (screenGeometry.height() - login_window->height()) / 2; - app_window->move(x, y); - app_window->show(); - }); - connect(main_window, &Ui::MainWindow::delete_account_requested, app_window, [app_window]() { - RegistrationWindow *registration_window = new RegistrationWindow(app_window); - app_window->setCentralWidget(registration_window); - app_window->resize(380, 480); - QRect screenGeometry = - QApplication::primaryScreen()->availableGeometry(); - int x = (screenGeometry.width() - registration_window->width()) / 2; - int y = (screenGeometry.height() - registration_window->height()) / 2; - app_window->move(x, y); - app_window->show(); - }); - app_window->setCentralWidget(main_window); - app_window->resize(800, 600); - QRect screenGeometry = - QApplication::primaryScreen()->availableGeometry(); - int x = (screenGeometry.width() - 800) / 2; - int y = (screenGeometry.height() - 600) / 2; - app_window->move(x, y); - app_window->show(); - // } else { - // QMessageBox::warning( - // this, "Ошибка ввода данных", "Неверный логин или пароль!" - // ); - // } - // } else { - // QMessageBox::warning( - // this, "Ошибка ввода данных", "Пожалуйста, заполните все поля!" - // ); - // } - // } +void LoginWindow::switch_to_registration_window(QMainWindow *app_window) { + RegistrationWindow *registration_window = new RegistrationWindow(app_window); + switch_window(app_window, registration_window, 380, 480); } \ No newline at end of file diff --git a/ui/authorization-windows/src/registration_window.cpp b/ui/authorization-windows/src/registration_window.cpp index 2ce13e9..6afce75 100644 --- a/ui/authorization-windows/src/registration_window.cpp +++ b/ui/authorization-windows/src/registration_window.cpp @@ -1,102 +1,81 @@ #include "registration_window.h" -#include -#include -#include -#include -#include #include -#include -#include -#include "applicationwindow.h" -#include "bottombar.h" -#include "database_manager.hpp" -#include "login_window.h" +#include #include "lr_dao.hpp" -#include "notelist.h" -#include "registration_window_style_sheet.h" -#include "ui_registration_window.h" -#include +#include "login_window.h" #include "theme_manager.h" +#include "registration_window_style_sheet.h" const std::vector RegistrationWindow::THEMES = { - Ui::registration_window_light_autumn_theme, - Ui::registration_window_dark_autumn_theme, - Ui::registration_window_dark_purple_theme, - Ui::registration_window_light_purple_theme, - Ui::registration_window_blue_theme - }; + Ui::registration_window_light_autumn_theme, + Ui::registration_window_dark_autumn_theme, + Ui::registration_window_dark_purple_theme, + Ui::registration_window_light_purple_theme, + Ui::registration_window_blue_theme +}; RegistrationWindow::RegistrationWindow(QWidget *parent) : QWidget(parent), ui(new Ui::RegistrationWindow) { ui->setupUi(this); - setFixedSize(380, 480); - ui->create_login->setPlaceholderText("Введите логин:"); - ui->create_password->setPlaceholderText("Введите пароль:"); - ui->repeat_password->setPlaceholderText("Повторите пароль:"); + ui->create_login->setPlaceholderText(tr("Введите логин:")); + ui->create_password->setPlaceholderText(tr("Введите пароль:")); + ui->repeat_password->setPlaceholderText(tr("Повторите пароль:")); ui->create_password->setEchoMode(QLineEdit::Password); ui->repeat_password->setEchoMode(QLineEdit::Password); setAttribute(Qt::WA_StyledBackground, true); - connect( - ui->switch_theme, &QPushButton::clicked, this, - &RegistrationWindow::on_switch_theme_clicked - , Qt::UniqueConnection); - - connect( - ui->push_registration, &QPushButton::clicked, this, - &RegistrationWindow::on_push_registration_clicked - , Qt::UniqueConnection); - connect( - ui->switch_mode, &QPushButton::clicked, this, - &RegistrationWindow::on_switch_mode_clicked - , Qt::UniqueConnection); + connect(ui->switch_theme, &QPushButton::clicked, this, + &RegistrationWindow::on_switch_theme_clicked, Qt::UniqueConnection); + connect(ui->push_registration, &QPushButton::clicked, this, + &RegistrationWindow::on_push_registration_clicked, Qt::UniqueConnection); + connect(ui->switch_mode, &QPushButton::clicked, this, + &RegistrationWindow::on_switch_mode_clicked, Qt::UniqueConnection); connect(ThemeManager::instance(), &ThemeManager::theme_changed, this, &RegistrationWindow::handle_theme_changed); + handle_theme_changed(ThemeManager::instance()->current_theme()); } - void RegistrationWindow::handle_theme_changed(int theme) { this->setStyleSheet(THEMES[theme]); } void RegistrationWindow::on_switch_theme_clicked() { - if ((this->counter_on_switch_theme_clicks++)%2){ + if ((this->counter_on_switch_theme_clicks++)%2) { int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; ThemeManager::instance()->apply_theme(next_theme); } } - RegistrationWindow::~RegistrationWindow() = default; void RegistrationWindow::on_switch_mode_clicked() { - QWidget *parent = this->parentWidget(); - - QMainWindow *app_window = qobject_cast(parent); - - if (QWidget *old = app_window->centralWidget()) { - old->deleteLater(); + if (QMainWindow *app_window = qobject_cast(this->parentWidget())) { + if (QWidget *old = app_window->centralWidget()) { + old->deleteLater(); + } + + LoginWindow *login_window = new LoginWindow(app_window); + app_window->setCentralWidget(login_window); + + QRect screen_geometry = QApplication::primaryScreen()->availableGeometry(); + app_window->move( + (screen_geometry.width() - login_window->width()) / 2, + (screen_geometry.height() - login_window->height()) / 2 + ); + + this->close(); } - LoginWindow *login_window = new LoginWindow(app_window); - - app_window->setCentralWidget(login_window); - QRect screenGeometry = QApplication::primaryScreen()->availableGeometry(); - int x = (screenGeometry.width() - login_window->width()) / 2; - int y = (screenGeometry.height() - login_window->height()) / 2; - app_window->move(x, y); - - this->close(); } bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { if (password.length() < 8) { QMessageBox::warning( - nullptr, "Ошибка: недостаточно надежный пароль", - "Пароль должен содержать не менее восьми символов" + nullptr, tr("Ошибка: недостаточно надежный пароль"), + tr("Пароль должен содержать не менее восьми символов") ); return false; } @@ -104,11 +83,11 @@ bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { bool has_digit = false; bool has_latin_letter = false; - for (const QChar ch : password) { + for (const QChar &ch : password) { if (!ch.isLetter() && !ch.isDigit()) { QMessageBox::warning( - nullptr, "Ошибка", - "Пароль должен содержать только символы латиницы и цифры" + nullptr, tr("Ошибка"), + tr("Пароль должен содержать только символы латиницы и цифры") ); return false; } else if (ch.isLetter()) { @@ -120,15 +99,15 @@ bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { if (!has_latin_letter) { QMessageBox::warning( - nullptr, "Ошибка: недостаточно надежный пароль", - "Пароль должен содержать хотя бы одну букву" + nullptr, tr("Ошибка: недостаточно надежный пароль"), + tr("Пароль должен содержать хотя бы одну букву") ); return false; } if (!has_digit) { QMessageBox::warning( - nullptr, "Ошибка: недостаточно надежный пароль", - "Пароль должен содержать хотя бы одну цифру" + nullptr, tr("Ошибка: недостаточно надежный пароль"), + tr("Пароль должен содержать хотя бы одну цифру") ); return false; } @@ -137,49 +116,62 @@ bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { } void RegistrationWindow::on_push_registration_clicked() { - if ((this->counter_on_switch_theme_clicks++)%2){ - QString created_login = ui->create_login->text(); + if ((this->counter_on_switch_theme_clicks++)%2) { + QString created_login = ui->create_login->text().trimmed(); QString created_password = ui->create_password->text(); QString repeated_password = ui->repeat_password->text(); - if (!created_login.isEmpty() && !created_password.isEmpty() && - !repeated_password.isEmpty()) { - if (created_password != repeated_password) { - QMessageBox::warning(this, "Ошибка", "Пароли не совпадают!"); - } else if (created_login.size() > 50) { + if (created_login.isEmpty() || created_password.isEmpty() || repeated_password.isEmpty()) { + QMessageBox::warning(this, tr("Ошибка"), tr("Пожалуйста, заполните все поля.")); + return; + } + + if (created_password != repeated_password) { + QMessageBox::warning(this, tr("Ошибка"), tr("Пароли не совпадают!")); + return; + } + + if (created_login.size() > 50) { + QMessageBox::warning( + this, tr("Ошибка"), + tr("Длина логина не должна превышать пятидесяти символов") + ); + return; + } + + if (created_password.size() > 50) { + QMessageBox::warning( + this, tr("Ошибка"), + tr("Длина пароля не должна превышать пятидесяти символов") + ); + return; + } + + if (!is_strong_and_valid_password(created_password)) { + return; + } + + int try_register_user = LRDao::try_register_user(created_login, created_password); + switch (try_register_user) { + case 0: QMessageBox::warning( - this, "Ошибка", - "Длина логина не должна превышать пятидесяти символов" + this, tr("Ошибка"), + tr("Извините, внутренняя ошибка с базами данных.") ); - } else if (created_password.size() > 50) { + break; + case -1: QMessageBox::warning( - this, "Ошибка", - "Длина пароля не должна превышать пятидесяти символов" + this, tr("Ошибка"), + tr("Пользователь с таким именем уже существует. Пожалуйста, придумайте другое!") + ); + break; + default: + QMessageBox::information( + this, tr("Регистрация"), + tr("Вы успешно зарегистрировались! Пожалуйста, выполните вход.") ); - } else if (is_strong_and_valid_password(created_password)) { - int try_register_user = - LRDao::try_register_user(created_login, created_password); - if (try_register_user == 0) { - QMessageBox::warning( - this, "Ошибка", - "Извините, внутренняя ошибка с базами данных." - ); - } else if (try_register_user == -1) { - QMessageBox::warning( - this, "Ошибка", - "Пользователь с таким именем уже существует. Пожалуйста, " - "придумайте другое!" - ); - } else { - QMessageBox::information( - this, "Регистрация", - "Вы успешно зарегистрировались! Пожалуйста, выполните вход." - ); - on_switch_mode_clicked(); - } - } - } else { - QMessageBox::warning(this, "Ошибка", "Пожалуйста, заполните все поля."); + on_switch_mode_clicked(); + break; } } } \ No newline at end of file diff --git a/ui/main-window/include/bottombar.h b/ui/main-window/include/bottombar.h index 3634dfb..0663d39 100644 --- a/ui/main-window/include/bottombar.h +++ b/ui/main-window/include/bottombar.h @@ -6,6 +6,7 @@ #include #include #include +#include namespace Ui { class BottomBar : public QWidget { @@ -14,8 +15,8 @@ class BottomBar : public QWidget { public: BottomBar( QWidget *parent, - std::string username, - std::string project_name + const std::string& username, + QString project_name ); signals: diff --git a/ui/main-window/include/main_window_style.hpp b/ui/main-window/include/main_window_style.hpp index 76ea0f0..532e157 100644 --- a/ui/main-window/include/main_window_style.hpp +++ b/ui/main-window/include/main_window_style.hpp @@ -116,9 +116,13 @@ QScrollArea { } #BottomBar QPushButton { + background-color: transparent; color: white; font-family: 'Arial'; font-size: 13px; + padding: 0px 0px; + min-width: 0px; + min-height: 0px; } #BottomBar QPushButton:hover { @@ -306,9 +310,13 @@ QString main_window_dark_autumn_theme = R"( } #BottomBar QPushButton { + background-color: transparent; color: #c0c0c0; font-family: 'Arial'; font-size: 13px; + padding: 0px 0px; + min-width: 0px; + min-height: 0px; } #BottomBar QPushButton:hover { @@ -497,9 +505,13 @@ QScrollArea { } #BottomBar QPushButton { + background-color: transparent; color: #9882B9; font-family: 'Arial'; font-size: 13px; + padding: 0px 0px; + min-width: 0px; + min-height: 0px; } #BottomBar QPushButton:hover { @@ -689,9 +701,13 @@ QScrollArea { } #BottomBar QPushButton { + background-color: transparent; color: #9882B9; font-family: 'Arial'; font-size: 13px; + padding: 0px 0px; + min-width: 0px; + min-height: 0px; } #BottomBar QPushButton:hover { @@ -879,9 +895,13 @@ QScrollArea { } #BottomBar QPushButton { + background-color: transparent; color: #BDD1BD; font-family: 'Arial'; font-size: 13px; + padding: 0px 0px; + min-width: 0px; + min-height: 0px; } #BottomBar QPushButton:hover { diff --git a/ui/main-window/src/bottombar.cpp b/ui/main-window/src/bottombar.cpp index 0e92c8a..8b5052d 100644 --- a/ui/main-window/src/bottombar.cpp +++ b/ui/main-window/src/bottombar.cpp @@ -2,16 +2,17 @@ #include #include #include +#include namespace Ui { BottomBar::BottomBar( QWidget *parent, - std::string username, - std::string project_name + const std::string& username, + QString project_name ) : QWidget(parent), main_layout_(new QHBoxLayout()), - project_name_(new QLabel(project_name.c_str())), + project_name_(new QLabel(project_name)), profile_button_(new QPushButton(username.c_str())) { this->setObjectName("BottomBar"); @@ -19,7 +20,6 @@ BottomBar::BottomBar( this->setFixedHeight(40); profile_button_->setObjectName("profile_button"); - profile_button_->setStyleSheet("background-color: transparent; text-align: right;"); project_name_->setAlignment(Qt::AlignLeft | Qt::AlignVCenter); @@ -29,5 +29,8 @@ BottomBar::BottomBar( connect(profile_button_, &QPushButton::clicked, this, &BottomBar::profile_button_clicked); + + this->setLayout(main_layout_); + this->setAttribute(Qt::WA_StyledBackground); } } // namespace Ui \ No newline at end of file diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index 5bcf480..2156cb5 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -12,6 +12,7 @@ #include #include #include +#include #include "applicationwindow.h" #include "bottombar.h" #include "lr_dao.hpp" @@ -44,13 +45,13 @@ MainWindow::MainWindow( : QWidget(parent), username(username), main_layout_(new QVBoxLayout(this)), - top_bar_(new BottomBar(this, username, "EFFICIO :: Таск-Трекер")), + top_bar_(new BottomBar(this, username, tr("EFFICIO :: Таск-Трекер"))), content_layout_(new QHBoxLayout(this)), project_list_(new ProjectList(this)), note_list_(new NoteList(this)), content_widget_(new QWidget(this)), - new_project_button_(new QPushButton("Новый проект", this)), - new_note_button_(new QPushButton("Новая заметка", this)), + new_project_button_(new QPushButton(tr("Новый проект"), this)), + new_note_button_(new QPushButton(tr("Новая заметка"), this)), storage_(storage) { this->setObjectName("main-window"); this->setAttribute(Qt::WA_StyledBackground); @@ -129,7 +130,7 @@ void MainWindow::on_profile_button_click() { void MainWindow::add_project() { bool ok; QString name_of_project = QInputDialog::getText( - nullptr, "Название проекта:", "Введите название", QLineEdit::Normal, "", + nullptr, tr("Название проекта:"), tr("Введите название"), QLineEdit::Normal, "", &ok ); if (ok) { @@ -154,12 +155,12 @@ void MainWindow::add_note() { project_item->project_->get_id(), id ); auto ¬e = - project_item->project_->add_note({id, "Пустая заметка", ""}); + project_item->project_->add_note({id, tr("Пустая заметка").toStdString(), ""}); note_list_->add_note_widget(¬e); } } else { QMessageBox msg; - msg.setText("Проект не выбран!"); + msg.setText(tr("Проект не выбран!")); msg.exec(); } } diff --git a/ui/main-window/src/notewidget.cpp b/ui/main-window/src/notewidget.cpp index 1b60987..c5ee584 100644 --- a/ui/main-window/src/notewidget.cpp +++ b/ui/main-window/src/notewidget.cpp @@ -14,13 +14,13 @@ NoteWidget::NoteWidget( : QWidget(parent), model_note_(model_note), main_layout_(new QVBoxLayout(this)), - open_button_(new QPushButton("Открыть")), + open_button_(new QPushButton(tr("Открыть"))), number_of_theme(number_of_theme_) { this->setObjectName("NoteWidget"); this->setMinimumWidth(100); this->setFixedHeight(100); - title_label_ = new QLabel(model_note_->get_title().c_str(), this); - text_label_ = new QLabel(model_note_->get_text().c_str(), this); + title_label_ = new QLabel(QString::fromStdString(model_note_->get_title()), this); + text_label_ = new QLabel(QString::fromStdString(model_note_->get_text()), this); title_label_->setStyleSheet("color: rgb(33, 44, 50);"); text_label_->setStyleSheet("color: rgb(33, 44, 50);"); @@ -48,8 +48,8 @@ void NoteWidget::open_note_window() const { ); dialog->setAttribute(Qt::WA_DeleteOnClose); dialog->exec(); - text_label_->setText(model_note_->get_text().c_str()); - title_label_->setText(model_note_->get_title().c_str()); + text_label_->setText(QString::fromStdString(model_note_->get_text())); + title_label_->setText(QString::fromStdString(model_note_->get_title())); main_layout_->update(); } } // namespace Ui \ No newline at end of file diff --git a/ui/note-widget/include/note_edit_dialog_styles.h b/ui/note-widget/include/note_edit_dialog_styles.h index 636903c..385fea9 100644 --- a/ui/note-widget/include/note_edit_dialog_styles.h +++ b/ui/note-widget/include/note_edit_dialog_styles.h @@ -129,6 +129,7 @@ QString note_edit_dialog_light_autumn_theme = R"( QDateEdit#dateEdit::drop-down { border: none; width: 20px; + border-radius: 5px; } /* Окно с сообщением */ @@ -455,8 +456,8 @@ QString note_edit_dialog_light_purple_theme = R"( QDateEdit#dateEdit { font-family: 'Arial'; border-radius: 5px; - background-color: #ffdda2; - color: #050505; + background-color: #C98BB8; + color: rgb(42, 10, 25); padding: 5px 5px; border: none; width: 70px; @@ -622,8 +623,8 @@ QString note_edit_dialog_dark_purple_theme = R"( QDateEdit#dateEdit { font-family: 'Arial'; border-radius: 5px; - background-color: #ffdda2; - color: #050505; + background-color: rgb(113, 97, 137); + color: #221932; padding: 5px 5px; border: none; width: 70px; @@ -799,8 +800,8 @@ QString note_edit_dialog_blue_theme = R"( QDateEdit#dateEdit { font-family: 'Arial'; border-radius: 5px; - background-color: #ffdda2; - color: #050505; + background-color: rgb(61, 104, 122); + color: #BDD1BD; padding: 5px 5px; border: none; width: 70px; diff --git a/ui/note-widget/include/tags_dialog.h b/ui/note-widget/include/tags_dialog.h index f8496c0..03611a6 100644 --- a/ui/note-widget/include/tags_dialog.h +++ b/ui/note-widget/include/tags_dialog.h @@ -7,11 +7,16 @@ #include #include #include +#include +#include + class TagsDialog final : public QDialog { Q_OBJECT public: + const static std::vector THEMES; + void handle_theme_changed(int theme); const int MAX_TAGS_COUNT = 5; const std::pair DIALOG_SIZE = std::make_pair(300, 250); diff --git a/ui/note-widget/include/tags_dialog_styles.h b/ui/note-widget/include/tags_dialog_styles.h index 15fd320..b73854f 100644 --- a/ui/note-widget/include/tags_dialog_styles.h +++ b/ui/note-widget/include/tags_dialog_styles.h @@ -4,7 +4,7 @@ #include "tags_dialog.h" namespace Ui { -QString tags_dialog_light_theme = R"( +QString tags_dialog_light_autumn_theme = R"( QDialog { background-color: #f5f5f5; } @@ -14,6 +14,7 @@ QString tags_dialog_light_theme = R"( font-family: 'Arial'; color: #727272; spacing: 5px; + background-color: transparent; } QCheckBox::indicator { @@ -21,17 +22,15 @@ QString tags_dialog_light_theme = R"( height: 16px; border-radius: 3px; border: 1px solid #727272; - background-color: #ffffff; + background-color: transparent; } QCheckBox::indicator:checked { - background-color: #fea36b; - border: 1px solid #fea36b; - image: url(:/images/check.png); + background-color: #727272; } QCheckBox::indicator:hover { - border: 1px solid #fea36b; + background-color: rgb(33, 44, 50); } /* Выпадающие списки цветов */ @@ -108,14 +107,443 @@ QString tags_dialog_light_theme = R"( background-color: white; color: #fea36b; padding: 5px 10px; - font-weight: bold; + } + + QPushButton#cancel_button:hover { + background-color: #dadada; + } +)"; + +QString tags_dialog_dark_autumn_theme = R"( + QDialog { + background-color: #202020; + } + + /* Чекбоксы */ + QCheckBox { + font-family: 'Arial'; + color: #727272; + spacing: 5px; + background-color: transparent; + } + QCheckBox::indicator { + width: 16px; + height: 16px; + border-radius: 3px; + border: 1px solid #727272; + background-color: transparent; + } + QCheckBox::indicator:hover { + background-color: #727272; + } + QCheckBox::indicator:checked { + background-color:rgb(0, 0, 0); + } + + /* Выпадающие списки цветов */ + QComboBox { + font-family: 'Arial'; + border-radius: 10px; + background-color: #363636; + color: #BDD1BD; + padding: 5px 10px; + border: 1px solid #505050; + } + + QComboBox:hover { + border: 1px solid #fea36b; + } + + QComboBox::drop-down { + width: 20px; + border: none; + } + + QComboBox::down-arrow { + image: url(:/images/down_arrow_light.png); + } + + QComboBox QAbstractItemView { + background-color: #363636; + color: #BDD1BD; + selection-background-color: #089083; + selection-color: white; + border: 1px solid #505050; + border-radius: 5px; + } + + /* Поля ввода имени тега */ + QLineEdit { + font-family: 'Arial'; + border-radius: 10px; + background-color: #363636; + color: #BDD1BD; + padding: 5px 10px; + border: 1px solid #505050; + } + + QLineEdit:hover, + QLineEdit:focus { border: 1px solid #fea36b; + } + + QLineEdit::placeholder { + color: #727272; + } + + /* Кнопка OK */ + QPushButton#ok_button { + font-family: 'Arial'; + border-radius: 10px; + background-color: #fea36b; + color: #263238; + padding: 5px 10px; + font-weight: bold; width: 30px; height: 25px; } + QPushButton#ok_button:hover { + background-color: #d58745; + } + + /* Кнопка Отмена */ + QPushButton#cancel_button { + font-family: 'Arial'; + border-radius: 10px; + background-color: #089083; + color: white; + padding: 5px 10px; + } + QPushButton#cancel_button:hover { - background-color: #dadada; + background-color: #01635d; + } + +)"; + +QString tags_dialog_light_purple_theme = R"( + QDialog { + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, + stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(125, 109, 148)); + } + + /* Чекбоксы */ + QCheckBox { + font-family: 'Arial'; + color: rgb(42, 10, 25); + spacing: 5px; + background-color: transparent; + } + QCheckBox::indicator { + width: 16px; + height: 16px; + border-radius: 3px; + border: 1px solid rgb(42, 10, 25); + background-color: transparent; + } + QCheckBox::indicator:hover { + background-color: rgb(218, 207, 235); + } + QCheckBox::indicator:checked { + background-color: rgb(42, 10, 25); + } + + /* Выпадающие списки цветов */ + QComboBox { + font-family: 'Arial'; + border-radius: 10px; + background-color: #E8C9E1; + color: #221932; + padding: 5px 10px; + border: 1px solid #C98BB8; + } + + QComboBox:hover { + border: 1px solid #722548; + } + + QComboBox::drop-down { + width: 20px; + border: none; + } + + QComboBox::down-arrow { + image: url(:/images/down_arrow_purple.png); + } + + QComboBox QAbstractItemView { + background-color: #E8C9E1; + color: #221932; + selection-background-color: #722548; + selection-color: white; + border: 1px solid #C98BB8; + border-radius: 5px; + } + + /* Поля ввода имени тега */ + QLineEdit { + font-family: 'Arial'; + border-radius: 10px; + background-color: #E8C9E1; + color: #221932; + padding: 5px 10px; + border: 1px solid #C98BB8; + } + + QLineEdit:hover, + QLineEdit:focus { + border: 1px solid #722548; + } + + QLineEdit::placeholder { + color: #7A6A9A; + } + + /* Кнопка OK */ + QPushButton#ok_button { + font-family: 'Arial'; + border-radius: 10px; + background-color: #722548; + color: #E8C9E1; + padding: 5px 10px; + font-weight: bold; + width: 30px; + height: 25px; + } + + QPushButton#ok_button:hover { + background-color: #5A1538; + } + + /* Кнопка Отмена */ + QPushButton#cancel_button { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: rgb(218, 207, 235); + padding: 5px 10px; + } + + QPushButton#cancel_button:hover { + background-color: rgb(27, 6, 16); + } +)"; + +QString tags_dialog_dark_purple_theme = R"( + QDialog { + background-color: rgb(9, 6, 10); + } + + /* Чекбоксы */ + QCheckBox { + font-family: 'Arial'; + color: #9882B9; + spacing: 5px; + background-color: transparent; + } + QCheckBox::indicator { + width: 16px; + height: 16px; + border-radius: 3px; + border: 1px solid #9882B9; + background-color: transparent; + } + QCheckBox::indicator:hover { + background-color: #221932; + } + QCheckBox::indicator:checked { + background-color: #9882B9; + } + + /* Выпадающие списки цветов */ + QComboBox { + font-family: 'Arial'; + border-radius: 10px; + background-color: #322242; + color: #9882B9; + padding: 5px 10px; + border: 1px solid #775E88; + } + + QComboBox:hover { + border: 1px solid #722548; + } + + QComboBox::drop-down { + width: 20px; + border: none; + } + + QComboBox::down-arrow { + image: url(:/images/down_arrow_purple.png); + } + + QComboBox QAbstractItemView { + background-color: #322242; + color: #9882B9; + selection-background-color: #722548; + selection-color: white; + border: 1px solid #775E88; + border-radius: 5px; + } + + /* Поля ввода имени тега */ + QLineEdit { + font-family: 'Arial'; + border-radius: 10px; + background-color: #322242; + color: #9882B9; + padding: 5px 10px; + border: 1px solid #775E88; + } + + QLineEdit:hover, + QLineEdit:focus { + border: 1px solid #722548; + } + + QLineEdit::placeholder { + color: #7A6A9A; + } + + /* Кнопка OK */ + QPushButton#ok_button { + font-family: 'Arial'; + border-radius: 10px; + background-color: #722548; + color: rgb(9, 6, 10); + padding: 5px 10px; + font-weight: bold; + width: 30px; + height: 25px; + } + + QPushButton#ok_button:hover { + background-color: #5A1538; + } + + /* Кнопка Отмена */ + QPushButton#cancel_button { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: #9882B9; + padding: 5px 10px; + } + + QPushButton#cancel_button:hover { + background-color: rgb(27, 6, 16); + } +)"; + +QString tags_dialog_blue_theme = R"( + QDialog { + background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, + stop:0 #173C4C, stop:0.5 rgb(30, 66, 65), stop:1 #07142B); + } + + /* Чекбоксы */ + QCheckBox { + font-family: 'Arial'; + color: #BDD1BD; + spacing: 5px; + background-color: transparent; + } + QCheckBox::indicator { + width: 16px; + height: 16px; + border-radius: 3px; + border: 1px solid #BDD1BD; + background-color: transparent; + } + QCheckBox::indicator:hover { + background-color: #BDD1BD; + } + QCheckBox::indicator:checked { + background-color: #07142B; + } + + /* Выпадающие списки цветов */ + QComboBox { + font-family: 'Arial'; + border-radius: 10px; + background-color: #173C4C; + color: #BDD1BD; + padding: 5px 10px; + border: 1px solid #326D6C; + } + + QComboBox:hover { + border: 1px solid #568F7C; + } + + QComboBox::drop-down { + width: 20px; + border: none; + } + + QComboBox::down-arrow { + image: url(:/images/down_arrow_blue.png); + } + + QComboBox QAbstractItemView { + background-color: #173C4C; + color: #BDD1BD; + selection-background-color: #568F7C; + selection-color: white; + border: 1px solid #326D6C; + border-radius: 5px; + } + + /* Поля ввода имени тега */ + QLineEdit { + font-family: 'Arial'; + border-radius: 10px; + background-color: #173C4C; + color: #BDD1BD; + padding: 5px 10px; + border: 1px solid #326D6C; + } + + QLineEdit:hover, + QLineEdit:focus { + border: 1px solid #568F7C; + } + + QLineEdit::placeholder { + color: #7D9CAD; + } + + /* Кнопка OK */ + QPushButton#ok_button { + font-family: 'Arial'; + border-radius: 10px; + background-color: #568F7C; + color: #BDD1BD; + padding: 5px 10px; + font-weight: bold; + width: 30px; + height: 25px; + } + + QPushButton#ok_button:hover { + background-color: #326D6C; + } + + /* Кнопка Отмена */ + QPushButton#cancel_button { + font-family: 'Arial'; + border-radius: 10px; + background-color: #326D6C; + color: #BDD1BD; + padding: 5px 10px; + border: 1px solid #568F7C; + } + + QPushButton#cancel_button:hover { + background-color: #568F7C; + color: #07142B; } )"; } diff --git a/ui/note-widget/src/tags_dialog.cpp b/ui/note-widget/src/tags_dialog.cpp index 5a3d61e..c2805c9 100644 --- a/ui/note-widget/src/tags_dialog.cpp +++ b/ui/note-widget/src/tags_dialog.cpp @@ -3,6 +3,16 @@ #include #include #include "tags_dialog_styles.h" +#include "theme_manager.h" + + +const std::vector TagsDialog::THEMES = { + Ui::tags_dialog_light_autumn_theme, + Ui::tags_dialog_dark_autumn_theme, + Ui::tags_dialog_dark_purple_theme, + Ui::tags_dialog_light_purple_theme, + Ui::tags_dialog_blue_theme +}; TagsDialog::TagsDialog(const QList &initial_tags, QWidget *parent) : QDialog(parent) { @@ -23,7 +33,7 @@ TagsDialog::TagsDialog(const QList &initial_tags, QWidget *parent) setWindowTitle("Добавить теги"); setModal(true); setFixedSize(DIALOG_SIZE.first, DIALOG_SIZE.second); - setStyleSheet(Ui::tags_dialog_light_theme); + handle_theme_changed(ThemeManager::instance()->current_theme()); } void TagsDialog::setup_ui() { @@ -69,6 +79,12 @@ void TagsDialog::setup_ui() { connect( cancel_button_.get(), &QPushButton::clicked, this, &TagsDialog::reject ); + connect(ThemeManager::instance(), &ThemeManager::theme_changed, + this, &TagsDialog::handle_theme_changed); +} + +void TagsDialog::handle_theme_changed(int theme) { + this->setStyleSheet(THEMES[theme]); } QList TagsDialog::get_selected_tags() const { diff --git a/ui/profile-window/include/profile_window.h b/ui/profile-window/include/profile_window.h index 7f34b89..ed44537 100644 --- a/ui/profile-window/include/profile_window.h +++ b/ui/profile-window/include/profile_window.h @@ -22,6 +22,7 @@ class ProfileWindow : public QDialog { QString current_username; void setup_ui(QDialog* profile_window); + void switch_window(QWidget *new_window); public: explicit ProfileWindow(const QString& username, QWidget* parent = nullptr); diff --git a/ui/profile-window/include/profile_window_style_sheet.h b/ui/profile-window/include/profile_window_style_sheet.h index 63aba3e..50df3f1 100644 --- a/ui/profile-window/include/profile_window_style_sheet.h +++ b/ui/profile-window/include/profile_window_style_sheet.h @@ -208,7 +208,7 @@ QString profile_window_light_purple_theme = R"( } QPushButton#stats_button:hover { - background-color: rgb(19, 5, 11); + background-color: rgb(42, 10, 25); } QPushButton#stats_button:pressed { diff --git a/ui/profile-window/src/profile_window.cpp b/ui/profile-window/src/profile_window.cpp index 9f59435..538e71d 100644 --- a/ui/profile-window/src/profile_window.cpp +++ b/ui/profile-window/src/profile_window.cpp @@ -20,25 +20,27 @@ ProfileWindow::ProfileWindow(const QString& username, QWidget* parent) : QDialog(parent), current_username(username) { main_layout = new QVBoxLayout(this); - logout_button = new QPushButton("Выйти из аккаунта", this); + logout_button = new QPushButton(tr("Выйти из аккаунта"), this); logout_button->setObjectName("logout_button"); main_layout->addWidget(logout_button); - delete_button = new QPushButton("Удалить аккаунт", this); + delete_button = new QPushButton(tr("Удалить аккаунт"), this); delete_button->setObjectName("delete_button"); main_layout->addWidget(delete_button); QHBoxLayout* bottom_layout = new QHBoxLayout(); - stats_button = new QPushButton("Моя статистика", this); + stats_button = new QPushButton(tr("Моя статистика"), this); stats_button->setObjectName("stats_button"); bottom_layout->addWidget(stats_button); - settings_button = new QPushButton("⚙", this); + settings_button = new QPushButton(tr("⚙"), this); settings_button->setObjectName("settings_button"); settings_button->setFixedSize(45, 45); bottom_layout->addWidget(settings_button); + setWindowTitle(tr("Профиль")); + main_layout->addLayout(bottom_layout); setFixedSize(250, 160); @@ -75,40 +77,39 @@ void ProfileWindow::on_logout_clicked() { void ProfileWindow::on_delete_account_clicked() { QMessageBox::StandardButton reply = QMessageBox::question( this, - "Удаление аккаунта", - "Вы уверены, что хотите удалить аккаунт? Все данные будут потеряны!", + tr("Удаление аккаунта"), + tr("Вы уверены, что хотите удалить аккаунт? Все данные будут потеряны!"), QMessageBox::Yes | QMessageBox::No ); if (reply == QMessageBox::Yes && LRDao::try_delete_user(current_username)) { - QMessageBox::information(this, "Успех", "Аккаунт успешно удалён"); + QMessageBox::information(this, tr("Успех"), tr("Аккаунт успешно удалён")); emit delete_account_requested(); this->deleteLater(); } else if (reply == QMessageBox::Yes) { - QMessageBox::critical(this, "Ошибка", "Не удалось удалить аккаунт"); + QMessageBox::critical(this, tr("Ошибка"), tr("Не удалось удалить аккаунт")); } } void ProfileWindow::on_stats_clicked() { - this->setEnabled(false); AnalyticsWindow *new_analytics_window = new AnalyticsWindow(this->parentWidget()); - new_analytics_window->setAttribute(Qt::WA_DeleteOnClose); - connect(new_analytics_window, &AnalyticsWindow::destroyed, - this, [this]() { this->setEnabled(true); }); - new_analytics_window->show(); - new_analytics_window->raise(); - new_analytics_window->activateWindow(); + this->switch_window(new_analytics_window); } void ProfileWindow::on_settings_clicked() { - this->setEnabled(false); SettingsWindow *new_settings_window = new SettingsWindow(this->parentWidget()); - new_settings_window->setAttribute(Qt::WA_DeleteOnClose); - connect(new_settings_window, &SettingsWindow::destroyed, + this->switch_window(new_settings_window); +} + + +void ProfileWindow::switch_window(QWidget *new_window) { + this->setEnabled(false); + new_window->setAttribute(Qt::WA_DeleteOnClose); + connect(new_window, &AnalyticsWindow::destroyed, this, [this]() { this->setEnabled(true); }); - new_settings_window->show(); - new_settings_window->raise(); - new_settings_window->activateWindow(); + new_window->show(); + new_window->raise(); + new_window->activateWindow(); } } // namespace Ui \ No newline at end of file diff --git a/ui/settings-window/include/settings_window_style_sheet.h b/ui/settings-window/include/settings_window_style_sheet.h index 55aacc5..0c4bc68 100644 --- a/ui/settings-window/include/settings_window_style_sheet.h +++ b/ui/settings-window/include/settings_window_style_sheet.h @@ -16,7 +16,7 @@ namespace Ui { } QLabel#title_label { - font-size: 20px; + font-size: 28px; } QLabel#font_size_label { @@ -73,11 +73,10 @@ namespace Ui { background-color: transparent; } QRadioButton::indicator:hover { - border: 1px solid #fea36b; + background-color: #727272; } QRadioButton::indicator:checked { - background-color: #fea36b; - border: 1px solid #fea36b; + background-color: rgb(33, 44, 50); } )"; @@ -94,7 +93,7 @@ namespace Ui { } QLabel#title_label { - font-size: 20px; + font-size: 28px; } QLabel#font_size_label { @@ -149,11 +148,10 @@ namespace Ui { background-color: transparent; } QRadioButton::indicator:hover { - border: 1px solid #fea36b; + background-color: #727272; } QRadioButton::indicator:checked { - background-color: #fea36b; - border: 1px solid #fea36b; + background-color:rgb(0, 0, 0); } )"; @@ -171,7 +169,7 @@ namespace Ui { } QLabel#title_label { - font-size: 20px; + font-size: 28px; } QLabel#font_size_label { @@ -214,7 +212,7 @@ namespace Ui { QRadioButton { font-family: 'Arial'; - color: rgb(218, 207, 235); + color: rgb(42, 10, 25); spacing: 5px; background-color: transparent; } @@ -222,15 +220,14 @@ namespace Ui { width: 16px; height: 16px; border-radius: 3px; - border: 1px solid rgb(218, 207, 235); + border: 1px solid rgb(42, 10, 25); background-color: transparent; } QRadioButton::indicator:hover { - border: 1px solid #722548; + background-color: rgb(42, 10, 25); } QRadioButton::indicator:checked { - background-color: #722548; - border: 1px solid #722548; + background-color: rgb(218, 207, 235); } )"; @@ -247,7 +244,7 @@ namespace Ui { } QLabel#title_label { - font-size: 20px; + font-size: 28px; } QLabel#font_size_label { @@ -302,11 +299,10 @@ namespace Ui { background-color: transparent; } QRadioButton::indicator:hover { - border: 1px solid #722548; + background-color: #221932; } QRadioButton::indicator:checked { - background-color: #722548; - border: 1px solid #722548; + background-color: #9882B9; } )"; @@ -323,7 +319,7 @@ namespace Ui { } QLabel#title_label { - font-size: 20px; + font-size: 28px; } QLabel#font_size_label { @@ -379,11 +375,10 @@ namespace Ui { background-color: transparent; } QRadioButton::indicator:hover { - border: 1px solid #568F7C; + background-color: #BDD1BD; } QRadioButton::indicator:checked { - background-color: #568F7C; - border: 1px solid #568F7C; + background-color: #07142B; } )"; diff --git a/ui/settings-window/src/settings_window.cpp b/ui/settings-window/src/settings_window.cpp index 5bb4b40..82a9318 100644 --- a/ui/settings-window/src/settings_window.cpp +++ b/ui/settings-window/src/settings_window.cpp @@ -13,30 +13,30 @@ const std::vector SettingsWindow::THEMES = { SettingsWindow::SettingsWindow(QWidget *parent) : QDialog(parent) { main_layout = new QVBoxLayout(this); - title_label = new QLabel("Настройки", this); + title_label = new QLabel(tr("Настройки"), this); title_label->setObjectName("title_label"); title_label->setAlignment(Qt::AlignCenter); main_layout->addWidget(title_label); QHBoxLayout *buttons_layout = new QHBoxLayout(); - language_button = new QPushButton("RU", this); + language_button = new QPushButton(tr("RU"), this); language_button->setObjectName("language_button"); - theme_button = new QPushButton("Тема", this); + theme_button = new QPushButton(tr("Тема"), this); theme_button->setObjectName("theme_button"); buttons_layout->addWidget(language_button); buttons_layout->addWidget(theme_button); main_layout->addLayout(buttons_layout); - font_size_label = new QLabel("Размер шрифта", this); + font_size_label = new QLabel(tr("Размер шрифта"), this); main_layout->addWidget(font_size_label); QButtonGroup *font_group = new QButtonGroup(this); - small_font_radio = new QRadioButton("Мелкий", this); - medium_font_radio = new QRadioButton("Средний", this); - large_font_radio = new QRadioButton("Крупный", this); + small_font_radio = new QRadioButton(tr("Мелкий"), this); + medium_font_radio = new QRadioButton(tr("Средний"), this); + large_font_radio = new QRadioButton(tr("Крупный"), this); font_group->addButton(small_font_radio); font_group->addButton(medium_font_radio); @@ -56,16 +56,19 @@ SettingsWindow::SettingsWindow(QWidget *parent) : QDialog(parent) { connect(large_font_radio, &QRadioButton::clicked, this, &SettingsWindow::set_large_font); connect(ThemeManager::instance(), &ThemeManager::theme_changed, this, &SettingsWindow::handle_theme_changed); - - title_label->setText("Настройки"); - font_size_label->setText("Размер шрифта"); - theme_button->setText("Тема"); - small_font_radio->setText("Мелкий"); - medium_font_radio->setText("Средний"); - large_font_radio->setText("Крупный"); + title_label->setText(tr("Настройки")); + font_size_label->setText(tr("Размер шрифта")); + theme_button->setText(tr("Тема")); + small_font_radio->setText(tr("Мелкий")); + medium_font_radio->setText(tr("Средний")); + large_font_radio->setText(tr("Крупный")); + + language_button->setText(tr("RU")); + setWindowTitle(tr("Настройки")); + setLayout(main_layout); - setFixedSize(240, 260); + setFixedSize(240, 240); handle_theme_changed(ThemeManager::instance()->current_theme()); } @@ -74,7 +77,11 @@ void SettingsWindow::handle_theme_changed(int theme) { } void SettingsWindow::toggle_language() { - + if (language_button->text() == tr("RU")) { + language_button->setText(tr("EN")); + } else { + language_button->setText(tr("RU")); + } } void SettingsWindow::toggle_theme() { From 1a0d8142b127bdbf2d01aee4c52f406adcf4b4fd Mon Sep 17 00:00:00 2001 From: MuravAna Date: Mon, 19 May 2025 02:27:36 +0300 Subject: [PATCH 11/17] Add ability to change font-size in all windows via settings --- .gitignore | 1 + CMakeLists.txt | 4 +- main.cpp | 4 +- translations/app_en.ts | 0 translations/app_ru.ts | 0 ui/analytics-window/CMakeLists.txt | 2 +- .../include/analytics_window.h | 1 + .../include/analytics_window_style_sheet.h | 10 +-- ui/analytics-window/src/analytics_window.cpp | 30 +++++++-- ui/authorization-windows/CMakeLists.txt | 2 +- ui/authorization-windows/src/login_window.cpp | 10 +-- .../src/registration_window.cpp | 10 +-- ui/main-window/CMakeLists.txt | 2 +- ui/main-window/include/main_window_style.hpp | 29 +++++---- ui/main-window/include/mainwindow.h | 2 + ui/main-window/include/notewidget.h | 1 + ui/main-window/src/mainwindow.cpp | 32 +++++++++- ui/main-window/src/notewidget.cpp | 25 +++++++- ui/note-widget/CMakeLists.txt | 2 +- ui/note-widget/include/note_edit_dialog.h | 1 + ui/note-widget/src/note_edit_dialog.cpp | 42 +++++++++++-- ui/note-widget/src/tags_dialog.cpp | 7 ++- ui/profile-window/CMakeLists.txt | 2 +- ui/profile-window/include/profile_window.h | 5 +- ui/profile-window/src/profile_window.cpp | 31 +++++++-- ui/settings-window/CMakeLists.txt | 2 +- ui/settings-window/include/settings_window.h | 5 +- ui/settings-window/src/settings_window.cpp | 63 +++++++++++++++---- .../CMakeLists.txt | 12 ++-- ui/style-manager/include/style_manager.h | 33 ++++++++++ ui/style-manager/src/style_manager.cpp | 37 +++++++++++ ui/theme-manager/include/theme_manager.h | 28 --------- ui/theme-manager/src/theme_manager.cpp | 27 -------- 33 files changed, 320 insertions(+), 142 deletions(-) create mode 100644 translations/app_en.ts create mode 100644 translations/app_ru.ts rename ui/{theme-manager => style-manager}/CMakeLists.txt (59%) create mode 100644 ui/style-manager/include/style_manager.h create mode 100644 ui/style-manager/src/style_manager.cpp delete mode 100644 ui/theme-manager/include/theme_manager.h delete mode 100644 ui/theme-manager/src/theme_manager.cpp diff --git a/.gitignore b/.gitignore index 973087b..77e4c99 100644 --- a/.gitignore +++ b/.gitignore @@ -13,6 +13,7 @@ protobuf/ *.o *.obj *.app +translations/*.qm moc_*.cpp ui_*.h diff --git a/CMakeLists.txt b/CMakeLists.txt index b495766..0b4bc18 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -29,7 +29,7 @@ add_subdirectory(ui/profile-window) add_subdirectory(ui/main-window) add_subdirectory(ui/authorization-windows) add_subdirectory(ui/note-widget) -add_subdirectory(ui/theme-manager) +add_subdirectory(ui/style-manager) add_subdirectory(ui/settings-window) add_subdirectory(ui/analytics-window) add_subdirectory(proto) @@ -44,7 +44,7 @@ target_link_libraries(EfficioTaskTracker PRIVATE efficio-rpc Database Scripts - ThemeManager + StyleManager AuthorizationWindows ProfileWindow MainWindow diff --git a/main.cpp b/main.cpp index 6b77343..08bc756 100644 --- a/main.cpp +++ b/main.cpp @@ -5,7 +5,7 @@ #include #include "applicationwindow.h" #include "login_window.h" -#include "theme_manager.h" +#include "style_manager.h" #include int main(int argc, char *argv[]) { @@ -30,7 +30,7 @@ int main(int argc, char *argv[]) { app.installTranslator(&qtTranslator); } - ThemeManager* themeManager = ThemeManager::instance(); + StyleManager* StyleManager = StyleManager::instance(); QMainWindow *app_window = new QMainWindow(); app_window->setWindowTitle("EFFICIO"); diff --git a/translations/app_en.ts b/translations/app_en.ts new file mode 100644 index 0000000..e69de29 diff --git a/translations/app_ru.ts b/translations/app_ru.ts new file mode 100644 index 0000000..e69de29 diff --git a/ui/analytics-window/CMakeLists.txt b/ui/analytics-window/CMakeLists.txt index 6d49ed1..c977927 100644 --- a/ui/analytics-window/CMakeLists.txt +++ b/ui/analytics-window/CMakeLists.txt @@ -34,7 +34,7 @@ target_link_libraries(AnalyticsWindow Qt6::Gui Qt6::Sql Database - ThemeManager + StyleManager PUBLIC Qt6::Widgets Qt6::Charts diff --git a/ui/analytics-window/include/analytics_window.h b/ui/analytics-window/include/analytics_window.h index b052775..b43f388 100644 --- a/ui/analytics-window/include/analytics_window.h +++ b/ui/analytics-window/include/analytics_window.h @@ -19,6 +19,7 @@ class AnalyticsWindow : public QDialog void setTasksData(int created, int completed, int overdue); void setProjectsData(const QMap& projects); void handle_theme_changed(int theme); + void handle_font_size_changed(std::string font_size); void on_switch_theme_clicked(); static const std::vector THEMES; diff --git a/ui/analytics-window/include/analytics_window_style_sheet.h b/ui/analytics-window/include/analytics_window_style_sheet.h index 124c75a..fb146a7 100644 --- a/ui/analytics-window/include/analytics_window_style_sheet.h +++ b/ui/analytics-window/include/analytics_window_style_sheet.h @@ -9,7 +9,7 @@ const QString analytics_window_light_autumn_theme = R"( #AnalyticsWindow { background-color: #f5f5f5; color: #444444; - font-family: "Segoe UI"; + font-family: 'Arial'; } QTabWidget::pane { @@ -83,7 +83,7 @@ const QString analytics_window_dark_autumn_theme = R"( #AnalyticsWindow { background-color: #202020; color: #BDD1BD; - font-family: "Segoe UI"; + font-family: 'Arial'; } QTabWidget::pane { @@ -157,7 +157,7 @@ const QString analytics_window_light_purple_theme = R"( #AnalyticsWindow { background-color: #9882B9; color: rgb(42, 10, 25); - font-family: "Segoe UI"; + font-family: 'Arial'; } QTabWidget::pane { @@ -231,7 +231,7 @@ const QString analytics_window_dark_purple_theme = R"( #AnalyticsWindow { background-color: #221932; color: #9882B9; - font-family: "Segoe UI"; + font-family: 'Arial'; } QTabWidget::pane { @@ -305,7 +305,7 @@ const QString analytics_window_blue_theme = R"( #AnalyticsWindow { background-color: #07142B; color: #BDD1BD; - font-family: "Segoe UI"; + font-family: 'Arial'; } QTabWidget::pane { diff --git a/ui/analytics-window/src/analytics_window.cpp b/ui/analytics-window/src/analytics_window.cpp index 69f1d3e..e29f8c9 100644 --- a/ui/analytics-window/src/analytics_window.cpp +++ b/ui/analytics-window/src/analytics_window.cpp @@ -1,5 +1,5 @@ #include "analytics_window.h" -#include "theme_manager.h" +#include "style_manager.h" #include "analytics_window_style_sheet.h" #include @@ -40,9 +40,29 @@ AnalyticsWindow::AnalyticsWindow(QWidget *parent) QMap projects; setProjectsData(projects); - connect(ThemeManager::instance(), &ThemeManager::theme_changed, + connect(StyleManager::instance(), &StyleManager::theme_changed, this, &AnalyticsWindow::handle_theme_changed); - handle_theme_changed(ThemeManager::instance()->current_theme()); + handle_theme_changed(StyleManager::instance()->current_theme()); + connect(StyleManager::instance(), &StyleManager::font_size_changed, + this, &AnalyticsWindow::handle_font_size_changed + ); + handle_font_size_changed(StyleManager::instance()->current_font_size()); +} + +void AnalyticsWindow::handle_font_size_changed(std::string font_size) { + + QString font_size_rule; + if(font_size == "small") { + font_size_rule = "QPushButton { font-size: 11px; }"; + } + else if(font_size == "medium") { + font_size_rule = "QPushButton { font-size: 13px; }"; + } + else if(font_size == "big") { + font_size_rule = "QPushButton { font-size: 15px; }"; + } + + this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_size_rule); } void AnalyticsWindow::handle_theme_changed(int theme) { @@ -50,8 +70,8 @@ void AnalyticsWindow::handle_theme_changed(int theme) { } void AnalyticsWindow::on_switch_theme_clicked() { - int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; - ThemeManager::instance()->apply_theme(next_theme); + int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; + StyleManager::instance()->apply_theme(next_theme); } AnalyticsWindow::~AnalyticsWindow(){} diff --git a/ui/authorization-windows/CMakeLists.txt b/ui/authorization-windows/CMakeLists.txt index 6096233..c2e2d58 100644 --- a/ui/authorization-windows/CMakeLists.txt +++ b/ui/authorization-windows/CMakeLists.txt @@ -41,4 +41,4 @@ target_include_directories(AuthorizationWindows $ ) -target_link_libraries(AuthorizationWindows PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts MainWindow ThemeManager ProfileWindow) \ No newline at end of file +target_link_libraries(AuthorizationWindows PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts MainWindow StyleManager ProfileWindow) \ No newline at end of file diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index 2662084..9d223d5 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -5,7 +5,7 @@ #include "registration_window.h" #include "login_window_style_sheet.h" #include "serialization.hpp" -#include "theme_manager.h" +#include "style_manager.h" #include #include @@ -32,10 +32,10 @@ LoginWindow::LoginWindow(QWidget *parent) &LoginWindow::on_switch_mode_clicked); connect(ui->push_enter, &QPushButton::clicked, this, &LoginWindow::on_push_enter_clicked); - connect(ThemeManager::instance(), &ThemeManager::theme_changed, + connect(StyleManager::instance(), &StyleManager::theme_changed, this, &LoginWindow::handle_theme_changed); - handle_theme_changed(ThemeManager::instance()->current_theme()); + handle_theme_changed(StyleManager::instance()->current_theme()); } void LoginWindow::handle_theme_changed(int theme) { @@ -44,8 +44,8 @@ void LoginWindow::handle_theme_changed(int theme) { void LoginWindow::on_switch_theme_clicked() { if ((this->counter_on_switch_theme_clicks++) % 2) { - int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; - ThemeManager::instance()->apply_theme(next_theme); + int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; + StyleManager::instance()->apply_theme(next_theme); } } diff --git a/ui/authorization-windows/src/registration_window.cpp b/ui/authorization-windows/src/registration_window.cpp index 6afce75..0fbdfd8 100644 --- a/ui/authorization-windows/src/registration_window.cpp +++ b/ui/authorization-windows/src/registration_window.cpp @@ -3,7 +3,7 @@ #include #include "lr_dao.hpp" #include "login_window.h" -#include "theme_manager.h" +#include "style_manager.h" #include "registration_window_style_sheet.h" const std::vector RegistrationWindow::THEMES = { @@ -33,10 +33,10 @@ RegistrationWindow::RegistrationWindow(QWidget *parent) &RegistrationWindow::on_push_registration_clicked, Qt::UniqueConnection); connect(ui->switch_mode, &QPushButton::clicked, this, &RegistrationWindow::on_switch_mode_clicked, Qt::UniqueConnection); - connect(ThemeManager::instance(), &ThemeManager::theme_changed, + connect(StyleManager::instance(), &StyleManager::theme_changed, this, &RegistrationWindow::handle_theme_changed); - handle_theme_changed(ThemeManager::instance()->current_theme()); + handle_theme_changed(StyleManager::instance()->current_theme()); } void RegistrationWindow::handle_theme_changed(int theme) { @@ -45,8 +45,8 @@ void RegistrationWindow::handle_theme_changed(int theme) { void RegistrationWindow::on_switch_theme_clicked() { if ((this->counter_on_switch_theme_clicks++)%2) { - int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; - ThemeManager::instance()->apply_theme(next_theme); + int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; + StyleManager::instance()->apply_theme(next_theme); } } diff --git a/ui/main-window/CMakeLists.txt b/ui/main-window/CMakeLists.txt index bd562c4..8afb56f 100644 --- a/ui/main-window/CMakeLists.txt +++ b/ui/main-window/CMakeLists.txt @@ -36,7 +36,7 @@ target_link_libraries(MainWindow PRIVATE Scripts Database NoteWidget - ThemeManager + StyleManager ProfileWindow AuthorizationWindows ) \ No newline at end of file diff --git a/ui/main-window/include/main_window_style.hpp b/ui/main-window/include/main_window_style.hpp index 532e157..6d79340 100644 --- a/ui/main-window/include/main_window_style.hpp +++ b/ui/main-window/include/main_window_style.hpp @@ -162,9 +162,8 @@ QPushButton { border-radius: 10px; background-color: #fea36b; color: white; - padding: 5px 10px; - min-width: 60px; - min-height: 25px; + padding: 10px 10px; + min-width: 40px; } QPushButton::hover { @@ -357,9 +356,9 @@ QString main_window_dark_autumn_theme = R"( border-radius: 10px; background-color:rgb(211, 139, 95); color: #263238; - padding: 5px 10px; - min-width: 60px; - min-height: 25px; + padding: 10px 10px; + min-width: 40px; + } QPushButton:hover { @@ -553,9 +552,9 @@ QPushButton { border-radius: 10px; background-color: #722548; color: #9882B9; - padding: 5px 10px; - min-width: 60px; - min-height: 25px; + padding: 10px 10px; + min-width: 40px; + } QPushButton:hover { @@ -747,9 +746,9 @@ QPushButton { border-radius: 10px; background-color: #722548; color: #060407; - padding: 5px 10px; - min-width: 60px; - min-height: 25px; + padding: 10px 10px; + min-width: 40px; + } QPushButton:hover { @@ -943,9 +942,9 @@ QPushButton { border-radius: 10px; background-color: #568F7C; color: #07142B; - padding: 5px 10px; - min-width: 60px; - min-height: 25px; + padding: 10px 10px; + min-width: 40px; + border: none; } diff --git a/ui/main-window/include/mainwindow.h b/ui/main-window/include/mainwindow.h index d02ae82..608007c 100644 --- a/ui/main-window/include/mainwindow.h +++ b/ui/main-window/include/mainwindow.h @@ -23,6 +23,7 @@ namespace Ui { class MainWindow : public QWidget { Q_OBJECT std::string username; + std::string font_size_ = "medium"; QVBoxLayout *main_layout_; BottomBar *top_bar_; QHBoxLayout *content_layout_; @@ -52,6 +53,7 @@ private slots: void on_logout_button_click(); void on_delete_account_button_click(); void handle_theme_changed(int theme); + void handle_font_size_changed(std::string font_size_); }; } // namespace Ui #endif // MAINWINDOW_H \ No newline at end of file diff --git a/ui/main-window/include/notewidget.h b/ui/main-window/include/notewidget.h index 959eb5d..fb2b646 100644 --- a/ui/main-window/include/notewidget.h +++ b/ui/main-window/include/notewidget.h @@ -24,6 +24,7 @@ class NoteWidget : public QWidget { int number_of_theme_ = 0 ); int number_of_theme; + void handle_font_size_changed(std::string font_size_); private slots: diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index 2156cb5..c7163bc 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -23,9 +23,11 @@ #include "project_dao.hpp" #include "projectitem.h" #include "projectlist.h" -#include "theme_manager.h" +#include "style_manager.h" #include "registration_window.h" #include "login_window.h" +#include +#include namespace Ui { @@ -88,10 +90,18 @@ MainWindow::MainWindow( this, &MainWindow::on_profile_button_click ); connect( - ThemeManager::instance(), &ThemeManager::theme_changed, + StyleManager::instance(), &StyleManager::theme_changed, this, &MainWindow::handle_theme_changed ); - handle_theme_changed(ThemeManager::instance()->current_theme()); + connect( + StyleManager::instance(), &StyleManager::font_size_changed, + this, &MainWindow::handle_font_size_changed + ); + handle_theme_changed(StyleManager::instance()->current_theme()); + connect(StyleManager::instance(), &StyleManager::font_size_changed, + this, &Ui::MainWindow::handle_font_size_changed + ); + handle_font_size_changed(StyleManager::instance()->current_font_size()); } void MainWindow::on_delete_account_button_click() { @@ -108,6 +118,22 @@ void MainWindow::handle_theme_changed(int theme) { this->setStyleSheet(THEMES[theme]); } +void MainWindow::handle_font_size_changed(std::string font_size_) { + + QString font_rule; + if (font_size_ == "small") { + font_rule = "#ProjectList, #BottomBar QLabel, #BottomBar QPushButton, #NoteWidget QPushButton, QPushButton { font-size: 11px; }"; + } + else if (font_size_ == "medium") { + font_rule = "#ProjectList, #BottomBar QLabel, #BottomBar QPushButton, #NoteWidget QPushButton, QPushButton { font-size: 13px; }"; + } + else if (font_size_ == "big") { + font_rule = "#ProjectList, #BottomBar QLabel, #BottomBar QPushButton, #NoteWidget QPushButton, QPushButton { font-size: 15px; }"; + } + + this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_rule); +} + void MainWindow::on_profile_button_click() { this->setEnabled(false); ProfileWindow *new_profile_window = new ProfileWindow(QString::fromStdString(this->username), this->parentWidget()); diff --git a/ui/main-window/src/notewidget.cpp b/ui/main-window/src/notewidget.cpp index c5ee584..629d6b4 100644 --- a/ui/main-window/src/notewidget.cpp +++ b/ui/main-window/src/notewidget.cpp @@ -4,6 +4,7 @@ #include #include "note.hpp" #include "note_edit_dialog.h" +#include "style_manager.h" namespace Ui { NoteWidget::NoteWidget( @@ -22,8 +23,8 @@ NoteWidget::NoteWidget( title_label_ = new QLabel(QString::fromStdString(model_note_->get_title()), this); text_label_ = new QLabel(QString::fromStdString(model_note_->get_text()), this); - title_label_->setStyleSheet("color: rgb(33, 44, 50);"); - text_label_->setStyleSheet("color: rgb(33, 44, 50);"); + title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); + text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); main_layout_->addWidget(title_label_); main_layout_->addWidget(text_label_); @@ -37,10 +38,30 @@ NoteWidget::NoteWidget( connect( open_button_, &QPushButton::clicked, this, &NoteWidget::open_note_window ); + connect( + StyleManager::instance(), &StyleManager::font_size_changed, + this, &NoteWidget::handle_font_size_changed + ); this->setLayout(main_layout_); this->setAttribute(Qt::WA_StyledBackground); } +void NoteWidget::handle_font_size_changed(std::string font_size_){ + QString font_rule; + if (font_size_ == "small") { + title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 13px;"); + text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 11px;"); + } + else if (font_size_ == "medium") { + title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); + text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 13px;"); + } + else if (font_size_ == "big") { + title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 17px;"); + text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); + } +} + void NoteWidget::open_note_window() const { auto dialog = new ::NoteEditDialog( const_cast(qobject_cast(this)), diff --git a/ui/note-widget/CMakeLists.txt b/ui/note-widget/CMakeLists.txt index a76f171..ff54b3c 100644 --- a/ui/note-widget/CMakeLists.txt +++ b/ui/note-widget/CMakeLists.txt @@ -37,4 +37,4 @@ target_include_directories(NoteWidget $ ) -target_link_libraries(NoteWidget PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts ThemeManager) \ No newline at end of file +target_link_libraries(NoteWidget PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts StyleManager) \ No newline at end of file diff --git a/ui/note-widget/include/note_edit_dialog.h b/ui/note-widget/include/note_edit_dialog.h index 204f15a..1bb99ad 100644 --- a/ui/note-widget/include/note_edit_dialog.h +++ b/ui/note-widget/include/note_edit_dialog.h @@ -29,6 +29,7 @@ class NoteEditDialog final : public QDialog { ~NoteEditDialog() override; static const std::vector THEMES; void handle_theme_changed(int theme); + void handle_font_size_changed(std::string font_size); private slots: void on_save_button_click(); diff --git a/ui/note-widget/src/note_edit_dialog.cpp b/ui/note-widget/src/note_edit_dialog.cpp index 664a043..31c4264 100644 --- a/ui/note-widget/src/note_edit_dialog.cpp +++ b/ui/note-widget/src/note_edit_dialog.cpp @@ -10,7 +10,7 @@ #include "./ui_note_edit_dialog.h" #include "note_edit_dialog_styles.h" #include "tags_dialog.h" -#include "theme_manager.h" +#include "style_manager.h" const std::vector NoteEditDialog::THEMES = { @@ -33,7 +33,8 @@ NoteEditDialog::NoteEditDialog(QWidget* parent, Note* note) setup_connections(); setup_ui(); - handle_theme_changed(ThemeManager::instance()->current_theme()); + handle_theme_changed(StyleManager::instance()->current_theme()); + handle_font_size_changed(StyleManager::instance()->current_font_size()); } @@ -48,8 +49,8 @@ void NoteEditDialog::init_basic_fields() { void NoteEditDialog::on_switch_theme_button_click() { - int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; - ThemeManager::instance()->apply_theme(next_theme); + int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; + StyleManager::instance()->apply_theme(next_theme); } @@ -105,14 +106,43 @@ void NoteEditDialog::setup_connections() { connect(ui_->switch_theme, &QPushButton::clicked, this, &NoteEditDialog::on_switch_theme_button_click ); - connect(ThemeManager::instance(), &ThemeManager::theme_changed, + connect(StyleManager::instance(), &StyleManager::theme_changed, this, &NoteEditDialog::handle_theme_changed); connect(ui_->addTagsButton, &QPushButton::clicked, this, &NoteEditDialog::on_add_tags_button_click); + connect(StyleManager::instance(), &StyleManager::font_size_changed, + this, &NoteEditDialog::handle_font_size_changed + ); +} + +void NoteEditDialog::handle_font_size_changed(std::string font_size_) { + QString current_style = this->styleSheet(); + + QString font_rules; + if(font_size_ == "small") { + font_rules = + "QLineEdit#titleLineEdit { font-size: 20px; }" + "QLabel#projectNameLabel { font-size: 11px; }" + "QLabel#descriptionLabel { font-size: 14px; }" + "QLabel#sidePanelLabel, QLabel#sidePanelLabel_2 { font-size: 12px; }" + "QMessageBox QLabel { font-size: 12px; }" + "QMessageBox QPushButton { font-size: 11px; }"; + } + else if(font_size_ == "big") { + font_rules = + "QLineEdit#titleLineEdit { font-size: 30px; }" + "QLabel#projectNameLabel { font-size: 16px; }" + "QLabel#descriptionLabel { font-size: 21px; }" + "QLabel#sidePanelLabel, QLabel#sidePanelLabel_2 { font-size: 17px; }" + "QMessageBox QLabel { font-size: 17px; }" + "QMessageBox QPushButton { font-size: 16px; }"; + } + + this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_rules); } void NoteEditDialog::setup_ui() { setFixedSize(700, 480); - setStyleSheet(THEMES[ThemeManager::instance()->current_theme()]); + setStyleSheet(THEMES[StyleManager::instance()->current_theme()]); ui_->buttonsLayout->setAlignment(Qt::AlignLeft); } diff --git a/ui/note-widget/src/tags_dialog.cpp b/ui/note-widget/src/tags_dialog.cpp index c2805c9..544145a 100644 --- a/ui/note-widget/src/tags_dialog.cpp +++ b/ui/note-widget/src/tags_dialog.cpp @@ -3,7 +3,7 @@ #include #include #include "tags_dialog_styles.h" -#include "theme_manager.h" +#include "style_manager.h" const std::vector TagsDialog::THEMES = { @@ -33,7 +33,8 @@ TagsDialog::TagsDialog(const QList &initial_tags, QWidget *parent) setWindowTitle("Добавить теги"); setModal(true); setFixedSize(DIALOG_SIZE.first, DIALOG_SIZE.second); - handle_theme_changed(ThemeManager::instance()->current_theme()); + handle_theme_changed(StyleManager::instance()->current_theme()); + } void TagsDialog::setup_ui() { @@ -79,7 +80,7 @@ void TagsDialog::setup_ui() { connect( cancel_button_.get(), &QPushButton::clicked, this, &TagsDialog::reject ); - connect(ThemeManager::instance(), &ThemeManager::theme_changed, + connect(StyleManager::instance(), &StyleManager::theme_changed, this, &TagsDialog::handle_theme_changed); } diff --git a/ui/profile-window/CMakeLists.txt b/ui/profile-window/CMakeLists.txt index b378586..cf9dade 100644 --- a/ui/profile-window/CMakeLists.txt +++ b/ui/profile-window/CMakeLists.txt @@ -34,7 +34,7 @@ target_link_libraries(ProfileWindow PRIVATE Qt6::Gui Qt6::Sql Database - ThemeManager + StyleManager AuthorizationWindows SettingsWindow AnalyticsWindow diff --git a/ui/profile-window/include/profile_window.h b/ui/profile-window/include/profile_window.h index ed44537..8011c5d 100644 --- a/ui/profile-window/include/profile_window.h +++ b/ui/profile-window/include/profile_window.h @@ -5,7 +5,7 @@ #include #include #include -#include "theme_manager.h" +#include "style_manager.h" #include QT_BEGIN_NAMESPACE @@ -28,8 +28,9 @@ class ProfileWindow : public QDialog { explicit ProfileWindow(const QString& username, QWidget* parent = nullptr); ~ProfileWindow() = default; - static const std::vector themes; + static const std::vector THEMES; void handle_theme_changed(int theme); + void handle_font_size_changed(std::string font_size); friend class MainWindow; signals: diff --git a/ui/profile-window/src/profile_window.cpp b/ui/profile-window/src/profile_window.cpp index 538e71d..f5b0742 100644 --- a/ui/profile-window/src/profile_window.cpp +++ b/ui/profile-window/src/profile_window.cpp @@ -8,7 +8,7 @@ namespace Ui { -const std::vector ProfileWindow::themes = { +const std::vector ProfileWindow::THEMES = { profile_window_light_autumn_theme, profile_window_dark_autumn_theme, profile_window_dark_purple_theme, @@ -34,7 +34,7 @@ ProfileWindow::ProfileWindow(const QString& username, QWidget* parent) stats_button->setObjectName("stats_button"); bottom_layout->addWidget(stats_button); - settings_button = new QPushButton(tr("⚙"), this); + settings_button = new QPushButton("⚙", this); settings_button->setObjectName("settings_button"); settings_button->setFixedSize(45, 45); bottom_layout->addWidget(settings_button); @@ -59,14 +59,35 @@ ProfileWindow::ProfileWindow(const QString& username, QWidget* parent) connect(settings_button, &QPushButton::clicked, this, &Ui::ProfileWindow::on_settings_clicked ); - connect(ThemeManager::instance(), &ThemeManager::theme_changed, + connect(StyleManager::instance(), &StyleManager::theme_changed, this, &Ui::ProfileWindow::handle_theme_changed ); - handle_theme_changed(ThemeManager::instance()->current_theme()); + handle_theme_changed(StyleManager::instance()->current_theme()); + connect(StyleManager::instance(), &StyleManager::font_size_changed, + this, &Ui::ProfileWindow::handle_font_size_changed + ); + handle_font_size_changed(StyleManager::instance()->current_font_size()); } +void ProfileWindow::handle_font_size_changed(std::string font_size) { + + QString font_rule; + if(font_size == "small") { + font_rule = "QPushButton { font-size: 11px; }"; + } + else if(font_size == "medium") { + font_rule = "QPushButton { font-size: 13px; }"; + } + else if(font_size == "big") { + font_rule = "QPushButton { font-size: 15px; }"; + } + + this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_rule); +} + + void ProfileWindow::handle_theme_changed(int theme) { - setStyleSheet(themes[theme]); + setStyleSheet(THEMES[theme]); } void ProfileWindow::on_logout_clicked() { diff --git a/ui/settings-window/CMakeLists.txt b/ui/settings-window/CMakeLists.txt index bac1da2..25e29c4 100644 --- a/ui/settings-window/CMakeLists.txt +++ b/ui/settings-window/CMakeLists.txt @@ -34,6 +34,6 @@ target_link_libraries(SettingsWindow PRIVATE Qt6::Gui Qt6::Sql Database - ThemeManager + StyleManager AuthorizationWindows ) \ No newline at end of file diff --git a/ui/settings-window/include/settings_window.h b/ui/settings-window/include/settings_window.h index f06da7e..a847cea 100644 --- a/ui/settings-window/include/settings_window.h +++ b/ui/settings-window/include/settings_window.h @@ -15,7 +15,8 @@ class SettingsWindow : public QDialog { public: explicit SettingsWindow(QWidget *parent = nullptr); - void handle_theme_changed(int theme); + void handle_theme_changed(int theme_); + void handle_font_size_changed(std::string font_size_); static const std::vector THEMES; private slots: @@ -23,7 +24,7 @@ private slots: void toggle_theme(); void set_small_font(); void set_medium_font(); - void set_large_font(); + void set_big_font(); private: void update_ui_text(); diff --git a/ui/settings-window/src/settings_window.cpp b/ui/settings-window/src/settings_window.cpp index 82a9318..2dd67a6 100644 --- a/ui/settings-window/src/settings_window.cpp +++ b/ui/settings-window/src/settings_window.cpp @@ -1,6 +1,7 @@ #include "settings_window.h" #include "settings_window_style_sheet.h" -#include "theme_manager.h" +#include "style_manager.h" +#include const std::vector SettingsWindow::THEMES = { Ui::settings_window_light_autumn_theme, @@ -53,10 +54,12 @@ SettingsWindow::SettingsWindow(QWidget *parent) : QDialog(parent) { connect(theme_button, &QPushButton::clicked, this, &SettingsWindow::toggle_theme); connect(small_font_radio, &QRadioButton::clicked, this, &SettingsWindow::set_small_font); connect(medium_font_radio, &QRadioButton::clicked, this, &SettingsWindow::set_medium_font); - connect(large_font_radio, &QRadioButton::clicked, this, &SettingsWindow::set_large_font); - connect(ThemeManager::instance(), &ThemeManager::theme_changed, + connect(large_font_radio, &QRadioButton::clicked, this, &SettingsWindow::set_big_font); + connect(StyleManager::instance(), &StyleManager::theme_changed, this, &SettingsWindow::handle_theme_changed); - + connect(StyleManager::instance(), &StyleManager::font_size_changed, + this, &SettingsWindow::handle_font_size_changed + ); title_label->setText(tr("Настройки")); font_size_label->setText(tr("Размер шрифта")); theme_button->setText(tr("Тема")); @@ -68,12 +71,40 @@ SettingsWindow::SettingsWindow(QWidget *parent) : QDialog(parent) { setWindowTitle(tr("Настройки")); setLayout(main_layout); - setFixedSize(240, 240); - handle_theme_changed(ThemeManager::instance()->current_theme()); + setFixedSize(250, 250); + handle_theme_changed(StyleManager::instance()->current_theme()); + + handle_font_size_changed(StyleManager::instance()->current_font_size()); } -void SettingsWindow::handle_theme_changed(int theme) { - this->setStyleSheet(THEMES[theme]); +void SettingsWindow::handle_font_size_changed(std::string font_size) { + QString font_rule; + if(font_size == "small") { + font_rule = + "QPushButton#language_button, QPushButton#theme_button { font-size: 12px; }" + "QWidget { font-size: 12px; }" + "QLabel#title_label { font-size: 23px; }" + "QLabel#font_size_label { font-size: 30px; }"; + } + else if(font_size == "medium") { + font_rule = + "QPushButton#language_button, QPushButton#theme_button { font-size: 15px; }" + "QWidget { font-size: 15px; }" + "QLabel#title_label { font-size: 28px; }" + "QLabel#font_size_label { font-size: 35px; }"; + } + else if(font_size == "big") { + font_rule = + "QPushButton#language_button, QPushButton#theme_button { font-size: 18px; }" + "QWidget { font-size: 18px; }" + "QLabel#title_label { font-size: 32px; }" + "QLabel#font_size_label { font-size: 40px; }"; + } + this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_rule); +} + +void SettingsWindow::handle_theme_changed(int theme_) { + this->setStyleSheet(THEMES[theme_]); } void SettingsWindow::toggle_language() { @@ -85,10 +116,16 @@ void SettingsWindow::toggle_language() { } void SettingsWindow::toggle_theme() { - int next_theme = (ThemeManager::instance()->current_theme() + 1) % 5; - ThemeManager::instance()->apply_theme(next_theme); + int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; + StyleManager::instance()->apply_theme(next_theme); } -void SettingsWindow::set_small_font() { qApp->setStyleSheet("QWidget { font-size: 12px; }"); } -void SettingsWindow::set_medium_font() { qApp->setStyleSheet("QWidget { font-size: 16px; }"); } -void SettingsWindow::set_large_font() { qApp->setStyleSheet("QWidget { font-size: 20px; }"); } \ No newline at end of file +void SettingsWindow::set_small_font() { + StyleManager::instance()->apply_font_size("small"); + } +void SettingsWindow::set_medium_font() { + StyleManager::instance()->apply_font_size("medium"); + } +void SettingsWindow::set_big_font() { + StyleManager::instance()->apply_font_size("big"); + } \ No newline at end of file diff --git a/ui/theme-manager/CMakeLists.txt b/ui/style-manager/CMakeLists.txt similarity index 59% rename from ui/theme-manager/CMakeLists.txt rename to ui/style-manager/CMakeLists.txt index a290e94..1706ec9 100644 --- a/ui/theme-manager/CMakeLists.txt +++ b/ui/style-manager/CMakeLists.txt @@ -1,6 +1,6 @@ cmake_minimum_required(VERSION 3.16) -project(ThemeManager LANGUAGES CXX) +project(StyleManager LANGUAGES CXX) set(CMAKE_CXX_STANDARD 20) set(CMAKE_CXX_STANDARD_REQUIRED ON) @@ -13,20 +13,20 @@ set(CMAKE_AUTORCC ON) set(SOURCES - src/theme_manager.cpp + src/style_manager.cpp ) set(HEADERS - include/theme_manager.h + include/style_manager.h ) -add_library(ThemeManager STATIC ${SOURCES} ${HEADERS}) +add_library(StyleManager STATIC ${SOURCES} ${HEADERS}) -target_include_directories(ThemeManager +target_include_directories(StyleManager PUBLIC $ $ ) -target_link_libraries(ThemeManager PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts) +target_link_libraries(StyleManager PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts) diff --git a/ui/style-manager/include/style_manager.h b/ui/style-manager/include/style_manager.h new file mode 100644 index 0000000..cd513ea --- /dev/null +++ b/ui/style-manager/include/style_manager.h @@ -0,0 +1,33 @@ +#ifndef style_manager_H +#define style_manager_H + +#include +#include +#include +#include +#include +#include + +class StyleManager : public QObject { + Q_OBJECT + +public: + static StyleManager* instance(); + + void apply_theme(int theme); + void apply_font_size(std::string font_size_); + int current_theme() const; + std::string current_font_size() const; + +signals: + void theme_changed(int new_theme); + void font_size_changed(std::string new_font_size_); + +private: + explicit StyleManager(QObject *parent = nullptr); + static StyleManager* m_instance; + int current_theme_; + std::string current_font_size_; +}; + +#endif // style_manager_H \ No newline at end of file diff --git a/ui/style-manager/src/style_manager.cpp b/ui/style-manager/src/style_manager.cpp new file mode 100644 index 0000000..0dc6ca4 --- /dev/null +++ b/ui/style-manager/src/style_manager.cpp @@ -0,0 +1,37 @@ +#include "style_manager.h" +#include +#include +#include + +StyleManager* StyleManager::m_instance = nullptr; + +StyleManager::StyleManager(QObject *parent) + : QObject(parent) { + current_theme_ = 0; + emit theme_changed(this->current_theme_); +} + +StyleManager* StyleManager::instance() { + if (!m_instance) { + m_instance = new StyleManager(); + } + return m_instance; +} + +void StyleManager::apply_theme(int theme) { + this->current_theme_ = theme; + emit theme_changed(this->current_theme_); +} + +int StyleManager::current_theme() const { + return current_theme_; +} + +void StyleManager::apply_font_size(std::string font_size_) { + this->current_font_size_ = font_size_; + emit font_size_changed(this->current_font_size_); +} + +std::string StyleManager::current_font_size() const { + return this->current_font_size_; +} \ No newline at end of file diff --git a/ui/theme-manager/include/theme_manager.h b/ui/theme-manager/include/theme_manager.h deleted file mode 100644 index 2a24aaf..0000000 --- a/ui/theme-manager/include/theme_manager.h +++ /dev/null @@ -1,28 +0,0 @@ -#ifndef THEME_MANAGER_H -#define THEME_MANAGER_H - -#include -#include -#include -#include -#include - -class ThemeManager : public QObject { - Q_OBJECT - -public: - static ThemeManager* instance(); - - void apply_theme(int theme); - int current_theme() const; - -signals: - void theme_changed(int new_theme); - -private: - explicit ThemeManager(QObject *parent = nullptr); - static ThemeManager* m_instance; - int current_theme_; -}; - -#endif // THEME_MANAGER_H \ No newline at end of file diff --git a/ui/theme-manager/src/theme_manager.cpp b/ui/theme-manager/src/theme_manager.cpp deleted file mode 100644 index 6a34df6..0000000 --- a/ui/theme-manager/src/theme_manager.cpp +++ /dev/null @@ -1,27 +0,0 @@ -#include "theme_manager.h" -#include -#include - -ThemeManager* ThemeManager::m_instance = nullptr; - -ThemeManager::ThemeManager(QObject *parent) - : QObject(parent) { - current_theme_ = 0; - emit theme_changed(this->current_theme_); -} - -ThemeManager* ThemeManager::instance() { - if (!m_instance) { - m_instance = new ThemeManager(); - } - return m_instance; -} - -void ThemeManager::apply_theme(int theme) { - this->current_theme_ = theme; - emit theme_changed(this->current_theme_); -} - -int ThemeManager::current_theme() const { - return current_theme_; -} \ No newline at end of file From be5f98522e3191f63d341d1acf6949cc3c639d8e Mon Sep 17 00:00:00 2001 From: MuravAna Date: Mon, 19 May 2025 14:53:22 +0300 Subject: [PATCH 12/17] Add ability to change language in all windows --- CMakeLists.txt | 16 +-- main.cpp | 4 +- translations/app_en.ts | 0 translations/app_ru.ts | 0 ui/analytics-window/CMakeLists.txt | 1 + .../include/analytics_window.h | 1 + ui/analytics-window/src/analytics_window.cpp | 42 ++++++ ui/authorization-windows/CMakeLists.txt | 2 +- .../include/login_window.h | 1 + .../include/registration_window.h | 1 + ui/authorization-windows/src/login_window.cpp | 72 +++++++--- .../src/registration_window.cpp | 128 ++++++++++++------ ui/language-manager/CMakeLists.txt | 32 +++++ .../include/language_manager.h | 29 ++++ ui/language-manager/src/language_manager.cpp | 28 ++++ ui/main-window/CMakeLists.txt | 1 + ui/main-window/include/mainwindow.h | 1 + ui/main-window/include/notewidget.h | 1 + ui/main-window/src/mainwindow.cpp | 19 ++- ui/main-window/src/notewidget.cpp | 34 ++++- ui/note-widget/CMakeLists.txt | 2 +- ui/note-widget/include/note_edit_dialog.h | 1 + ui/note-widget/include/tags_dialog.h | 1 + ui/note-widget/src/note_edit_dialog.cpp | 61 ++++++++- ui/note-widget/src/tags_dialog.cpp | 48 ++++++- ui/profile-window/CMakeLists.txt | 1 + ui/profile-window/include/profile_window.h | 1 + ui/profile-window/src/profile_window.cpp | 22 +++ ui/settings-window/CMakeLists.txt | 1 + ui/settings-window/include/settings_window.h | 1 + ui/settings-window/src/settings_window.cpp | 31 +++++ ui/style-manager/include/style_manager.h | 5 +- 32 files changed, 498 insertions(+), 90 deletions(-) delete mode 100644 translations/app_en.ts delete mode 100644 translations/app_ru.ts create mode 100644 ui/language-manager/CMakeLists.txt create mode 100644 ui/language-manager/include/language_manager.h create mode 100644 ui/language-manager/src/language_manager.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index 0b4bc18..b8ae4ca 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -9,19 +9,7 @@ set(CMAKE_AUTOUIC ON) set(CMAKE_CXX_STANDARD 20) set(CMAKE_CXX_STANDARD_REQUIRED ON) -find_package(Qt6 COMPONENTS Widgets LinguistTools Core Gui Sql REQUIRED) - -set(TS_FILES - translations/app_ru.ts - translations/app_en.ts -) - -qt_add_translation(QM_FILES ${TS_FILES}) - -qt_add_resources(PROJECT_RESOURCES - PREFIX "/translations" - FILES ${QM_FILES} -) +find_package(Qt6 COMPONENTS Widgets Core Gui Sql REQUIRED) add_subdirectory(scripts) add_subdirectory(database) @@ -32,6 +20,7 @@ add_subdirectory(ui/note-widget) add_subdirectory(ui/style-manager) add_subdirectory(ui/settings-window) add_subdirectory(ui/analytics-window) +add_subdirectory(ui/language-manager) add_subdirectory(proto) add_executable(EfficioTaskTracker main.cpp) @@ -45,6 +34,7 @@ target_link_libraries(EfficioTaskTracker PRIVATE Database Scripts StyleManager + LanguageManager AuthorizationWindows ProfileWindow MainWindow diff --git a/main.cpp b/main.cpp index 08bc756..f16cc7c 100644 --- a/main.cpp +++ b/main.cpp @@ -6,6 +6,7 @@ #include "applicationwindow.h" #include "login_window.h" #include "style_manager.h" +#include "language_manager.h" #include int main(int argc, char *argv[]) { @@ -30,7 +31,8 @@ int main(int argc, char *argv[]) { app.installTranslator(&qtTranslator); } - StyleManager* StyleManager = StyleManager::instance(); + StyleManager* style_manager = StyleManager::instance(); + LanguageManager* language_manager = LanguageManager::instance(); QMainWindow *app_window = new QMainWindow(); app_window->setWindowTitle("EFFICIO"); diff --git a/translations/app_en.ts b/translations/app_en.ts deleted file mode 100644 index e69de29..0000000 diff --git a/translations/app_ru.ts b/translations/app_ru.ts deleted file mode 100644 index e69de29..0000000 diff --git a/ui/analytics-window/CMakeLists.txt b/ui/analytics-window/CMakeLists.txt index c977927..9c3798e 100644 --- a/ui/analytics-window/CMakeLists.txt +++ b/ui/analytics-window/CMakeLists.txt @@ -35,6 +35,7 @@ target_link_libraries(AnalyticsWindow Qt6::Sql Database StyleManager + LanguageManager PUBLIC Qt6::Widgets Qt6::Charts diff --git a/ui/analytics-window/include/analytics_window.h b/ui/analytics-window/include/analytics_window.h index b43f388..aee1065 100644 --- a/ui/analytics-window/include/analytics_window.h +++ b/ui/analytics-window/include/analytics_window.h @@ -20,6 +20,7 @@ class AnalyticsWindow : public QDialog void setProjectsData(const QMap& projects); void handle_theme_changed(int theme); void handle_font_size_changed(std::string font_size); + void handle_language_changed(std::string new_language); void on_switch_theme_clicked(); static const std::vector THEMES; diff --git a/ui/analytics-window/src/analytics_window.cpp b/ui/analytics-window/src/analytics_window.cpp index e29f8c9..3ea1b96 100644 --- a/ui/analytics-window/src/analytics_window.cpp +++ b/ui/analytics-window/src/analytics_window.cpp @@ -1,5 +1,6 @@ #include "analytics_window.h" #include "style_manager.h" +#include "language_manager.h" #include "analytics_window_style_sheet.h" #include @@ -47,6 +48,47 @@ AnalyticsWindow::AnalyticsWindow(QWidget *parent) this, &AnalyticsWindow::handle_font_size_changed ); handle_font_size_changed(StyleManager::instance()->current_font_size()); + + connect(LanguageManager::instance(), &LanguageManager::language_changed, + this, &AnalyticsWindow::handle_language_changed + ); + handle_language_changed(LanguageManager::instance()->current_language()); +} + + +void AnalyticsWindow::handle_language_changed(std::string new_language) { + if (new_language == "RU") { + tab_widget->setTabText(0, tr("Статистика задач")); + tab_widget->setTabText(1, tr("Распределение по проектам")); + setWindowTitle(tr("Аналитическая панель")); + + QChart *tasks_chart = static_cast(tasks_layout->itemAt(0)->widget())->chart(); + tasks_chart->setTitle(tr("Статистика задач за период")); + static_cast(tasks_chart->axes(Qt::Vertical)[0])->setTitleText(tr("Количество")); + + QBarSeries *tasks_series = static_cast(tasks_chart->series()[0]); + static_cast(tasks_series->barSets()[0])->setLabel(tr("Создано")); + static_cast(tasks_series->barSets()[1])->setLabel(tr("Завершено")); + static_cast(tasks_series->barSets()[2])->setLabel(tr("Просрочено")); + + button_box->button(QDialogButtonBox::Close)->setText(tr("Закрыть")); + } + else if(new_language == "EN") { + tab_widget->setTabText(0, tr("Tasks Statistics")); + tab_widget->setTabText(1, tr("Projects Distribution")); + setWindowTitle(tr("Analytics Panel")); + + QChart *tasks_chart = static_cast(tasks_layout->itemAt(0)->widget())->chart(); + tasks_chart->setTitle(tr("Tasks Statistics for Period")); + static_cast(tasks_chart->axes(Qt::Vertical)[0])->setTitleText(tr("Count")); + + QBarSeries *tasks_series = static_cast(tasks_chart->series()[0]); + static_cast(tasks_series->barSets()[0])->setLabel(tr("Created")); + static_cast(tasks_series->barSets()[1])->setLabel(tr("Completed")); + static_cast(tasks_series->barSets()[2])->setLabel(tr("Overdue")); + + button_box->button(QDialogButtonBox::Close)->setText(tr("Close")); + } } void AnalyticsWindow::handle_font_size_changed(std::string font_size) { diff --git a/ui/authorization-windows/CMakeLists.txt b/ui/authorization-windows/CMakeLists.txt index c2e2d58..566818b 100644 --- a/ui/authorization-windows/CMakeLists.txt +++ b/ui/authorization-windows/CMakeLists.txt @@ -41,4 +41,4 @@ target_include_directories(AuthorizationWindows $ ) -target_link_libraries(AuthorizationWindows PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts MainWindow StyleManager ProfileWindow) \ No newline at end of file +target_link_libraries(AuthorizationWindows PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database LanguageManager Scripts MainWindow StyleManager ProfileWindow) \ No newline at end of file diff --git a/ui/authorization-windows/include/login_window.h b/ui/authorization-windows/include/login_window.h index 2c5d7e3..ee74dae 100644 --- a/ui/authorization-windows/include/login_window.h +++ b/ui/authorization-windows/include/login_window.h @@ -21,6 +21,7 @@ class LoginWindow : public QWidget static const std::vector THEMES; void handle_theme_changed(int theme); + void handle_language_changed(std::string new_language); private slots: void on_switch_mode_clicked(); diff --git a/ui/authorization-windows/include/registration_window.h b/ui/authorization-windows/include/registration_window.h index 671bd41..5002971 100644 --- a/ui/authorization-windows/include/registration_window.h +++ b/ui/authorization-windows/include/registration_window.h @@ -17,6 +17,7 @@ class RegistrationWindow : public QWidget { bool is_strong_and_valid_password(const QString &password); static const std::vector THEMES; void handle_theme_changed(int theme); + void handle_language_changed(std::string new_language); private slots: void on_switch_mode_clicked(); diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index 9d223d5..a2641ec 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -6,6 +6,7 @@ #include "login_window_style_sheet.h" #include "serialization.hpp" #include "style_manager.h" +#include "language_manager.h" #include #include @@ -36,8 +37,30 @@ LoginWindow::LoginWindow(QWidget *parent) this, &LoginWindow::handle_theme_changed); handle_theme_changed(StyleManager::instance()->current_theme()); + connect(LanguageManager::instance(), &LanguageManager::language_changed, + this, &LoginWindow::handle_language_changed + ); + handle_language_changed(LanguageManager::instance()->current_language()); } +void LoginWindow::handle_language_changed(std::string new_language) { + if (new_language == "RU") { + ui->input_login->setPlaceholderText(tr("Введите логин:")); + ui->input_password->setPlaceholderText(tr("Введите пароль:")); + ui->switch_mode->setText(tr("Еще нет аккаунта? Зарегестрируйтесь!")); + ui->switch_theme->setText(tr("Тема")); + ui->push_enter->setText(tr("Войти")); + } + else if (new_language == "EN") { + ui->input_login->setPlaceholderText(tr("Enter login:")); + ui->input_password->setPlaceholderText(tr("Enter password:")); + ui->switch_mode->setText(tr("Don't have an account yet? Register!")); + ui->switch_theme->setText(tr("Theme")); + ui->push_enter->setText(tr("Login")); + } +} + + void LoginWindow::handle_theme_changed(int theme) { this->setStyleSheet(THEMES[theme]); } @@ -58,44 +81,54 @@ void LoginWindow::on_switch_mode_clicked() { this->close(); } } - void LoginWindow::on_push_enter_clicked() { if ((this->counter_on_switch_theme_clicks++) % 2) { - // QString login = ui->input_login->text().trimmed(); - // QString password = ui->input_password->text(); + QString login = ui->input_login->text().trimmed(); + QString password = ui->input_password->text(); + std::string lang = LanguageManager::instance()->current_language(); // if (login.isEmpty() || password.isEmpty()) { - // QMessageBox::warning(this, - // tr("Ошибка ввода данных"), - // tr("Пожалуйста, заполните все поля!")); + // if (lang == "RU") { + // QMessageBox::warning(this, "Ошибка ввода данных", "Пожалуйста, заполните все поля!"); + // } else { + // QMessageBox::warning(this, "Input Error", "Please fill in all the fields!"); + // } // return; // } // if (login.size() > 50) { - // QMessageBox::warning(this, - // tr("Ошибка"), - // tr("Длина логина не должна превышать пятидесяти символов")); + // if (lang == "RU") { + // QMessageBox::warning(this, "Ошибка", "Длина логина не должна превышать пятидесяти символов"); + // } else { + // QMessageBox::warning(this, "Error", "Login must not exceed fifty characters"); + // } // return; // } // if (password.size() > 50) { - // QMessageBox::warning(this, - // tr("Ошибка"), - // tr("Длина пароля не должна превышать пятидесяти символов")); + // if (lang == "RU") { + // QMessageBox::warning(this, "Ошибка", "Длина пароля не должна превышать пятидесяти символов"); + // } else { + // QMessageBox::warning(this, "Error", "Password must not exceed fifty characters"); + // } // return; // } // if (!LRDao::validate_user(login, password)) { - // QMessageBox::warning(this, - // tr("Ошибка ввода данных"), - // tr("Неверный логин или пароль!")); + // if (lang == "RU") { + // QMessageBox::warning(this, "Ошибка ввода данных", "Неверный логин или пароль!"); + // } else { + // QMessageBox::warning(this, "Login Error", "Incorrect login or password!"); + // } // return; // } - // QMessageBox::information(this, - // tr("Вход"), - // tr("Вы успешно вошли! Добро пожаловать :)")); - QString login = "user"; + if (lang == "RU") { + QMessageBox::information(this, "Вход", "Вы успешно вошли. Добро пожаловать!"); + } else { + QMessageBox::information(this, "Login", "You have successfully logged in. Welcome!"); + } + if (QMainWindow *app_window = qobject_cast(this->parentWidget())) { this->deleteLater(); project_storage_model::Storage *storage = new project_storage_model::Storage(); @@ -116,6 +149,7 @@ void LoginWindow::on_push_enter_clicked() { } } + void LoginWindow::switch_window(QMainWindow *app_window, QWidget *new_window, int width, int height) { if (QWidget *old = app_window->centralWidget()) { old->deleteLater(); diff --git a/ui/authorization-windows/src/registration_window.cpp b/ui/authorization-windows/src/registration_window.cpp index 0fbdfd8..9db5a3c 100644 --- a/ui/authorization-windows/src/registration_window.cpp +++ b/ui/authorization-windows/src/registration_window.cpp @@ -4,6 +4,7 @@ #include "lr_dao.hpp" #include "login_window.h" #include "style_manager.h" +#include "language_manager.h" #include "registration_window_style_sheet.h" const std::vector RegistrationWindow::THEMES = { @@ -37,8 +38,33 @@ RegistrationWindow::RegistrationWindow(QWidget *parent) this, &RegistrationWindow::handle_theme_changed); handle_theme_changed(StyleManager::instance()->current_theme()); + connect(LanguageManager::instance(), &LanguageManager::language_changed, + this, &RegistrationWindow::handle_language_changed + ); + handle_language_changed(LanguageManager::instance()->current_language()); } +void RegistrationWindow::handle_language_changed(std::string new_language) { + if (new_language == "RU") { + ui->create_login->setPlaceholderText(tr("Введите логин:")); + ui->create_password->setPlaceholderText(tr("Введите пароль:")); + ui->repeat_password->setPlaceholderText(tr("Повторите пароль:")); + ui->switch_mode->setText(tr("Уже есть аккаунт? Войдите!")); + ui->switch_theme->setText(tr("Тема")); + ui->push_registration->setText(tr("Already have an account? Login!")); + } + else if (new_language == "EN") { + ui->create_login->setPlaceholderText(tr("Enter login:")); + ui->create_password->setPlaceholderText(tr("Enter password:")); + ui->repeat_password->setPlaceholderText(tr("Repeat password:")); + ui->switch_mode->setText(tr("Back")); + ui->switch_theme->setText(tr("Theme")); + ui->push_registration->setText(tr("Register")); + } +} + + + void RegistrationWindow::handle_theme_changed(int theme) { this->setStyleSheet(THEMES[theme]); } @@ -72,11 +98,14 @@ void RegistrationWindow::on_switch_mode_clicked() { } bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { + std::string lang = LanguageManager::instance()->current_language(); + if (password.length() < 8) { - QMessageBox::warning( - nullptr, tr("Ошибка: недостаточно надежный пароль"), - tr("Пароль должен содержать не менее восьми символов") - ); + if (lang == "RU") { + QMessageBox::warning(nullptr, "Ошибка: недостаточно надежный пароль", "Пароль должен содержать не менее восьми символов"); + } else { + QMessageBox::warning(nullptr, "Error: Weak Password", "Password must be at least 8 characters long"); + } return false; } @@ -85,10 +114,11 @@ bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { for (const QChar &ch : password) { if (!ch.isLetter() && !ch.isDigit()) { - QMessageBox::warning( - nullptr, tr("Ошибка"), - tr("Пароль должен содержать только символы латиницы и цифры") - ); + if (lang == "RU") { + QMessageBox::warning(nullptr, "Ошибка", "Пароль должен содержать только символы латиницы и цифры"); + } else { + QMessageBox::warning(nullptr, "Error", "Password must contain only Latin letters and digits"); + } return false; } else if (ch.isLetter()) { has_latin_letter = true; @@ -98,17 +128,20 @@ bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { } if (!has_latin_letter) { - QMessageBox::warning( - nullptr, tr("Ошибка: недостаточно надежный пароль"), - tr("Пароль должен содержать хотя бы одну букву") - ); + if (lang == "RU") { + QMessageBox::warning(nullptr, "Ошибка: недостаточно надежный пароль", "Пароль должен содержать хотя бы одну букву"); + } else { + QMessageBox::warning(nullptr, "Error: Weak Password", "Password must contain at least one letter"); + } return false; } + if (!has_digit) { - QMessageBox::warning( - nullptr, tr("Ошибка: недостаточно надежный пароль"), - tr("Пароль должен содержать хотя бы одну цифру") - ); + if (lang == "RU") { + QMessageBox::warning(nullptr, "Ошибка: недостаточно надежный пароль", "Пароль должен содержать хотя бы одну цифру"); + } else { + QMessageBox::warning(nullptr, "Error: Weak Password", "Password must contain at least one digit"); + } return false; } @@ -116,34 +149,46 @@ bool RegistrationWindow::is_strong_and_valid_password(const QString &password) { } void RegistrationWindow::on_push_registration_clicked() { - if ((this->counter_on_switch_theme_clicks++)%2) { + if ((this->counter_on_switch_theme_clicks++) % 2) { QString created_login = ui->create_login->text().trimmed(); QString created_password = ui->create_password->text(); QString repeated_password = ui->repeat_password->text(); + std::string lang = LanguageManager::instance()->current_language(); + if (created_login.isEmpty() || created_password.isEmpty() || repeated_password.isEmpty()) { - QMessageBox::warning(this, tr("Ошибка"), tr("Пожалуйста, заполните все поля.")); + if (lang == "RU") { + QMessageBox::warning(this, "Ошибка", "Пожалуйста, заполните все поля."); + } else { + QMessageBox::warning(this, "Error", "Please fill in all the fields."); + } return; } if (created_password != repeated_password) { - QMessageBox::warning(this, tr("Ошибка"), tr("Пароли не совпадают!")); + if (lang == "RU") { + QMessageBox::warning(this, "Ошибка", "Пароли не совпадают!"); + } else { + QMessageBox::warning(this, "Error", "Passwords do not match!"); + } return; } if (created_login.size() > 50) { - QMessageBox::warning( - this, tr("Ошибка"), - tr("Длина логина не должна превышать пятидесяти символов") - ); + if (lang == "RU") { + QMessageBox::warning(this, "Ошибка", "Длина логина не должна превышать пятидесяти символов"); + } else { + QMessageBox::warning(this, "Error", "Login must not exceed fifty characters."); + } return; } if (created_password.size() > 50) { - QMessageBox::warning( - this, tr("Ошибка"), - tr("Длина пароля не должна превышать пятидесяти символов") - ); + if (lang == "RU") { + QMessageBox::warning(this, "Ошибка", "Длина пароля не должна превышать пятидесяти символов"); + } else { + QMessageBox::warning(this, "Error", "Password must not exceed fifty characters."); + } return; } @@ -154,24 +199,27 @@ void RegistrationWindow::on_push_registration_clicked() { int try_register_user = LRDao::try_register_user(created_login, created_password); switch (try_register_user) { case 0: - QMessageBox::warning( - this, tr("Ошибка"), - tr("Извините, внутренняя ошибка с базами данных.") - ); + if (lang == "RU") { + QMessageBox::warning(this, "Ошибка", "Извините, внутренняя ошибка с базами данных."); + } else { + QMessageBox::warning(this, "Error", "Sorry, an internal database error occurred."); + } break; case -1: - QMessageBox::warning( - this, tr("Ошибка"), - tr("Пользователь с таким именем уже существует. Пожалуйста, придумайте другое!") - ); + if (lang == "RU") { + QMessageBox::warning(this, "Ошибка", "Пользователь с таким именем уже существует. Пожалуйста, придумайте другое!"); + } else { + QMessageBox::warning(this, "Error", "A user with this name already exists. Please choose a different one!"); + } break; default: - QMessageBox::information( - this, tr("Регистрация"), - tr("Вы успешно зарегистрировались! Пожалуйста, выполните вход.") - ); + if (lang == "RU") { + QMessageBox::information(this, "Регистрация", "Вы успешно зарегистрировались! Пожалуйста, выполните вход."); + } else { + QMessageBox::information(this, "Registration", "You have successfully registered! Please log in."); + } on_switch_mode_clicked(); break; } } -} \ No newline at end of file +} diff --git a/ui/language-manager/CMakeLists.txt b/ui/language-manager/CMakeLists.txt new file mode 100644 index 0000000..151f92e --- /dev/null +++ b/ui/language-manager/CMakeLists.txt @@ -0,0 +1,32 @@ +cmake_minimum_required(VERSION 3.16) + +project(LanguageManager LANGUAGES CXX) + +set(CMAKE_CXX_STANDARD 20) +set(CMAKE_CXX_STANDARD_REQUIRED ON) + +find_package(Qt6 COMPONENTS Core Gui Widgets Core Gui Sql REQUIRED) + +set(CMAKE_AUTOMOC ON) +set(CMAKE_AUTOUIC ON) +set(CMAKE_AUTORCC ON) + + +set(SOURCES + src/language_manager.cpp +) + +set(HEADERS + include/language_manager.h +) + +add_library(LanguageManager STATIC ${SOURCES} ${HEADERS}) + +target_include_directories(LanguageManager + PUBLIC + $ + $ +) + +target_link_libraries(LanguageManager PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts) + diff --git a/ui/language-manager/include/language_manager.h b/ui/language-manager/include/language_manager.h new file mode 100644 index 0000000..88ee68d --- /dev/null +++ b/ui/language-manager/include/language_manager.h @@ -0,0 +1,29 @@ +#ifndef style_manager_H +#define style_manager_H + +#include +#include +#include +#include +#include +#include + +class LanguageManager : public QObject { + Q_OBJECT + +public: + static LanguageManager* instance(); + + void apply_language(std::string new_language_); + std::string current_language() const; + +signals: + void language_changed(std::string new_language_); + +private: + explicit LanguageManager(QObject *parent = nullptr); + static LanguageManager* m_instance; + std::string current_language_; +}; + +#endif // style_manager_H \ No newline at end of file diff --git a/ui/language-manager/src/language_manager.cpp b/ui/language-manager/src/language_manager.cpp new file mode 100644 index 0000000..f0b52ea --- /dev/null +++ b/ui/language-manager/src/language_manager.cpp @@ -0,0 +1,28 @@ +#include "language_manager.h" +#include +#include +#include + +LanguageManager* LanguageManager::m_instance = nullptr; + +LanguageManager::LanguageManager(QObject *parent) + : QObject(parent) { + std::string language = "RU"; + apply_language(language); +} + +LanguageManager* LanguageManager::instance() { + if (!m_instance) { + m_instance = new LanguageManager(); + } + return m_instance; +} + +void LanguageManager::apply_language(std::string new_language_) { + this->current_language_ = new_language_; + emit language_changed(this->current_language_); +} + +std::string LanguageManager::current_language() const { + return current_language_; +} \ No newline at end of file diff --git a/ui/main-window/CMakeLists.txt b/ui/main-window/CMakeLists.txt index 8afb56f..c36aa37 100644 --- a/ui/main-window/CMakeLists.txt +++ b/ui/main-window/CMakeLists.txt @@ -39,4 +39,5 @@ target_link_libraries(MainWindow PRIVATE StyleManager ProfileWindow AuthorizationWindows + LanguageManager ) \ No newline at end of file diff --git a/ui/main-window/include/mainwindow.h b/ui/main-window/include/mainwindow.h index 608007c..31207fc 100644 --- a/ui/main-window/include/mainwindow.h +++ b/ui/main-window/include/mainwindow.h @@ -53,6 +53,7 @@ private slots: void on_logout_button_click(); void on_delete_account_button_click(); void handle_theme_changed(int theme); + void handle_language_changed(std::string new_language); void handle_font_size_changed(std::string font_size_); }; } // namespace Ui diff --git a/ui/main-window/include/notewidget.h b/ui/main-window/include/notewidget.h index fb2b646..d7c28b9 100644 --- a/ui/main-window/include/notewidget.h +++ b/ui/main-window/include/notewidget.h @@ -25,6 +25,7 @@ class NoteWidget : public QWidget { ); int number_of_theme; void handle_font_size_changed(std::string font_size_); + void handle_language_changed(std::string new_language); private slots: diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index c7163bc..1f95a61 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -24,6 +24,7 @@ #include "projectitem.h" #include "projectlist.h" #include "style_manager.h" +#include "language_manager.h" #include "registration_window.h" #include "login_window.h" #include @@ -47,7 +48,7 @@ MainWindow::MainWindow( : QWidget(parent), username(username), main_layout_(new QVBoxLayout(this)), - top_bar_(new BottomBar(this, username, tr("EFFICIO :: Таск-Трекер"))), + top_bar_(new BottomBar(this, username, tr("EFFICIO :: Task-Tracker"))), content_layout_(new QHBoxLayout(this)), project_list_(new ProjectList(this)), note_list_(new NoteList(this)), @@ -102,6 +103,22 @@ MainWindow::MainWindow( this, &Ui::MainWindow::handle_font_size_changed ); handle_font_size_changed(StyleManager::instance()->current_font_size()); + connect(LanguageManager::instance(), &LanguageManager::language_changed, + this, &MainWindow::handle_language_changed + ); + handle_language_changed(LanguageManager::instance()->current_language()); +} + + +void MainWindow::handle_language_changed(std::string new_language) { + if (new_language == "RU") { + new_project_button_->setText(tr("Новый проект")); + new_note_button_->setText(tr("Новая заметка")); + } + else if(new_language == "EN") { + new_project_button_->setText(tr("New project")); + new_note_button_->setText(tr("New note")); + } } void MainWindow::on_delete_account_button_click() { diff --git a/ui/main-window/src/notewidget.cpp b/ui/main-window/src/notewidget.cpp index 629d6b4..21f4cc6 100644 --- a/ui/main-window/src/notewidget.cpp +++ b/ui/main-window/src/notewidget.cpp @@ -5,6 +5,7 @@ #include "note.hpp" #include "note_edit_dialog.h" #include "style_manager.h" +#include "language_manager.h" namespace Ui { NoteWidget::NoteWidget( @@ -44,21 +45,46 @@ NoteWidget::NoteWidget( ); this->setLayout(main_layout_); this->setAttribute(Qt::WA_StyledBackground); + connect(LanguageManager::instance(), &LanguageManager::language_changed, + this, &NoteWidget::handle_language_changed + ); + handle_language_changed(LanguageManager::instance()->current_language()); +} + +void NoteWidget::handle_language_changed(std::string new_language) { + if (new_language == "RU") { + open_button_->setText(tr("Открыть")); + if (title_label_->text() == "Empty note") { + title_label_->setText("Пустая заметка"); + } + // if (text_label_->text() == "Add a detailed description of your note") { + // title_label_->setText("Добавьте подробное описание вашей заметки"); + // } + } + else if (new_language == "EN") { + open_button_->setText(tr("Open")); + if (title_label_->text() == "Пустая заметка") { + title_label_->setText("Empty note"); + } + // if (text_label_->text() == "Добавьте подробное описание вашей заметки") { + // title_label_->setText("Add a detailed description of your note"); + // } + } } void NoteWidget::handle_font_size_changed(std::string font_size_){ QString font_rule; if (font_size_ == "small") { title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 13px;"); - text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 11px;"); + // text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 11px;"); } else if (font_size_ == "medium") { title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); - text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 13px;"); + // text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 13px;"); } else if (font_size_ == "big") { title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 17px;"); - text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); + // text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); } } @@ -69,7 +95,7 @@ void NoteWidget::open_note_window() const { ); dialog->setAttribute(Qt::WA_DeleteOnClose); dialog->exec(); - text_label_->setText(QString::fromStdString(model_note_->get_text())); +// text_label_->setText(QString::fromStdString(model_note_->get_text())); title_label_->setText(QString::fromStdString(model_note_->get_title())); main_layout_->update(); } diff --git a/ui/note-widget/CMakeLists.txt b/ui/note-widget/CMakeLists.txt index ff54b3c..9dcfe1d 100644 --- a/ui/note-widget/CMakeLists.txt +++ b/ui/note-widget/CMakeLists.txt @@ -37,4 +37,4 @@ target_include_directories(NoteWidget $ ) -target_link_libraries(NoteWidget PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database Scripts StyleManager) \ No newline at end of file +target_link_libraries(NoteWidget PRIVATE Qt6::Widgets Qt6::Core Qt6::Gui Qt6::Sql Database LanguageManager Scripts StyleManager) \ No newline at end of file diff --git a/ui/note-widget/include/note_edit_dialog.h b/ui/note-widget/include/note_edit_dialog.h index 1bb99ad..62f6286 100644 --- a/ui/note-widget/include/note_edit_dialog.h +++ b/ui/note-widget/include/note_edit_dialog.h @@ -30,6 +30,7 @@ class NoteEditDialog final : public QDialog { static const std::vector THEMES; void handle_theme_changed(int theme); void handle_font_size_changed(std::string font_size); + void handle_language_changed(std::string new_language); private slots: void on_save_button_click(); diff --git a/ui/note-widget/include/tags_dialog.h b/ui/note-widget/include/tags_dialog.h index 03611a6..df23a47 100644 --- a/ui/note-widget/include/tags_dialog.h +++ b/ui/note-widget/include/tags_dialog.h @@ -17,6 +17,7 @@ class TagsDialog final : public QDialog { public: const static std::vector THEMES; void handle_theme_changed(int theme); + void handle_language_changed(std::string new_language); const int MAX_TAGS_COUNT = 5; const std::pair DIALOG_SIZE = std::make_pair(300, 250); diff --git a/ui/note-widget/src/note_edit_dialog.cpp b/ui/note-widget/src/note_edit_dialog.cpp index 31c4264..d621718 100644 --- a/ui/note-widget/src/note_edit_dialog.cpp +++ b/ui/note-widget/src/note_edit_dialog.cpp @@ -11,6 +11,7 @@ #include "note_edit_dialog_styles.h" #include "tags_dialog.h" #include "style_manager.h" +#include "language_manager.h" const std::vector NoteEditDialog::THEMES = { @@ -47,7 +48,6 @@ void NoteEditDialog::init_basic_fields() { ui_->descriptionTextEdit->setText(QString::fromStdString(note_->get_text())); } - void NoteEditDialog::on_switch_theme_button_click() { int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; StyleManager::instance()->apply_theme(next_theme); @@ -112,6 +112,41 @@ void NoteEditDialog::setup_connections() { connect(StyleManager::instance(), &StyleManager::font_size_changed, this, &NoteEditDialog::handle_font_size_changed ); + connect(LanguageManager::instance(), &LanguageManager::language_changed, + this, &NoteEditDialog::handle_language_changed + ); + handle_language_changed(LanguageManager::instance()->current_language()); +} + +void NoteEditDialog::handle_language_changed(std::string new_language) { + if (new_language == "RU") { + setWindowTitle("EFFICIO"); + ui_->saveButton->setText(tr("Сохранить")); + ui_->cancelButton->setText(tr("Отмена")); + ui_->joinButton->setText(ui_->membersLabel->isVisible() ? tr("Покинуть") : tr("Присоединиться")); + ui_->addMembersButton->setText(tr("Добавить участников")); + ui_->addDateButton->setText(tr("Добавить дату")); + ui_->addTagsButton->setText(tr("Добавить теги")); + ui_->projectNameLabel->setText(tr("Проект:")); + ui_->descriptionLabel->setText(tr("Описание:")); + ui_->descriptionTextEdit->setText(tr("Добавьте подробное описание вашей заметки")); + ui_->sidePanelLabel->setText(tr("Участники:")); + ui_->sidePanelLabel_2->setText(tr("Теги:")); + } + else if(new_language == "EN") { + setWindowTitle("EFFICIO"); + ui_->saveButton->setText(tr("Save")); + ui_->cancelButton->setText(tr("Cancel")); + ui_->joinButton->setText(ui_->membersLabel->isVisible() ? tr("Leave") : tr("Join")); + ui_->addMembersButton->setText(tr("Add members")); + ui_->addDateButton->setText(tr("Add date")); + ui_->descriptionTextEdit->setText(tr("Add a detailed description of your note")); + ui_->addTagsButton->setText(tr("Add tags")); + ui_->projectNameLabel->setText(tr("Project:")); + ui_->descriptionLabel->setText(tr("Description:")); + ui_->sidePanelLabel->setText(tr("Members:")); + ui_->sidePanelLabel_2->setText(tr("Tags:")); + } } void NoteEditDialog::handle_font_size_changed(std::string font_size_) { @@ -148,11 +183,21 @@ void NoteEditDialog::setup_ui() { void NoteEditDialog::on_save_button_click() { if (try_save_note()) { - QMessageBox::information(this, "Заметка сохранена", - QString("Заголовок: %1\nСодержимое: %2") - .arg(ui_->titleLineEdit->text(), ui_->descriptionTextEdit->toPlainText())); + if(LanguageManager::instance()->current_language() == "RU"){ + QMessageBox::information(this, "Заметка сохранена", + QString("Заголовок: %1\nСодержимое: %2") + .arg(ui_->titleLineEdit->text(), ui_->descriptionTextEdit->toPlainText())); + } else { + QMessageBox::information(this, "Note Saved", + QString("Title: %1\nDescription: %2") + .arg(ui_->titleLineEdit->text(), ui_->descriptionTextEdit->toPlainText())); + } } else { - QMessageBox::information(this, "Ошибка", "Не удалось сохранить заметку"); + if(LanguageManager::instance()->current_language() == "RU"){ + QMessageBox::information(this, "Ошибка", "Не удалось сохранить заметку"); + } else { + QMessageBox::information(this, "Error", "Failed to save the note"); + } } close(); } @@ -196,7 +241,11 @@ void NoteEditDialog::clear_member_avatars() { } void NoteEditDialog::on_add_members_button_click() { - QMessageBox::information(this, "Ошибка", "Другие участники не найдены :("); + if(LanguageManager::instance()->current_language() == "RU"){ + QMessageBox::information(this, "Ошибка", "Другие участники не найдены."); + } else { + QMessageBox::information(this, "Error", "No other participants were found."); + } } void NoteEditDialog::on_add_tags_button_click() { diff --git a/ui/note-widget/src/tags_dialog.cpp b/ui/note-widget/src/tags_dialog.cpp index 544145a..5287165 100644 --- a/ui/note-widget/src/tags_dialog.cpp +++ b/ui/note-widget/src/tags_dialog.cpp @@ -4,6 +4,7 @@ #include #include "tags_dialog_styles.h" #include "style_manager.h" +#include "language_manager.h" const std::vector TagsDialog::THEMES = { @@ -34,9 +35,54 @@ TagsDialog::TagsDialog(const QList &initial_tags, QWidget *parent) setModal(true); setFixedSize(DIALOG_SIZE.first, DIALOG_SIZE.second); handle_theme_changed(StyleManager::instance()->current_theme()); - + connect(LanguageManager::instance(), &LanguageManager::language_changed, + this, &TagsDialog::handle_language_changed + ); + handle_language_changed(LanguageManager::instance()->current_language()); +} + + +void TagsDialog::handle_language_changed(std::string new_language) { + if (new_language == "RU") { + setWindowTitle("Добавить теги"); + ok_button_->setText(tr("OK")); + cancel_button_->setText(tr("Отмена")); + + const QStringList colors = {"Красный", "Синий", "Розовый", "Зеленый", "Желтый"}; + for (int i = 0; i < MAX_TAGS_COUNT; ++i) { + if (color_combo_boxes_[i]) { + color_combo_boxes_[i]->setItemText(0, colors[0]); + color_combo_boxes_[i]->setItemText(1, colors[1]); + color_combo_boxes_[i]->setItemText(2, colors[2]); + color_combo_boxes_[i]->setItemText(3, colors[3]); + color_combo_boxes_[i]->setItemText(4, colors[4]); + } + if (name_line_edits_[i]) { + name_line_edits_[i]->setPlaceholderText("Имя тега " + QString::number(i + 1)); + } + } + } else if (new_language == "EN") { + setWindowTitle("Add tags"); + ok_button_->setText(tr("OK")); + cancel_button_->setText(tr("Cancel")); + + const QStringList colors = {"Red", "Blue", "Pink", "Green", "Yellow"}; + for (int i = 0; i < MAX_TAGS_COUNT; ++i) { + if (color_combo_boxes_[i]) { + color_combo_boxes_[i]->setItemText(0, colors[0]); + color_combo_boxes_[i]->setItemText(1, colors[1]); + color_combo_boxes_[i]->setItemText(2, colors[2]); + color_combo_boxes_[i]->setItemText(3, colors[3]); + color_combo_boxes_[i]->setItemText(4, colors[4]); + } + if (name_line_edits_[i]) { + name_line_edits_[i]->setPlaceholderText("Tag name " + QString::number(i + 1)); + } + } + } } + void TagsDialog::setup_ui() { auto *main_layout = new QVBoxLayout(this); diff --git a/ui/profile-window/CMakeLists.txt b/ui/profile-window/CMakeLists.txt index cf9dade..2e19e88 100644 --- a/ui/profile-window/CMakeLists.txt +++ b/ui/profile-window/CMakeLists.txt @@ -35,6 +35,7 @@ target_link_libraries(ProfileWindow PRIVATE Qt6::Sql Database StyleManager + LanguageManager AuthorizationWindows SettingsWindow AnalyticsWindow diff --git a/ui/profile-window/include/profile_window.h b/ui/profile-window/include/profile_window.h index 8011c5d..28f1fee 100644 --- a/ui/profile-window/include/profile_window.h +++ b/ui/profile-window/include/profile_window.h @@ -31,6 +31,7 @@ class ProfileWindow : public QDialog { static const std::vector THEMES; void handle_theme_changed(int theme); void handle_font_size_changed(std::string font_size); + void handle_language_changed(std::string new_language); friend class MainWindow; signals: diff --git a/ui/profile-window/src/profile_window.cpp b/ui/profile-window/src/profile_window.cpp index f5b0742..20872d6 100644 --- a/ui/profile-window/src/profile_window.cpp +++ b/ui/profile-window/src/profile_window.cpp @@ -5,6 +5,7 @@ #include "lr_dao.hpp" #include "settings_window.h" #include "analytics_window.h" +#include "language_manager.h" namespace Ui { @@ -83,9 +84,30 @@ void ProfileWindow::handle_font_size_changed(std::string font_size) { } this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_rule); + connect(LanguageManager::instance(), &LanguageManager::language_changed, + this, &ProfileWindow::handle_language_changed + ); + handle_language_changed(LanguageManager::instance()->current_language()); +} + + +void ProfileWindow::handle_language_changed(std::string new_language) { + if (new_language == "RU") { + setWindowTitle(tr("Профиль")); + logout_button->setText(tr("Выйти из аккаунта")); + delete_button->setText(tr("Удалить аккаунт")); + stats_button->setText(tr("Моя статистика")); + } + else if (new_language == "EN") { + setWindowTitle(tr("Profile")); + logout_button->setText(tr("Log out")); + delete_button->setText(tr("Delete account")); + stats_button->setText(tr("My statistics")); + } } + void ProfileWindow::handle_theme_changed(int theme) { setStyleSheet(THEMES[theme]); } diff --git a/ui/settings-window/CMakeLists.txt b/ui/settings-window/CMakeLists.txt index 25e29c4..ec37601 100644 --- a/ui/settings-window/CMakeLists.txt +++ b/ui/settings-window/CMakeLists.txt @@ -35,5 +35,6 @@ target_link_libraries(SettingsWindow PRIVATE Qt6::Sql Database StyleManager + LanguageManager AuthorizationWindows ) \ No newline at end of file diff --git a/ui/settings-window/include/settings_window.h b/ui/settings-window/include/settings_window.h index a847cea..d64a358 100644 --- a/ui/settings-window/include/settings_window.h +++ b/ui/settings-window/include/settings_window.h @@ -17,6 +17,7 @@ class SettingsWindow : public QDialog { explicit SettingsWindow(QWidget *parent = nullptr); void handle_theme_changed(int theme_); void handle_font_size_changed(std::string font_size_); + void handle_language_changed(std::string new_language); static const std::vector THEMES; private slots: diff --git a/ui/settings-window/src/settings_window.cpp b/ui/settings-window/src/settings_window.cpp index 2dd67a6..d39c939 100644 --- a/ui/settings-window/src/settings_window.cpp +++ b/ui/settings-window/src/settings_window.cpp @@ -1,6 +1,7 @@ #include "settings_window.h" #include "settings_window_style_sheet.h" #include "style_manager.h" +#include "language_manager.h" #include const std::vector SettingsWindow::THEMES = { @@ -75,8 +76,36 @@ SettingsWindow::SettingsWindow(QWidget *parent) : QDialog(parent) { handle_theme_changed(StyleManager::instance()->current_theme()); handle_font_size_changed(StyleManager::instance()->current_font_size()); + connect(LanguageManager::instance(), &LanguageManager::language_changed, + this, &SettingsWindow::handle_language_changed + ); + handle_language_changed(LanguageManager::instance()->current_language()); } +void SettingsWindow::handle_language_changed(std::string new_language) { + if (new_language == "RU") { + setWindowTitle(tr("Настройки")); + title_label->setText(tr("Настройки")); + font_size_label->setText(tr("Размер шрифта")); + theme_button->setText(tr("Тема")); + small_font_radio->setText(tr("Мелкий")); + medium_font_radio->setText(tr("Средний")); + large_font_radio->setText(tr("Крупный")); + language_button->setText("RU"); + } + else if (new_language == "EN") { + setWindowTitle(tr("Settings")); + title_label->setText(tr("Settings")); + font_size_label->setText(tr("Font size")); + theme_button->setText(tr("Theme")); + small_font_radio->setText(tr("Small")); + medium_font_radio->setText(tr("Medium")); + large_font_radio->setText(tr("Large")); + language_button->setText("EN"); + } +} + + void SettingsWindow::handle_font_size_changed(std::string font_size) { QString font_rule; if(font_size == "small") { @@ -110,8 +139,10 @@ void SettingsWindow::handle_theme_changed(int theme_) { void SettingsWindow::toggle_language() { if (language_button->text() == tr("RU")) { language_button->setText(tr("EN")); + LanguageManager::instance()->apply_language("EN"); } else { language_button->setText(tr("RU")); + LanguageManager::instance()->apply_language("RU"); } } diff --git a/ui/style-manager/include/style_manager.h b/ui/style-manager/include/style_manager.h index cd513ea..a34ce77 100644 --- a/ui/style-manager/include/style_manager.h +++ b/ui/style-manager/include/style_manager.h @@ -1,5 +1,5 @@ -#ifndef style_manager_H -#define style_manager_H +#ifndef STYLE_MANAGER_H +#define STYLE_MANAGER_H #include #include @@ -18,7 +18,6 @@ class StyleManager : public QObject { void apply_font_size(std::string font_size_); int current_theme() const; std::string current_font_size() const; - signals: void theme_changed(int new_theme); void font_size_changed(std::string new_font_size_); From c15c5788371bf823f512430a35cb69a69906e33e Mon Sep 17 00:00:00 2001 From: MuravAna Date: Tue, 3 Jun 2025 16:16:54 +0300 Subject: [PATCH 13/17] Add language button iin autorizations window. Fix bug in main window with empty names for projects. Rewrite analytics window: now there is pie chart --- .../include/analytics_window.h | 39 +- ui/analytics-window/src/analytics_window.cpp | 420 ++++++++++++------ .../include/login_window.h | 4 +- .../include/login_window_style_sheet.h | 322 +------------- .../include/registration_window.h | 4 +- .../include/registration_window_style_sheet.h | 324 +------------- ui/authorization-windows/src/login_window.cpp | 40 +- .../src/registration_window.cpp | 48 +- ui/main-window/src/mainwindow.cpp | 61 ++- ui/note-widget/include/note_edit_dialog.h | 2 + .../include/note_edit_dialog_styles.h | 66 ++- ui/note-widget/src/note_edit_dialog.cpp | 80 +++- .../include/settings_window_style_sheet.h | 16 +- ui/style-manager/src/style_manager.cpp | 6 +- 14 files changed, 544 insertions(+), 888 deletions(-) diff --git a/ui/analytics-window/include/analytics_window.h b/ui/analytics-window/include/analytics_window.h index aee1065..63dddd5 100644 --- a/ui/analytics-window/include/analytics_window.h +++ b/ui/analytics-window/include/analytics_window.h @@ -3,9 +3,8 @@ #include #include -#include -#include -#include +#include +#include #include class AnalyticsWindow : public QDialog @@ -13,26 +12,34 @@ class AnalyticsWindow : public QDialog Q_OBJECT public: - explicit AnalyticsWindow(QWidget *parent = nullptr); + explicit AnalyticsWindow( + QWidget *parent = nullptr, + int created_count = 3, + int completed_count = 4, + int expired_count = 5 + ); ~AnalyticsWindow(); - void setTasksData(int created, int completed, int overdue); - void setProjectsData(const QMap& projects); + static const std::vector THEMES; + +private: + void handle_theme_changed(int theme); void handle_font_size_changed(std::string font_size); void handle_language_changed(std::string new_language); void on_switch_theme_clicked(); + void setup_chart(); - static const std::vector THEMES; - -private: - QTabWidget *tab_widget; - QVBoxLayout *tasks_layout; - QVBoxLayout *projects_layout; - QDialogButtonBox *button_box; - - QChart *createTasksChart(int created, int completed, int overdue); - QChart *createProjectsChart(const QMap& projects); + int m_created_count; + int m_completed_count; + int m_expired_count; + + QChartView *chart_view; + QPieSeries *series; + QChart *chart; + QPieSlice *completed_slice; + QPieSlice *expired_slice; + QPieSlice *created_slice; }; #endif // ANALYTICS_DIALOG_H \ No newline at end of file diff --git a/ui/analytics-window/src/analytics_window.cpp b/ui/analytics-window/src/analytics_window.cpp index 3ea1b96..aec7e19 100644 --- a/ui/analytics-window/src/analytics_window.cpp +++ b/ui/analytics-window/src/analytics_window.cpp @@ -12,83 +12,124 @@ const std::vector AnalyticsWindow::THEMES = { Ui::analytics_window_blue_theme }; -AnalyticsWindow::AnalyticsWindow(QWidget *parent) - : QDialog(parent) +AnalyticsWindow::AnalyticsWindow(QWidget *parent, + int created_count, + int completed_count, + int expired_count) + : QDialog(parent), + m_created_count(created_count), + m_completed_count(completed_count), + m_expired_count(expired_count), + chart_view(new QChartView(this)), + series(new QPieSeries()), + chart(new QChart()) { - QVBoxLayout *main_layout = new QVBoxLayout(this); + setFixedSize(700, 400); - tab_widget = new QTabWidget(this); + QVBoxLayout *main_layout = new QVBoxLayout(this); - QWidget *tasks_tab = new QWidget(); - tasks_layout = new QVBoxLayout(tasks_tab); - tab_widget->addTab(tasks_tab, "Статистика задач"); + completed_slice = new QPieSlice(); + completed_slice->setValue(m_completed_count); + completed_slice->setColor(QColor(46, 204, 113)); - QWidget *projects_tab = new QWidget(); - projects_layout = new QVBoxLayout(projects_tab); - tab_widget->addTab(projects_tab, "Распределение по проектам"); + expired_slice = new QPieSlice(); + expired_slice->setValue(m_expired_count); + expired_slice->setColor(QColor(231, 76, 60)); - button_box = new QDialogButtonBox(QDialogButtonBox::Close, this); - connect(button_box, &QDialogButtonBox::rejected, this, &QDialog::reject); + created_slice = new QPieSlice(); + created_slice->setValue(m_created_count); + created_slice->setColor(QColor(52, 152, 219)); - main_layout->addWidget(tab_widget); - main_layout->addWidget(button_box); + series->append(completed_slice); + series->append(expired_slice); + series->append(created_slice); - setWindowTitle("Аналитическая панель"); - resize(800, 600); + chart->addSeries(series); + chart->legend()->setAlignment(Qt::AlignBottom); + chart->setAnimationOptions(QChart::AllAnimations); - setTasksData(0, 0, 0); + chart_view->setRenderHint(QPainter::Antialiasing); + chart_view->setChart(chart); - QMap projects; - setProjectsData(projects); + main_layout->addWidget(chart_view); + setLayout(main_layout); - connect(StyleManager::instance(), &StyleManager::theme_changed, - this, &AnalyticsWindow::handle_theme_changed); - handle_theme_changed(StyleManager::instance()->current_theme()); - connect(StyleManager::instance(), &StyleManager::font_size_changed, - this, &AnalyticsWindow::handle_font_size_changed + connect( + StyleManager::instance(), &StyleManager::theme_changed, + this, &AnalyticsWindow::handle_theme_changed + ); + connect( + StyleManager::instance(), &StyleManager::font_size_changed, + this, &AnalyticsWindow::handle_font_size_changed ); - handle_font_size_changed(StyleManager::instance()->current_font_size()); - connect(LanguageManager::instance(), &LanguageManager::language_changed, this, &AnalyticsWindow::handle_language_changed ); + handle_font_size_changed(StyleManager::instance()->current_font_size()); + handle_theme_changed(StyleManager::instance()->current_theme()); handle_language_changed(LanguageManager::instance()->current_language()); } +void AnalyticsWindow::setup_chart() +{ + series->append("Завершенные", m_completed_count); + series->append("Просроченные", m_expired_count); + series->append("Созданные", m_created_count); + + QPieSlice *completed_slice = series->slices().at(0); + completed_slice->setColor(QColor(46, 204, 113)); + completed_slice->setLabelVisible(true); + + QPieSlice *expired_slice = series->slices().at(1); + expired_slice->setColor(QColor(231, 76, 60)); + expired_slice->setLabelVisible(true); + + QPieSlice *created_slice = series->slices().at(2); + created_slice->setColor(QColor(52, 152, 219)); + created_slice->setLabelVisible(true); + + for(QPieSlice *slice : series->slices()) { + slice->setLabel(slice->label() + + QString(": %1 (%2%)") + .arg(slice->value()) + .arg(100 * slice->percentage(), 0, 'f', 1)); + } + + QChart *chart = new QChart(); + chart->addSeries(series); + chart->setTitle("Статистика заметок"); + chart->setTitleFont(QFont("Arial", 14, QFont::Bold)); + chart->legend()->setAlignment(Qt::AlignBottom); + chart->setAnimationOptions(QChart::AllAnimations); + + chart_view->setChart(chart); +} + +AnalyticsWindow::~AnalyticsWindow(){} void AnalyticsWindow::handle_language_changed(std::string new_language) { if (new_language == "RU") { - tab_widget->setTabText(0, tr("Статистика задач")); - tab_widget->setTabText(1, tr("Распределение по проектам")); - setWindowTitle(tr("Аналитическая панель")); - - QChart *tasks_chart = static_cast(tasks_layout->itemAt(0)->widget())->chart(); - tasks_chart->setTitle(tr("Статистика задач за период")); - static_cast(tasks_chart->axes(Qt::Vertical)[0])->setTitleText(tr("Количество")); - - QBarSeries *tasks_series = static_cast(tasks_chart->series()[0]); - static_cast(tasks_series->barSets()[0])->setLabel(tr("Создано")); - static_cast(tasks_series->barSets()[1])->setLabel(tr("Завершено")); - static_cast(tasks_series->barSets()[2])->setLabel(tr("Просрочено")); - - button_box->button(QDialogButtonBox::Close)->setText(tr("Закрыть")); - } - else if(new_language == "EN") { - tab_widget->setTabText(0, tr("Tasks Statistics")); - tab_widget->setTabText(1, tr("Projects Distribution")); - setWindowTitle(tr("Analytics Panel")); - - QChart *tasks_chart = static_cast(tasks_layout->itemAt(0)->widget())->chart(); - tasks_chart->setTitle(tr("Tasks Statistics for Period")); - static_cast(tasks_chart->axes(Qt::Vertical)[0])->setTitleText(tr("Count")); - - QBarSeries *tasks_series = static_cast(tasks_chart->series()[0]); - static_cast(tasks_series->barSets()[0])->setLabel(tr("Created")); - static_cast(tasks_series->barSets()[1])->setLabel(tr("Completed")); - static_cast(tasks_series->barSets()[2])->setLabel(tr("Overdue")); - - button_box->button(QDialogButtonBox::Close)->setText(tr("Close")); + chart->setTitle("Статистика заметок"); + completed_slice->setLabel("Завершенные"); + expired_slice->setLabel("Просроченные"); + created_slice->setLabel("Созданные"); + setWindowTitle("Аналитическая панель"); } + else if (new_language == "EN") { + chart->setTitle("Notes Statistics"); + completed_slice->setLabel("Completed"); + expired_slice->setLabel("Expired"); + created_slice->setLabel("Created"); + setWindowTitle("Analytics Panel"); + } + for (QPieSlice *slice : series->slices()) { + slice->setLabelVisible(true); + QString label = slice->label() + + QString(": %1 (%2%)") + .arg(slice->value()) + .arg(100 * slice->percentage(), 0, 'f', 1); + slice->setLabel(label); + } } void AnalyticsWindow::handle_font_size_changed(std::string font_size) { @@ -116,89 +157,212 @@ void AnalyticsWindow::on_switch_theme_clicked() { StyleManager::instance()->apply_theme(next_theme); } -AnalyticsWindow::~AnalyticsWindow(){} -void AnalyticsWindow::setTasksData(int created, int completed, int overdue) -{ - QLayoutItem *child; - while (child = tasks_layout->takeAt(0)) { - delete child->widget(); - delete child; - } + + + + +// #include "analytics_window.h" +// #include "style_manager.h" +// #include "language_manager.h" +// #include "analytics_window_style_sheet.h" +// #include + +// const std::vector AnalyticsWindow::THEMES = { +// Ui::analytics_window_light_autumn_theme, +// Ui::analytics_window_dark_autumn_theme, +// Ui::analytics_window_dark_purple_theme, +// Ui::analytics_window_light_purple_theme, +// Ui::analytics_window_blue_theme +// }; + +// AnalyticsWindow::AnalyticsWindow(QWidget *parent) +// : QDialog(parent) +// { +// QVBoxLayout *main_layout = new QVBoxLayout(this); - QChart *chart = createTasksChart(created, completed, overdue); - tasks_layout->addWidget(new QChartView(chart)); -} +// tab_widget = new QTabWidget(this); + +// QWidget *tasks_tab = new QWidget(); +// tasks_layout = new QVBoxLayout(tasks_tab); +// tab_widget->addTab(tasks_tab, "Статистика задач"); + +// QWidget *projects_tab = new QWidget(); +// projects_layout = new QVBoxLayout(projects_tab); +// tab_widget->addTab(projects_tab, "Распределение по проектам"); + +// button_box = new QDialogButtonBox(QDialogButtonBox::Close, this); +// connect(button_box, &QDialogButtonBox::rejected, this, &QDialog::reject); + +// main_layout->addWidget(tab_widget); +// main_layout->addWidget(button_box); + +// setWindowTitle("Аналитическая панель"); +// resize(800, 600); + +// setTasksData(0, 0, 0); + +// QMap projects; +// setProjectsData(projects); -void AnalyticsWindow::setProjectsData(const QMap& projects) -{ - QLayoutItem *child; - while (child = projects_layout->takeAt(0)) { - delete child->widget(); - delete child; - } +// connect(StyleManager::instance(), &StyleManager::theme_changed, +// this, &AnalyticsWindow::handle_theme_changed); +// handle_theme_changed(StyleManager::instance()->current_theme()); +// connect(StyleManager::instance(), &StyleManager::font_size_changed, +// this, &AnalyticsWindow::handle_font_size_changed +// ); +// handle_font_size_changed(StyleManager::instance()->current_font_size()); + +// connect(LanguageManager::instance(), &LanguageManager::language_changed, +// this, &AnalyticsWindow::handle_language_changed +// ); +// handle_language_changed(LanguageManager::instance()->current_language()); +// } + + +// void AnalyticsWindow::handle_language_changed(std::string new_language) { +// if (new_language == "RU") { +// tab_widget->setTabText(0, tr("Статистика задач")); +// tab_widget->setTabText(1, tr("Распределение по проектам")); +// setWindowTitle(tr("Аналитическая панель")); + +// QChart *tasks_chart = static_cast(tasks_layout->itemAt(0)->widget())->chart(); +// tasks_chart->setTitle(tr("Статистика задач за период")); +// static_cast(tasks_chart->axes(Qt::Vertical)[0])->setTitleText(tr("Количество")); + +// QBarSeries *tasks_series = static_cast(tasks_chart->series()[0]); +// static_cast(tasks_series->barSets()[0])->setLabel(tr("Создано")); +// static_cast(tasks_series->barSets()[1])->setLabel(tr("Завершено")); +// static_cast(tasks_series->barSets()[2])->setLabel(tr("Просрочено")); + +// button_box->button(QDialogButtonBox::Close)->setText(tr("Закрыть")); +// } +// else if(new_language == "EN") { +// tab_widget->setTabText(0, tr("Tasks Statistics")); +// tab_widget->setTabText(1, tr("Projects Distribution")); +// setWindowTitle(tr("Analytics Panel")); + +// QChart *tasks_chart = static_cast(tasks_layout->itemAt(0)->widget())->chart(); +// tasks_chart->setTitle(tr("Tasks Statistics for Period")); +// static_cast(tasks_chart->axes(Qt::Vertical)[0])->setTitleText(tr("Count")); + +// QBarSeries *tasks_series = static_cast(tasks_chart->series()[0]); +// static_cast(tasks_series->barSets()[0])->setLabel(tr("Created")); +// static_cast(tasks_series->barSets()[1])->setLabel(tr("Completed")); +// static_cast(tasks_series->barSets()[2])->setLabel(tr("Overdue")); + +// button_box->button(QDialogButtonBox::Close)->setText(tr("Close")); +// } +// } + +// void AnalyticsWindow::handle_font_size_changed(std::string font_size) { - QChart *chart = createProjectsChart(projects); - projects_layout->addWidget(new QChartView(chart)); -} +// QString font_size_rule; +// if(font_size == "small") { +// font_size_rule = "QPushButton { font-size: 11px; }"; +// } +// else if(font_size == "medium") { +// font_size_rule = "QPushButton { font-size: 13px; }"; +// } +// else if(font_size == "big") { +// font_size_rule = "QPushButton { font-size: 15px; }"; +// } + +// this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_size_rule); +// } -QChart* AnalyticsWindow::createTasksChart(int created, int completed, int overdue) -{ - QBarSet *created_set = new QBarSet("Создано"); - *created_set << created; +// void AnalyticsWindow::handle_theme_changed(int theme) { +// this->setStyleSheet(THEMES[theme]); +// } + +// void AnalyticsWindow::on_switch_theme_clicked() { +// int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; +// StyleManager::instance()->apply_theme(next_theme); +// } + +// AnalyticsWindow::~AnalyticsWindow(){} + +// void AnalyticsWindow::setTasksData(int created, int completed, int overdue) +// { +// QLayoutItem *child; +// while (child = tasks_layout->takeAt(0)) { +// delete child->widget(); +// delete child; +// } - QBarSet *completed_set = new QBarSet("Завершено"); - *completed_set << completed; +// QChart *chart = createTasksChart(created, completed, overdue); +// tasks_layout->addWidget(new QChartView(chart)); +// } + +// void AnalyticsWindow::setProjectsData(const QMap& projects) +// { +// QLayoutItem *child; +// while (child = projects_layout->takeAt(0)) { +// delete child->widget(); +// delete child; +// } - QBarSet *overdue_set = new QBarSet("Просрочено"); - *overdue_set << overdue; +// QChart *chart = createProjectsChart(projects); +// projects_layout->addWidget(new QChartView(chart)); +// } - QBarSeries *series = new QBarSeries(); - series->append(created_set); - series->append(completed_set); - series->append(overdue_set); +// QChart* AnalyticsWindow::createTasksChart(int created, int completed, int overdue) +// { +// QBarSet *created_set = new QBarSet("Создано"); +// *created_set << created; + +// QBarSet *completed_set = new QBarSet("Завершено"); +// *completed_set << completed; + +// QBarSet *overdue_set = new QBarSet("Просрочено"); +// *overdue_set << overdue; - QChart *chart = new QChart(); - chart->addSeries(series); - chart->setTitle("Статистика задач за период"); - chart->setAnimationOptions(QChart::SeriesAnimations); - - QBarCategoryAxis *axisX = new QBarCategoryAxis(); - axisX->append("Тип задач"); - chart->addAxis(axisX, Qt::AlignBottom); - series->attachAxis(axisX); - - QValueAxis *axisY = new QValueAxis(); - int maxValue = qMax(created, qMax(completed, overdue)); - axisY->setRange(0, maxValue + (maxValue * 0.1)); // +10% отмакс. значения - axisY->setTitleText("Количество"); - chart->addAxis(axisY, Qt::AlignLeft); - series->attachAxis(axisY); - - return chart; -} +// QBarSeries *series = new QBarSeries(); +// series->append(created_set); +// series->append(completed_set); +// series->append(overdue_set); -QChart* AnalyticsWindow::createProjectsChart(const QMap& projects) -{ - QPieSeries *series = new QPieSeries(); +// QChart *chart = new QChart(); +// chart->addSeries(series); +// chart->setTitle("Статистика задач за период"); +// chart->setAnimationOptions(QChart::SeriesAnimations); + +// QBarCategoryAxis *axisX = new QBarCategoryAxis(); +// axisX->append("Тип задач"); +// chart->addAxis(axisX, Qt::AlignBottom); +// series->attachAxis(axisX); + +// QValueAxis *axisY = new QValueAxis(); +// int maxValue = qMax(created, qMax(completed, overdue)); +// axisY->setRange(0, maxValue + (maxValue * 0.1)); // +10% отмакс. значения +// axisY->setTitleText("Количество"); +// chart->addAxis(axisY, Qt::AlignLeft); +// series->attachAxis(axisY); + +// return chart; +// } + +// QChart* AnalyticsWindow::createProjectsChart(const QMap& projects) +// { +// QPieSeries *series = new QPieSeries(); - int total = 0; - for (auto it = projects.begin(); it != projects.end(); ++it) { - series->append(it.key(), it.value()); - total += it.value(); - } +// int total = 0; +// for (auto it = projects.begin(); it != projects.end(); ++it) { +// series->append(it.key(), it.value()); +// total += it.value(); +// } - series->setLabelsVisible(); - foreach(QPieSlice *slice, series->slices()) { - slice->setLabel(QString("%1 (%2%)") - .arg(slice->label()) - .arg(100 * slice->percentage(), 0, 'f', 1)); - } +// series->setLabelsVisible(); +// foreach(QPieSlice *slice, series->slices()) { +// slice->setLabel(QString("%1 (%2%)") +// .arg(slice->label()) +// .arg(100 * slice->percentage(), 0, 'f', 1)); +// } - QChart *chart = new QChart(); - chart->addSeries(series); - chart->setTitle(QString("Распределение задач (%1 всего)").arg(total)); - chart->legend()->setAlignment(Qt::AlignRight); +// QChart *chart = new QChart(); +// chart->addSeries(series); +// chart->setTitle(QString("Распределение задач (%1 всего)").arg(total)); +// chart->legend()->setAlignment(Qt::AlignRight); - return chart; -} \ No newline at end of file +// return chart; +// } \ No newline at end of file diff --git a/ui/authorization-windows/include/login_window.h b/ui/authorization-windows/include/login_window.h index ee74dae..21e2028 100644 --- a/ui/authorization-windows/include/login_window.h +++ b/ui/authorization-windows/include/login_window.h @@ -19,14 +19,12 @@ class LoginWindow : public QWidget explicit LoginWindow(QWidget *parent = nullptr); ~LoginWindow() override; - static const std::vector THEMES; - void handle_theme_changed(int theme); void handle_language_changed(std::string new_language); private slots: void on_switch_mode_clicked(); void on_push_enter_clicked(); - void on_switch_theme_clicked(); + void on_switch_language_clicked(); private: std::shared_ptr ui; diff --git a/ui/authorization-windows/include/login_window_style_sheet.h b/ui/authorization-windows/include/login_window_style_sheet.h index 4483df3..68fa3c4 100644 --- a/ui/authorization-windows/include/login_window_style_sheet.h +++ b/ui/authorization-windows/include/login_window_style_sheet.h @@ -52,326 +52,24 @@ namespace Ui { color: #727272; } - QPushButton#switch_theme { - width: 20px; - height: 20px; - min-width: 20px; - min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #089083; - } - QPushButton::hover#switch_theme { - background-color: #089083; - } - QPushButton::pressed#switch_theme { - background-color:rgb(7, 110, 100); - } - - )"; - - QString login_window_dark_autumn_theme = R"( - QWidget { - background-color: #202020; - } - - QLabel { - background-color: transparent; - font-family: 'Arial'; - font-size: 13px; - color: #089083; - padding: 1px; - } - - QPushButton#push_enter { - font-family: 'Arial'; - border-radius: 10px; - background-color: #fea36b; - color: #263238; - padding: 5px 10px; - } - - QPushButton#push_enter:hover { - background-color:rgb(225, 133, 76); - } - - QPushButton#switch_mode { - font-family: 'Arial'; - border-radius: 10px; + QPushButton#switch_theme { background-color: #089083; - color: white; - padding: 5px 10px; - } - - QPushButton#switch_mode:hover { - background-color: #01635d; - } - - QLineEdit { - border-radius: 10px; - border: 1px solid rgb(0, 0, 0); - background:rgb(0, 0, 0); - color: #727272; - padding: 5px; - } - - QLineEdit::placeholder { - color: #727272; - } - - QPushButton#switch_theme { - width: 20px; - height: 20px; - min-width: 20px; - min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #089083; - } - QPushButton::hover#switch_theme { - background-color: #089083; - } - QPushButton::pressed#switch_theme { - background-color:rgb(13, 93, 85); - } - )"; - - QString login_window_light_purple_theme = R"( - QWidget { - background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, - stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(103, 88, 126)); - margin: 0; - padding: 0; - border: none; - } - - QLabel { - background-color: transparent; - font-family: 'Arial'; - font-size: 13px; - color: rgb(42, 10, 25); - padding: 1px; - } - - QPushButton#push_enter { - font-family: 'Arial'; - border-radius: 10px; - background-color: #722548; - color:rgb(206, 193, 224); - padding: 5px 10px; - } - - QPushButton#push_enter:hover { - background-color:rgb(98, 27, 59) - } - - QPushButton#switch_mode { - font-family: 'Arial'; - border-radius: 10px; - background-color: rgb(42, 10, 25); - color: rgb(218, 207, 235); - padding: 5px 10px; - } - - QPushButton#switch_mode:hover { - background-color:rgb(27, 6, 16); - } - - QLineEdit { - border-radius: 10px; - border: 1px solid rgb(221, 210, 238); - background: rgb(221, 210, 238); - color: #221932; - padding: 5px; - } - - QLineEdit::placeholder { - color: white; - } - - QPushButton#switch_theme { - width: 20px; - height: 20px; min-width: 20px; min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #060407; - } - QPushButton::hover#switch_theme { - background-color: #060407; - } - QPushButton::pressed#switch_theme { - background-color:rgb(2, 0, 2); - } - )"; - - QString login_window_dark_purple_theme = R"( - QWidget { - background-color:rgb(9, 6, 10); - } - - QLabel { - background-color: transparent; - font-family: 'Arial'; + color: #f5f5f5; + padding: 2px; font-size: 13px; - color: #9882B9; - padding: 1px; - } - - QPushButton#push_enter { - font-family: 'Arial'; - border-radius: 10px; - background-color: #722548; - color: #060407; - padding: 5px 10px; - } - - QPushButton#push_enter:hover { - background-color:rgb(98, 27, 59) - } - - QPushButton#switch_mode { - font-family: 'Arial'; - border-radius: 10px; - background-color: rgb(42, 10, 25); - color: #9882B9; - padding: 5px 10px; + border-radius: 7px; + font-family: 'Arial' bold; } - - QPushButton#switch_mode:hover { - background-color:rgb(27, 6, 16); + QPushButton#switch_theme:hover { + background-color: rgb(8, 82, 74); + color: #f5f5f5; } - QLineEdit { - border-radius: 10px; - border: 1px solid #221932; - background: #221932; - color: #9882B9; - padding: 5px; - } - - QLineEdit::placeholder { - color: white; - } - - QPushButton#switch_theme { - width: 20px; - height: 20px; - min-width: 20px; - min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #9882B9; - } - QPushButton::hover#switch_theme { - background-color: #9882B9; - } QPushButton::pressed#switch_theme { - background-color:rgb(113, 93, 143); - } - - )"; - - QString login_window_blue_theme = R"( - QWidget { - background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, - stop:0 #173C4C, stop:0.5 #326D6C, stop:1 #07142B); - margin: 0; - padding: 0; - border: none; - } - - QLabel { - background-color: transparent; - font-family: 'Arial'; - font-size: 13px; - color: #BDD1BD; - padding: 1px; - } - - QPushButton#push_enter { - font-family: 'Arial'; - border-radius: 10px; - background-color: #568F7C; - color: #BDD1BD; - padding: 5px 10px; - border: none; - font-weight: bold; - } - - QPushButton#push_enter:hover { - background-color: #326D6C; - } - - QPushButton#push_enter:pressed { - background-color: #07142B; - } - - QPushButton#switch_mode { - font-family: 'Arial'; - border-radius: 10px; - background-color: #326D6C; - color: #BDD1BD; - padding: 5px 10px; - border: 1px solid #568F7C; - } - - QPushButton#switch_mode:hover { - background-color: #568F7C; - color: #07142B; - } - - QLineEdit { - border-radius: 10px; - border: 1px solid #568F7C; - background: #07142B; - color: #BDD1BD; - padding: 5px; - selection-background-color: #326D6C; - } - - QLineEdit::placeholder { - color: #85B093; - opacity: 0.7; - } - - QPushButton#switch_theme { - width: 20px; - height: 20px; - min-width: 20px; - min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #85B093; - } - - QPushButton#switch_theme:hover { - background-color: #85B093; - } - - QPushButton#switch_theme:pressed { - background-color:rgb(107, 141, 118); + background-color:rgb(3, 58, 54); + color: #f5f5f5; } )"; } // namespace Ui \ No newline at end of file diff --git a/ui/authorization-windows/include/registration_window.h b/ui/authorization-windows/include/registration_window.h index 5002971..61c1ef6 100644 --- a/ui/authorization-windows/include/registration_window.h +++ b/ui/authorization-windows/include/registration_window.h @@ -15,14 +15,12 @@ class RegistrationWindow : public QWidget { ~RegistrationWindow() override; bool is_strong_and_valid_password(const QString &password); - static const std::vector THEMES; - void handle_theme_changed(int theme); void handle_language_changed(std::string new_language); private slots: void on_switch_mode_clicked(); void on_push_registration_clicked(); - void on_switch_theme_clicked(); + void on_switch_language_clicked(); private: std::shared_ptr ui; diff --git a/ui/authorization-windows/include/registration_window_style_sheet.h b/ui/authorization-windows/include/registration_window_style_sheet.h index 3a7c0f7..21e2491 100644 --- a/ui/authorization-windows/include/registration_window_style_sheet.h +++ b/ui/authorization-windows/include/registration_window_style_sheet.h @@ -11,9 +11,9 @@ namespace Ui { QLabel { font-family: 'Arial'; background-color: transparent; - font-size: 13px; color: #089083; - padding: 1px; + font-size: 14px; + padding: 12px; } QPushButton#push_registration { @@ -25,7 +25,7 @@ namespace Ui { } QPushButton#switch_mode { - font-family: 'Arial'; + font-family: 'Arial' bold; border-radius: 10px; background-color: white; color: #fea36b; @@ -52,322 +52,24 @@ namespace Ui { color: #727272; } - QPushButton#switch_theme { - width: 20px; - height: 20px; - min-width: 20px; - min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #089083; - } - QPushButton::hover#switch_theme { - background-color: #089083; - } - QPushButton::pressed#switch_theme { - background-color:rgb(7, 110, 100); - } - )"; - - QString registration_window_dark_autumn_theme = R"( - QWidget { - background-color: #202020; - } - - QLabel { - font-family: 'Arial'; - background-color: transparent; - font-size: 13px; - color: #089083; - padding: 1px; - } - - QPushButton#push_registration { - font-family: 'Arial'; - border-radius: 10px; - background-color: #fea36b; - color: #263238; - padding: 5px 10px; - } - - QPushButton#push_registration:hover { - background-color: rgb(225, 133, 76); - } - - QPushButton#switch_mode { - font-family: 'Arial'; - border-radius: 10px; + QPushButton#switch_theme { background-color: #089083; - color: white; - padding: 5px 10px; - } - - QPushButton#switch_mode:hover { - background-color: #01635d; - } - - QLineEdit { - border-radius: 10px; - border: 1px solid rgb(0, 0, 0); - background: rgb(0, 0, 0); - color: #727272; - padding: 5px; - } - - QLineEdit::placeholder { - color: #727272; - } - - QPushButton#switch_theme { - width: 20px; - height: 20px; min-width: 20px; min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #089083; - } - QPushButton::hover#switch_theme { - background-color: #089083; - } - QPushButton::pressed#switch_theme { - background-color:rgb(13, 93, 85); - } - )"; - - QString registration_window_light_purple_theme = R"( - QWidget { - background: qlineargradient(x1:0, y1:0, x2:0, y2:1, - stop:0 #9882B9, stop:0.5 rgb(176, 157, 205), stop:1 rgb(103, 88, 126)); - margin: 0; - padding: 0; - border: none; - } - - QLabel { - font-family: 'Arial'; - background-color: transparent; + color: #f5f5f5; + padding: 2px; font-size: 13px; - color: rgb(42, 10, 25); - padding: 1px; - } - - QPushButton#push_registration { - font-family: 'Arial'; - border-radius: 10px; - background-color: #722548; - color: rgb(206, 193, 224); - padding: 5px 10px; + border-radius: 7px; + font-family: 'Arial' bold; } - - QPushButton#push_registration:hover { - background-color: rgb(98, 27, 59); - } - - QPushButton#switch_mode { - font-family: 'Arial'; - border-radius: 10px; - background-color: rgb(42, 10, 25); - color: rgb(218, 207, 235); - padding: 5px 10px; - } - - QPushButton#switch_mode:hover { - background-color: rgb(27, 6, 16); - } - - QLineEdit { - border-radius: 10px; - border: 1px solid rgb(221, 210, 238); - background: rgb(221, 210, 238); - color: #221932; - padding: 5px; - } - - QLineEdit::placeholder { - color: white; - } - - QPushButton#switch_theme { - width: 20px; - height: 20px; - min-width: 20px; - min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #060407; - } - QPushButton::hover#switch_theme { - background-color: #060407; - } - QPushButton::pressed#switch_theme { - background-color:rgb(2, 0, 2); + QPushButton#switch_theme:hover { + background-color: rgb(8, 82, 74); + color: #f5f5f5; } - )"; - QString registration_window_dark_purple_theme = R"( - QWidget { - background-color: rgb(9, 6, 10); - } - - QLabel { - font-family: 'Arial'; - background-color: transparent; - font-size: 13px; - color: #9882B9; - padding: 1px; - } - - QPushButton#push_registration { - font-family: 'Arial'; - border-radius: 10px; - background-color: #722548; - color: #060407; - padding: 5px 10px; - } - - QPushButton#push_registration:hover { - background-color: rgb(98, 27, 59); - } - - QPushButton#switch_mode { - font-family: 'Arial'; - border-radius: 10px; - background-color: rgb(42, 10, 25); - color: #9882B9; - padding: 5px 10px; - } - - QPushButton#switch_mode:hover { - background-color: rgb(27, 6, 16); - } - - QLineEdit { - border-radius: 10px; - border: 1px solid #221932; - background: #221932; - color: #9882B9; - padding: 5px; - } - - QLineEdit::placeholder { - color: white; - } - - QPushButton#switch_theme { - width: 20px; - height: 20px; - min-width: 20px; - min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #9882B9; - } - QPushButton::hover#switch_theme { - background-color: #9882B9; - } QPushButton::pressed#switch_theme { - background-color:rgb(113, 93, 143); - } - )"; - - QString registration_window_blue_theme = R"( - QWidget { - background: qlineargradient(spread:pad, x1:0, y1:0, x2:0, y2:1, - stop:0 #173C4C, stop:0.5 #326D6C, stop:1 #07142B) !important; - margin: 0; - padding: 0; - border: none; - } - - QLabel { - font-family: 'Arial'; - background-color: transparent; - font-size: 13px; - color: #BDD1BD; - padding: 1px; - } - - QPushButton#push_registration { - font-family: 'Arial'; - border-radius: 10px; - background-color: #568F7C; - color: #BDD1BD; - padding: 5px 10px; - border: none; - font-weight: bold; - } - - QPushButton#push_registration:hover { - background-color: #326D6C; - } - - QPushButton#push_registration:pressed { - background-color: #07142B; - } - - QPushButton#switch_mode { - font-family: 'Arial'; - border-radius: 10px; - background-color: #326D6C; - color: #BDD1BD; - padding: 5px 10px; - border: 1px solid #568F7C; - } - - QPushButton#switch_mode:hover { - background-color: #568F7C; - color: #07142B; - } - - QLineEdit { - border-radius: 10px; - border: 1px solid #568F7C; - background: #07142B; - color: #BDD1BD; - padding: 5px; - selection-background-color: #326D6C; - } - - QLineEdit::placeholder { - color: #85B093; - opacity: 0.7; - } - - QPushButton#switch_theme { - width: 20px; - height: 20px; - min-width: 20px; - min-height: 20px; - max-width: 20px; - max-height: 20px; - border-radius: 7px; - padding: 0; - margin-bottom: 2px; - background-color: transparent; - border: 2px solid #85B093; - } - QPushButton#switch_theme:hover { - background-color: #85B093; - } - QPushButton#switch_theme:pressed { - background-color:rgb(107, 141, 118); + background-color:rgb(3, 58, 54); + color: #f5f5f5; } )"; } // namespace Ui \ No newline at end of file diff --git a/ui/authorization-windows/src/login_window.cpp b/ui/authorization-windows/src/login_window.cpp index a2641ec..0f85af3 100644 --- a/ui/authorization-windows/src/login_window.cpp +++ b/ui/authorization-windows/src/login_window.cpp @@ -9,14 +9,7 @@ #include "language_manager.h" #include #include - -const std::vector LoginWindow::THEMES = { - Ui::login_window_light_autumn_theme, - Ui::login_window_dark_autumn_theme, - Ui::login_window_dark_purple_theme, - Ui::login_window_light_purple_theme, - Ui::login_window_blue_theme -}; +#include LoginWindow::LoginWindow(QWidget *parent) : QWidget(parent), ui(new Ui::LoginWindow) { @@ -27,48 +20,45 @@ LoginWindow::LoginWindow(QWidget *parent) ui->input_password->setPlaceholderText(tr("Введите пароль:")); ui->input_password->setEchoMode(QLineEdit::Password); - connect(ui->switch_theme, &QPushButton::clicked, this, - &LoginWindow::on_switch_theme_clicked, Qt::UniqueConnection); connect(ui->switch_mode, &QPushButton::clicked, this, &LoginWindow::on_switch_mode_clicked); connect(ui->push_enter, &QPushButton::clicked, this, &LoginWindow::on_push_enter_clicked); - connect(StyleManager::instance(), &StyleManager::theme_changed, - this, &LoginWindow::handle_theme_changed); - - handle_theme_changed(StyleManager::instance()->current_theme()); connect(LanguageManager::instance(), &LanguageManager::language_changed, this, &LoginWindow::handle_language_changed ); + connect(ui->switch_theme, &QPushButton::clicked, this, + &LoginWindow::on_switch_language_clicked, Qt::UniqueConnection); handle_language_changed(LanguageManager::instance()->current_language()); + setStyleSheet(Ui::login_window_light_autumn_theme); } void LoginWindow::handle_language_changed(std::string new_language) { if (new_language == "RU") { ui->input_login->setPlaceholderText(tr("Введите логин:")); + ui->enter_label->setText(tr("Вход")); ui->input_password->setPlaceholderText(tr("Введите пароль:")); ui->switch_mode->setText(tr("Еще нет аккаунта? Зарегестрируйтесь!")); - ui->switch_theme->setText(tr("Тема")); + ui->switch_theme->setText(tr("RU")); ui->push_enter->setText(tr("Войти")); } else if (new_language == "EN") { ui->input_login->setPlaceholderText(tr("Enter login:")); + ui->enter_label->setText(tr("Enter")); ui->input_password->setPlaceholderText(tr("Enter password:")); ui->switch_mode->setText(tr("Don't have an account yet? Register!")); - ui->switch_theme->setText(tr("Theme")); + ui->switch_theme->setText(tr("EN")); ui->push_enter->setText(tr("Login")); } } - -void LoginWindow::handle_theme_changed(int theme) { - this->setStyleSheet(THEMES[theme]); -} - -void LoginWindow::on_switch_theme_clicked() { - if ((this->counter_on_switch_theme_clicks++) % 2) { - int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; - StyleManager::instance()->apply_theme(next_theme); +void LoginWindow::on_switch_language_clicked() { + if (ui->switch_theme->text() == tr("RU")) { + ui->switch_theme->setText(tr("EN")); + LanguageManager::instance()->apply_language("EN"); + } else { + ui->switch_theme->setText(tr("RU")); + LanguageManager::instance()->apply_language("RU"); } } diff --git a/ui/authorization-windows/src/registration_window.cpp b/ui/authorization-windows/src/registration_window.cpp index 9db5a3c..13cce80 100644 --- a/ui/authorization-windows/src/registration_window.cpp +++ b/ui/authorization-windows/src/registration_window.cpp @@ -6,14 +6,7 @@ #include "style_manager.h" #include "language_manager.h" #include "registration_window_style_sheet.h" - -const std::vector RegistrationWindow::THEMES = { - Ui::registration_window_light_autumn_theme, - Ui::registration_window_dark_autumn_theme, - Ui::registration_window_dark_purple_theme, - Ui::registration_window_light_purple_theme, - Ui::registration_window_blue_theme -}; +#include RegistrationWindow::RegistrationWindow(QWidget *parent) : QWidget(parent), ui(new Ui::RegistrationWindow) { @@ -28,51 +21,48 @@ RegistrationWindow::RegistrationWindow(QWidget *parent) setAttribute(Qt::WA_StyledBackground, true); - connect(ui->switch_theme, &QPushButton::clicked, this, - &RegistrationWindow::on_switch_theme_clicked, Qt::UniqueConnection); connect(ui->push_registration, &QPushButton::clicked, this, &RegistrationWindow::on_push_registration_clicked, Qt::UniqueConnection); connect(ui->switch_mode, &QPushButton::clicked, this, - &RegistrationWindow::on_switch_mode_clicked, Qt::UniqueConnection); - connect(StyleManager::instance(), &StyleManager::theme_changed, - this, &RegistrationWindow::handle_theme_changed); - - handle_theme_changed(StyleManager::instance()->current_theme()); + &RegistrationWindow::on_switch_mode_clicked, Qt::UniqueConnection); + connect(ui->switch_theme, &QPushButton::clicked, this, + &RegistrationWindow::on_switch_language_clicked, Qt::UniqueConnection); + connect(LanguageManager::instance(), &LanguageManager::language_changed, this, &RegistrationWindow::handle_language_changed ); handle_language_changed(LanguageManager::instance()->current_language()); + this->setStyleSheet(Ui::registration_window_light_autumn_theme); } void RegistrationWindow::handle_language_changed(std::string new_language) { if (new_language == "RU") { ui->create_login->setPlaceholderText(tr("Введите логин:")); + ui->registration_label->setText(tr("Регистрация")); ui->create_password->setPlaceholderText(tr("Введите пароль:")); ui->repeat_password->setPlaceholderText(tr("Повторите пароль:")); ui->switch_mode->setText(tr("Уже есть аккаунт? Войдите!")); - ui->switch_theme->setText(tr("Тема")); - ui->push_registration->setText(tr("Already have an account? Login!")); + ui->switch_theme->setText(tr("RU")); + ui->push_registration->setText(tr("Зарегистрироваться")); } else if (new_language == "EN") { ui->create_login->setPlaceholderText(tr("Enter login:")); + ui->registration_label->setText(tr("Registration")); ui->create_password->setPlaceholderText(tr("Enter password:")); ui->repeat_password->setPlaceholderText(tr("Repeat password:")); - ui->switch_mode->setText(tr("Back")); - ui->switch_theme->setText(tr("Theme")); + ui->switch_mode->setText(tr("Already have an account? Login!")); + ui->switch_theme->setText(tr("EN")); ui->push_registration->setText(tr("Register")); } } - - -void RegistrationWindow::handle_theme_changed(int theme) { - this->setStyleSheet(THEMES[theme]); -} - -void RegistrationWindow::on_switch_theme_clicked() { - if ((this->counter_on_switch_theme_clicks++)%2) { - int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; - StyleManager::instance()->apply_theme(next_theme); +void RegistrationWindow::on_switch_language_clicked() { + if (ui->switch_theme->text() == tr("RU")) { + ui->switch_theme->setText(tr("EN")); + LanguageManager::instance()->apply_language("EN"); + } else { + ui->switch_theme->setText(tr("RU")); + LanguageManager::instance()->apply_language("RU"); } } diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index 1f95a61..645940c 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -48,13 +48,13 @@ MainWindow::MainWindow( : QWidget(parent), username(username), main_layout_(new QVBoxLayout(this)), - top_bar_(new BottomBar(this, username, tr("EFFICIO :: Task-Tracker"))), + top_bar_(new BottomBar(this, username, "EFFICIO :: Task-Tracker")), content_layout_(new QHBoxLayout(this)), project_list_(new ProjectList(this)), note_list_(new NoteList(this)), content_widget_(new QWidget(this)), - new_project_button_(new QPushButton(tr("Новый проект"), this)), - new_note_button_(new QPushButton(tr("Новая заметка"), this)), + new_project_button_(new QPushButton("Новый проект", this)), + new_note_button_(new QPushButton("Новая заметка", this)), storage_(storage) { this->setObjectName("main-window"); this->setAttribute(Qt::WA_StyledBackground); @@ -98,26 +98,23 @@ MainWindow::MainWindow( StyleManager::instance(), &StyleManager::font_size_changed, this, &MainWindow::handle_font_size_changed ); - handle_theme_changed(StyleManager::instance()->current_theme()); - connect(StyleManager::instance(), &StyleManager::font_size_changed, - this, &Ui::MainWindow::handle_font_size_changed - ); - handle_font_size_changed(StyleManager::instance()->current_font_size()); connect(LanguageManager::instance(), &LanguageManager::language_changed, this, &MainWindow::handle_language_changed ); + handle_theme_changed(StyleManager::instance()->current_theme()); + handle_font_size_changed(StyleManager::instance()->current_font_size()); handle_language_changed(LanguageManager::instance()->current_language()); } void MainWindow::handle_language_changed(std::string new_language) { if (new_language == "RU") { - new_project_button_->setText(tr("Новый проект")); - new_note_button_->setText(tr("Новая заметка")); + new_project_button_->setText("Новый проект"); + new_note_button_->setText("Новая заметка"); } else if(new_language == "EN") { - new_project_button_->setText(tr("New project")); - new_note_button_->setText(tr("New note")); + new_project_button_->setText("New project"); + new_note_button_->setText("New note"); } } @@ -172,21 +169,36 @@ void MainWindow::on_profile_button_click() { void MainWindow::add_project() { bool ok; - QString name_of_project = QInputDialog::getText( - nullptr, tr("Название проекта:"), tr("Введите название"), QLineEdit::Normal, "", - &ok - ); - if (ok) { - int id = 0; + QString name_of_project; + if (LanguageManager::instance()->current_language() == "RU") { + name_of_project = QInputDialog::getText( + nullptr, "Название проекта:", "Введите название", QLineEdit::Normal, "", + &ok + ); + } else if (LanguageManager::instance()->current_language() == "EN") { + name_of_project = QInputDialog::getText( + nullptr, "Name of project:", "Create a name", QLineEdit::Normal, "", + &ok + ); + } + if (ok && name_of_project.trimmed()== ""){ + if (LanguageManager::instance()->current_language() == "RU") { + QMessageBox::warning(this, "Ошибка", "Введите название!"); + } else { + QMessageBox::warning(this, "Error", "Please enter a name!"); + } + } else if (ok){ + int id = 0; - if (DB::ProjectDAO::create_project(name_of_project.toStdString(), id)) { + if (DB::ProjectDAO::create_project(name_of_project.trimmed().toStdString(), id)) { LRDao::add_project_to_user(username, id); auto &project = storage_->add_project( - Project(id, name_of_project.toStdString(), "") + Project(id, name_of_project.trimmed().toStdString(), "") ); project_list_->add_project(&project); } } + handle_font_size_changed(StyleManager::instance()->current_font_size()); } void MainWindow::add_note() { @@ -198,14 +210,19 @@ void MainWindow::add_note() { project_item->project_->get_id(), id ); auto ¬e = - project_item->project_->add_note({id, tr("Пустая заметка").toStdString(), ""}); + project_item->project_->add_note({id, "Пустая заметка", ""}); note_list_->add_note_widget(¬e); } } else { QMessageBox msg; - msg.setText(tr("Проект не выбран!")); + if (LanguageManager::instance()->current_language() == "RU") { + msg.setText("Сперва выберите проект!"); + } else if (LanguageManager::instance()->current_language() == "EN") { + msg.setText("Choose a project first!"); + } msg.exec(); } + handle_font_size_changed(StyleManager::instance()->current_font_size()); } } // namespace Ui \ No newline at end of file diff --git a/ui/note-widget/include/note_edit_dialog.h b/ui/note-widget/include/note_edit_dialog.h index 62f6286..14dde57 100644 --- a/ui/note-widget/include/note_edit_dialog.h +++ b/ui/note-widget/include/note_edit_dialog.h @@ -38,6 +38,7 @@ private slots: void on_add_members_button_click(); void on_add_tags_button_click(); void on_switch_theme_button_click(); + void on_delete_button_click(); private: void init_basic_fields(); @@ -54,6 +55,7 @@ private slots: [[nodiscard]] bool try_save_note() const; Ui::NoteEditDialog* ui_{}; + QPushButton *deleteButton; std::vector> member_avatars_; std::vector> tag_labels_; QList selected_tags_; diff --git a/ui/note-widget/include/note_edit_dialog_styles.h b/ui/note-widget/include/note_edit_dialog_styles.h index 385fea9..898475f 100644 --- a/ui/note-widget/include/note_edit_dialog_styles.h +++ b/ui/note-widget/include/note_edit_dialog_styles.h @@ -76,7 +76,17 @@ QString note_edit_dialog_light_autumn_theme = R"( background-color: #dadada; } - /* Боковое меню */ + QPushButton#deleteButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: white; + color: #fea36b; + padding: 5px 10px; + } + + QPushButton#deleteButton:hover { + background-color: #dadada; + } QPushButton#joinButton, QPushButton#addMembersButton, @@ -112,8 +122,6 @@ QString note_edit_dialog_light_autumn_theme = R"( color: #727272; } - /* Дополнительные элементы заметки */ - QDateEdit#dateEdit { font-family: 'Arial'; border-radius: 5px; @@ -132,8 +140,6 @@ QString note_edit_dialog_light_autumn_theme = R"( border-radius: 5px; } - /* Окно с сообщением */ - QMessageBox { background-color: #ffffff; } @@ -251,6 +257,18 @@ QString note_edit_dialog_dark_autumn_theme = R"( background-color: #01635d; } + QPushButton#deleteButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: #089083; + color: white; + padding: 5px 10px; + } + + QPushButton#deleteButton:hover { + background-color: #01635d; + } + QPushButton#joinButton, QPushButton#addMembersButton, QPushButton#addDateButton, @@ -419,6 +437,18 @@ QString note_edit_dialog_light_purple_theme = R"( background-color: rgb(27, 6, 16); } + QPushButton#deleteButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: rgb(218, 207, 235); + padding: 5px 10px; + } + + QPushButton#deleteButton:hover { + background-color: rgb(27, 6, 16); + } + QPushButton#joinButton, QPushButton#addMembersButton, QPushButton#addDateButton, @@ -586,6 +616,18 @@ QString note_edit_dialog_dark_purple_theme = R"( background-color: rgb(27, 6, 16); } + QPushButton#deleteButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: rgb(42, 10, 25); + color: #9882B9; + padding: 5px 10px; + } + + QPushButton#deleteButton:hover { + background-color: rgb(27, 6, 16); + } + QPushButton#joinButton, QPushButton#addMembersButton, QPushButton#addDateButton, @@ -762,6 +804,20 @@ QString note_edit_dialog_blue_theme = R"( color: #07142B; } + QPushButton#deleteButton { + font-family: 'Arial'; + border-radius: 10px; + background-color: #326D6C; + color: #BDD1BD; + padding: 5px 10px; + border: 1px solid #568F7C; + } + + QPushButton#deleteButton:hover { + background-color: #568F7C; + color: #07142B; + } + QPushButton#joinButton, QPushButton#addMembersButton, QPushButton#addDateButton, diff --git a/ui/note-widget/src/note_edit_dialog.cpp b/ui/note-widget/src/note_edit_dialog.cpp index d621718..e1fe52e 100644 --- a/ui/note-widget/src/note_edit_dialog.cpp +++ b/ui/note-widget/src/note_edit_dialog.cpp @@ -25,10 +25,13 @@ const std::vector NoteEditDialog::THEMES = { NoteEditDialog::NoteEditDialog(QWidget* parent, Note* note) : QDialog(parent), ui_(new Ui::NoteEditDialog), - note_(note) { + note_(note), + deleteButton(new QPushButton("Удалить", this)) { ui_->setupUi(this); setWindowTitle("EFFICIO"); + deleteButton->setGeometry(width() - 80, height() - 40, 100, width() - 100); + deleteButton->setFixedSize(100, 30); init_basic_fields(); init_additional_fields(); setup_connections(); @@ -121,31 +124,46 @@ void NoteEditDialog::setup_connections() { void NoteEditDialog::handle_language_changed(std::string new_language) { if (new_language == "RU") { setWindowTitle("EFFICIO"); - ui_->saveButton->setText(tr("Сохранить")); - ui_->cancelButton->setText(tr("Отмена")); - ui_->joinButton->setText(ui_->membersLabel->isVisible() ? tr("Покинуть") : tr("Присоединиться")); - ui_->addMembersButton->setText(tr("Добавить участников")); - ui_->addDateButton->setText(tr("Добавить дату")); - ui_->addTagsButton->setText(tr("Добавить теги")); - ui_->projectNameLabel->setText(tr("Проект:")); - ui_->descriptionLabel->setText(tr("Описание:")); - ui_->descriptionTextEdit->setText(tr("Добавьте подробное описание вашей заметки")); - ui_->sidePanelLabel->setText(tr("Участники:")); - ui_->sidePanelLabel_2->setText(tr("Теги:")); + ui_->saveButton->setText("Сохранить"); + deleteButton->setText("Удалить"); + ui_->dateLabel->setText("Срок"); + ui_->cancelButton->setText("Отмена"); + ui_->joinButton->setText(ui_->membersLabel->isVisible() ? "Покинуть" : "Присоединиться"); + ui_->addMembersButton->setText("Добавить участников"); + ui_->addDateButton->setText("Добавить дату"); + ui_->addTagsButton->setText("Добавить теги"); + ui_->projectNameLabel->setText("Проект:"); + ui_->descriptionLabel->setText("Описание:"); + if(note_->get_title() == "" or note_->get_title() == "Empty note"){ + ui_->titleLineEdit->setText("Пустая заметка"); + } + if(note_->get_text() == "" or note_->get_text() == "Add a detailed description of your note"){ + ui_->descriptionTextEdit->setPlaceholderText("Добавьте подробное описание вашей заметки"); + } + ui_->sidePanelLabel->setText("Участники:"); + ui_->sidePanelLabel_2->setText("Теги:"); } else if(new_language == "EN") { setWindowTitle("EFFICIO"); - ui_->saveButton->setText(tr("Save")); - ui_->cancelButton->setText(tr("Cancel")); - ui_->joinButton->setText(ui_->membersLabel->isVisible() ? tr("Leave") : tr("Join")); - ui_->addMembersButton->setText(tr("Add members")); - ui_->addDateButton->setText(tr("Add date")); - ui_->descriptionTextEdit->setText(tr("Add a detailed description of your note")); - ui_->addTagsButton->setText(tr("Add tags")); - ui_->projectNameLabel->setText(tr("Project:")); - ui_->descriptionLabel->setText(tr("Description:")); - ui_->sidePanelLabel->setText(tr("Members:")); - ui_->sidePanelLabel_2->setText(tr("Tags:")); + ui_->saveButton->setText("Save"); + ui_->dateLabel->setText("Deadline"); + deleteButton->setText("Delete"); + ui_->cancelButton->setText("Cancel"); + ui_->joinButton->setText(ui_->membersLabel->isVisible() ? "Leave" : "Join"); + ui_->addMembersButton->setText("Add members"); + ui_->addDateButton->setText("Add date"); + ui_->addTagsButton->setText("Add tags"); + ui_->projectNameLabel->setText("Project:"); + ui_->descriptionLabel->setText("Description:"); + if(note_->get_title() == "" or note_->get_title() == "Пустая заметка"){ + ui_->titleLineEdit->setText("Empty note"); + } + + if(note_->get_text() == "" or note_->get_text() == "Добавьте подробное описание вашей заметки"){ + ui_->descriptionTextEdit->setPlaceholderText("Add a detailed description of your note"); + } + ui_->sidePanelLabel->setText("Members:"); + ui_->sidePanelLabel_2->setText("Tags:"); } } @@ -202,6 +220,22 @@ void NoteEditDialog::on_save_button_click() { close(); } +void NoteEditDialog::on_delete_button_click() { + QMessageBox::StandardButton reply = QMessageBox::question( + this, + tr("Удаление заметки"), + tr("Вы уверены, что хотите удалить заметку?"), + QMessageBox::Yes | QMessageBox::No + ); + + if (reply == QMessageBox::Yes) { // здесь должен выполняться запрос на удаление заметки + this->deleteLater(); + } else if (reply == QMessageBox::Yes) { + QMessageBox::critical(this, tr("Ошибка"), tr("Не удалось удалить заметку")); + } + close(); +} + void NoteEditDialog::on_join_button_click() { const bool is_joined = ui_->membersLabel->isVisible(); ui_->membersLabel->setVisible(!is_joined); diff --git a/ui/settings-window/include/settings_window_style_sheet.h b/ui/settings-window/include/settings_window_style_sheet.h index 0c4bc68..416d05d 100644 --- a/ui/settings-window/include/settings_window_style_sheet.h +++ b/ui/settings-window/include/settings_window_style_sheet.h @@ -23,38 +23,38 @@ namespace Ui { font-size: 35px; } - QPushButton#language_button { + QPushButton#switch_theme { background-color: #fea36b; width: 50px; height: 30px; color: #f5f5f5; padding: 2px; - font-size: 20px; + font-size: 15px; border-radius: 7px; } - QPushButton#language_button:hover { + QPushButton#switch_theme:hover { background-color:rgb(245, 148, 89); } - QPushButton#language_button:pressed { + QPushButton#switch_theme:pressed { background-color:rgb(238, 122, 50); } - QPushButton#theme_button { + QPushButton#language_button { background-color: #089083; width: 50px; height: 30px; color: #f5f5f5; padding: 2px; - font-size: 15px; + font-size: 20px; border-radius: 7px; } - QPushButton#theme_button:hover { + QPushButton#language_button:hover { background-color: rgb(8, 82, 74); color: #f5f5f5; } - QPushButton::pressed#switch_theme { + QPushButton::pressed#language_button { background-color:rgb(3, 58, 54); color: #f5f5f5; } diff --git a/ui/style-manager/src/style_manager.cpp b/ui/style-manager/src/style_manager.cpp index 0dc6ca4..8cf6c93 100644 --- a/ui/style-manager/src/style_manager.cpp +++ b/ui/style-manager/src/style_manager.cpp @@ -28,10 +28,10 @@ int StyleManager::current_theme() const { } void StyleManager::apply_font_size(std::string font_size_) { - this->current_font_size_ = font_size_; - emit font_size_changed(this->current_font_size_); + current_font_size_ = font_size_; + emit font_size_changed(current_font_size_); } std::string StyleManager::current_font_size() const { - return this->current_font_size_; + return current_font_size_; } \ No newline at end of file From 43e671ce6f466192015b4a369b35e355e456f01d Mon Sep 17 00:00:00 2001 From: Anastasiya Date: Tue, 3 Jun 2025 16:34:15 +0300 Subject: [PATCH 14/17] Delete switch_theme_button, add delete_button --- ui/note-widget/ui/note_edit_dialog.ui | 48 +++++++++++++++------------ 1 file changed, 26 insertions(+), 22 deletions(-) diff --git a/ui/note-widget/ui/note_edit_dialog.ui b/ui/note-widget/ui/note_edit_dialog.ui index e0057f3..615a90b 100644 --- a/ui/note-widget/ui/note_edit_dialog.ui +++ b/ui/note-widget/ui/note_edit_dialog.ui @@ -363,29 +363,33 @@ - - - - 660 - 440 - 20 - 20 - - - - - 20 - 20 - - - - - 20 - 20 - - + + + + 610 + 409 + 70 + 45 + + + + + 70 + 45 + + + + + Arial + 11 + true + + + + Удалить + - \ No newline at end of file + From d4ba50e97687c516a21b7351df9e395f9906ba15 Mon Sep 17 00:00:00 2001 From: Anastasiya Date: Tue, 3 Jun 2025 16:44:38 +0300 Subject: [PATCH 15/17] Delete delete_button --- ui/note-widget/ui/note_edit_dialog.ui | 26 -------------------------- 1 file changed, 26 deletions(-) diff --git a/ui/note-widget/ui/note_edit_dialog.ui b/ui/note-widget/ui/note_edit_dialog.ui index 615a90b..d82f559 100644 --- a/ui/note-widget/ui/note_edit_dialog.ui +++ b/ui/note-widget/ui/note_edit_dialog.ui @@ -363,32 +363,6 @@ - - - - 610 - 409 - 70 - 45 - - - - - 70 - 45 - - - - - Arial - 11 - true - - - - Удалить - - From 427985745eabb0242cf4b9e92a9679053502330e Mon Sep 17 00:00:00 2001 From: MuravAna Date: Sun, 8 Jun 2025 15:59:18 +0300 Subject: [PATCH 16/17] Add draft of types of notes --- database/src/database_manager.cpp | 2 + database/src/note_dao.cpp | 18 +- scripts/include/note.hpp | 3 + scripts/src/note.cpp | 8 + ui/analytics-window/src/analytics_window.cpp | 212 +----------------- ui/main-window/include/main_window_style.hpp | 42 +++- ui/main-window/include/mainwindow.h | 8 +- ui/main-window/include/notelist.h | 8 +- ui/main-window/include/notewidget.h | 13 +- ui/main-window/include/projectitem.h | 4 +- ui/main-window/src/mainwindow.cpp | 74 ++++-- ui/main-window/src/notelist.cpp | 29 +-- ui/main-window/src/notewidget.cpp | 65 ++++-- ui/note-widget/include/note_edit_dialog.h | 3 - ui/note-widget/src/note_edit_dialog.cpp | 55 ++--- .../include/settings_window_style_sheet.h | 6 +- 16 files changed, 231 insertions(+), 319 deletions(-) diff --git a/database/src/database_manager.cpp b/database/src/database_manager.cpp index ad5b9ec..72a801a 100644 --- a/database/src/database_manager.cpp +++ b/database/src/database_manager.cpp @@ -13,10 +13,12 @@ DatabaseManager::DatabaseManager() { database_.open(); QSqlQuery query(database_); + query.exec( "CREATE TABLE IF NOT EXISTS notes (" "id SERIAL PRIMARY KEY, " "title TEXT NOT NULL, " + "type TEXT NOT NULL, " "content TEXT, " "members VARCHAR(50)[], " "date VARCHAR(50), " diff --git a/database/src/note_dao.cpp b/database/src/note_dao.cpp index 369f192..950bd3c 100644 --- a/database/src/note_dao.cpp +++ b/database/src/note_dao.cpp @@ -6,8 +6,8 @@ bool NoteDao::initialize_note(int &id) { QSqlQuery query; const auto is_successful = DatabaseManager::get_instance().execute_query( query, - "INSERT INTO notes (title, content) " - "VALUES ('Пустая заметка', '')" + "INSERT INTO notes (title, type, content) " + "VALUES ('Пустая заметка', 'actual', '')" "RETURNING id" ); if (is_successful && query.next()) { @@ -23,6 +23,7 @@ bool NoteDao::update_note(const Note ¬e) { const QString sql_query = "UPDATE notes SET " "title = :title, " + "type = :type, " "content = :content, " "members = :members, " "date = :date, " @@ -31,6 +32,7 @@ bool NoteDao::update_note(const Note ¬e) { const QVariantList params = { QString::fromStdString(note.get_title()), QString::fromStdString(note.get_text()), + QString::fromStdString(note.get_type()), convert_string_set_to_postgres_array(note.get_members()), QString::fromStdString(note.get_date()), convert_tags_to_postgres_array(note.get_tags()), @@ -58,6 +60,7 @@ std::vector NoteDao::get_all_notes() { while (query.next()) { auto id = query.value("id").toUInt(); auto title = query.value("title").toString().toStdString(); + auto type = query.value("type").toString().toStdString(); auto text = query.value("content").toString().toStdString(); notes.emplace_back(id, title, text); } @@ -68,14 +71,15 @@ std::vector NoteDao::get_all_notes() { Note NoteDao::get_note_by_id(int id) { QSqlQuery query; DatabaseManager::get_instance().execute_query( - query, "SELECT title, content, array_to_string(tags, ','), date, array_to_string(members, ',') FROM notes WHERE id = ?", {id} + query, "SELECT title, type, content, array_to_string(tags, ','), date, array_to_string(members, ',') FROM notes WHERE id = ?", {id} ); query.next(); auto title = query.value(0).toString().toStdString(); - auto text = query.value(1).toString().toStdString(); - auto date = query.value(3).toString().toStdString(); + auto type = query.value(1).toString().toStdString(); + auto text = query.value(2).toString().toStdString(); + auto date = query.value(4).toString().toStdString(); Note result{id, title, text}; - auto tags_list = query.value(2).toString().split(","); + auto tags_list = query.value(3).toString().split(","); if (!tags_list.empty() && tags_list[0] != "") { for (const auto& tag_str : tags_list) { @@ -83,7 +87,7 @@ Note NoteDao::get_note_by_id(int id) { result.add_tag(tag_str.split(':')[0].toStdString(), tag_str.split(':')[1].toStdString()); } } - auto member_list = query.value(4).toString().split(","); + auto member_list = query.value(5).toString().split(","); if (!member_list.empty() && member_list[0] != "") { for (const auto& member : member_list) { result.add_member(member.toStdString()); diff --git a/scripts/include/note.hpp b/scripts/include/note.hpp index e54e01a..4568a6f 100644 --- a/scripts/include/note.hpp +++ b/scripts/include/note.hpp @@ -20,11 +20,13 @@ class Note { [[nodiscard]] const std::string &get_title() const; [[nodiscard]] const std::string &get_text() const; [[nodiscard]] const std::string &get_date() const; + [[nodiscard]] const std::string &get_type() const; [[nodiscard]] const std::vector &get_tags() const; [[nodiscard]] const std::unordered_set &get_members() const; void set_title(const std::string &title); void set_text(const std::string &text); + void set_type(const std::string &type); void add_tag(const std::string &tag, const std::string &color = "#e7624b"); void set_date(const std::string &date); void add_member(const std::string &member); @@ -37,6 +39,7 @@ class Note { std::string title_; std::string text_; std::string date_; + std::string type_; std::vector tags_; std::unordered_set members_; }; diff --git a/scripts/src/note.cpp b/scripts/src/note.cpp index dcb8391..8ea7d0e 100644 --- a/scripts/src/note.cpp +++ b/scripts/src/note.cpp @@ -20,6 +20,10 @@ Note::Note(const int id, std::string title, std::string text) return text_; } +[[nodiscard]] const std::string &Note::get_type() const { + return type_; +} + const std::string &Note::get_date() const { return date_; } @@ -40,6 +44,10 @@ void Note::set_text(const std::string &text) { text_ = text; } +void Note::set_type(const std::string &type) { + type_ = type; +} + void Note::add_tag(const std::string &tag, const std::string &color) { tags_.push_back({tag, color}); } diff --git a/ui/analytics-window/src/analytics_window.cpp b/ui/analytics-window/src/analytics_window.cpp index aec7e19..e20c464 100644 --- a/ui/analytics-window/src/analytics_window.cpp +++ b/ui/analytics-window/src/analytics_window.cpp @@ -155,214 +155,4 @@ void AnalyticsWindow::handle_theme_changed(int theme) { void AnalyticsWindow::on_switch_theme_clicked() { int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; StyleManager::instance()->apply_theme(next_theme); -} - - - - - - -// #include "analytics_window.h" -// #include "style_manager.h" -// #include "language_manager.h" -// #include "analytics_window_style_sheet.h" -// #include - -// const std::vector AnalyticsWindow::THEMES = { -// Ui::analytics_window_light_autumn_theme, -// Ui::analytics_window_dark_autumn_theme, -// Ui::analytics_window_dark_purple_theme, -// Ui::analytics_window_light_purple_theme, -// Ui::analytics_window_blue_theme -// }; - -// AnalyticsWindow::AnalyticsWindow(QWidget *parent) -// : QDialog(parent) -// { -// QVBoxLayout *main_layout = new QVBoxLayout(this); - -// tab_widget = new QTabWidget(this); - -// QWidget *tasks_tab = new QWidget(); -// tasks_layout = new QVBoxLayout(tasks_tab); -// tab_widget->addTab(tasks_tab, "Статистика задач"); - -// QWidget *projects_tab = new QWidget(); -// projects_layout = new QVBoxLayout(projects_tab); -// tab_widget->addTab(projects_tab, "Распределение по проектам"); - -// button_box = new QDialogButtonBox(QDialogButtonBox::Close, this); -// connect(button_box, &QDialogButtonBox::rejected, this, &QDialog::reject); - -// main_layout->addWidget(tab_widget); -// main_layout->addWidget(button_box); - -// setWindowTitle("Аналитическая панель"); -// resize(800, 600); - -// setTasksData(0, 0, 0); - -// QMap projects; -// setProjectsData(projects); - -// connect(StyleManager::instance(), &StyleManager::theme_changed, -// this, &AnalyticsWindow::handle_theme_changed); -// handle_theme_changed(StyleManager::instance()->current_theme()); -// connect(StyleManager::instance(), &StyleManager::font_size_changed, -// this, &AnalyticsWindow::handle_font_size_changed -// ); -// handle_font_size_changed(StyleManager::instance()->current_font_size()); - -// connect(LanguageManager::instance(), &LanguageManager::language_changed, -// this, &AnalyticsWindow::handle_language_changed -// ); -// handle_language_changed(LanguageManager::instance()->current_language()); -// } - - -// void AnalyticsWindow::handle_language_changed(std::string new_language) { -// if (new_language == "RU") { -// tab_widget->setTabText(0, tr("Статистика задач")); -// tab_widget->setTabText(1, tr("Распределение по проектам")); -// setWindowTitle(tr("Аналитическая панель")); - -// QChart *tasks_chart = static_cast(tasks_layout->itemAt(0)->widget())->chart(); -// tasks_chart->setTitle(tr("Статистика задач за период")); -// static_cast(tasks_chart->axes(Qt::Vertical)[0])->setTitleText(tr("Количество")); - -// QBarSeries *tasks_series = static_cast(tasks_chart->series()[0]); -// static_cast(tasks_series->barSets()[0])->setLabel(tr("Создано")); -// static_cast(tasks_series->barSets()[1])->setLabel(tr("Завершено")); -// static_cast(tasks_series->barSets()[2])->setLabel(tr("Просрочено")); - -// button_box->button(QDialogButtonBox::Close)->setText(tr("Закрыть")); -// } -// else if(new_language == "EN") { -// tab_widget->setTabText(0, tr("Tasks Statistics")); -// tab_widget->setTabText(1, tr("Projects Distribution")); -// setWindowTitle(tr("Analytics Panel")); - -// QChart *tasks_chart = static_cast(tasks_layout->itemAt(0)->widget())->chart(); -// tasks_chart->setTitle(tr("Tasks Statistics for Period")); -// static_cast(tasks_chart->axes(Qt::Vertical)[0])->setTitleText(tr("Count")); - -// QBarSeries *tasks_series = static_cast(tasks_chart->series()[0]); -// static_cast(tasks_series->barSets()[0])->setLabel(tr("Created")); -// static_cast(tasks_series->barSets()[1])->setLabel(tr("Completed")); -// static_cast(tasks_series->barSets()[2])->setLabel(tr("Overdue")); - -// button_box->button(QDialogButtonBox::Close)->setText(tr("Close")); -// } -// } - -// void AnalyticsWindow::handle_font_size_changed(std::string font_size) { - -// QString font_size_rule; -// if(font_size == "small") { -// font_size_rule = "QPushButton { font-size: 11px; }"; -// } -// else if(font_size == "medium") { -// font_size_rule = "QPushButton { font-size: 13px; }"; -// } -// else if(font_size == "big") { -// font_size_rule = "QPushButton { font-size: 15px; }"; -// } - -// this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_size_rule); -// } - -// void AnalyticsWindow::handle_theme_changed(int theme) { -// this->setStyleSheet(THEMES[theme]); -// } - -// void AnalyticsWindow::on_switch_theme_clicked() { -// int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; -// StyleManager::instance()->apply_theme(next_theme); -// } - -// AnalyticsWindow::~AnalyticsWindow(){} - -// void AnalyticsWindow::setTasksData(int created, int completed, int overdue) -// { -// QLayoutItem *child; -// while (child = tasks_layout->takeAt(0)) { -// delete child->widget(); -// delete child; -// } - -// QChart *chart = createTasksChart(created, completed, overdue); -// tasks_layout->addWidget(new QChartView(chart)); -// } - -// void AnalyticsWindow::setProjectsData(const QMap& projects) -// { -// QLayoutItem *child; -// while (child = projects_layout->takeAt(0)) { -// delete child->widget(); -// delete child; -// } - -// QChart *chart = createProjectsChart(projects); -// projects_layout->addWidget(new QChartView(chart)); -// } - -// QChart* AnalyticsWindow::createTasksChart(int created, int completed, int overdue) -// { -// QBarSet *created_set = new QBarSet("Создано"); -// *created_set << created; - -// QBarSet *completed_set = new QBarSet("Завершено"); -// *completed_set << completed; - -// QBarSet *overdue_set = new QBarSet("Просрочено"); -// *overdue_set << overdue; - -// QBarSeries *series = new QBarSeries(); -// series->append(created_set); -// series->append(completed_set); -// series->append(overdue_set); - -// QChart *chart = new QChart(); -// chart->addSeries(series); -// chart->setTitle("Статистика задач за период"); -// chart->setAnimationOptions(QChart::SeriesAnimations); - -// QBarCategoryAxis *axisX = new QBarCategoryAxis(); -// axisX->append("Тип задач"); -// chart->addAxis(axisX, Qt::AlignBottom); -// series->attachAxis(axisX); - -// QValueAxis *axisY = new QValueAxis(); -// int maxValue = qMax(created, qMax(completed, overdue)); -// axisY->setRange(0, maxValue + (maxValue * 0.1)); // +10% отмакс. значения -// axisY->setTitleText("Количество"); -// chart->addAxis(axisY, Qt::AlignLeft); -// series->attachAxis(axisY); - -// return chart; -// } - -// QChart* AnalyticsWindow::createProjectsChart(const QMap& projects) -// { -// QPieSeries *series = new QPieSeries(); - -// int total = 0; -// for (auto it = projects.begin(); it != projects.end(); ++it) { -// series->append(it.key(), it.value()); -// total += it.value(); -// } - -// series->setLabelsVisible(); -// foreach(QPieSlice *slice, series->slices()) { -// slice->setLabel(QString("%1 (%2%)") -// .arg(slice->label()) -// .arg(100 * slice->percentage(), 0, 'f', 1)); -// } - -// QChart *chart = new QChart(); -// chart->addSeries(series); -// chart->setTitle(QString("Распределение задач (%1 всего)").arg(total)); -// chart->legend()->setAlignment(Qt::AlignRight); - -// return chart; -// } \ No newline at end of file +} \ No newline at end of file diff --git a/ui/main-window/include/main_window_style.hpp b/ui/main-window/include/main_window_style.hpp index 6d79340..54cb417 100644 --- a/ui/main-window/include/main_window_style.hpp +++ b/ui/main-window/include/main_window_style.hpp @@ -103,7 +103,7 @@ QScrollArea { } #BottomBar { - background-color: rgb(33, 44, 50); + background-color: #212c32; border-radius: 8px; padding: 8px; outline: 0; @@ -131,9 +131,47 @@ QScrollArea { font-size: 13px; } +QTabWidget { + background-color: white; + border-radius: 8px; + padding: 5px; +} + +QTabWidget::pane { + background-color: white; + border-radius: 8px; + margin-top: 5px; +} + +QTabBar::tab { + color: rgb(33, 44, 50); + font-family: 'Arial'; + font-size: 13px; + font-weight: bold; + background: #e0e0e0; + padding: 6px 8px; + border-top-right-radius: 4px; + border-top-left-radius: 4px; + margin-right: 2px; +} + +QTabBar::tab:hover { + background: #e8e8e8; +} + +QTabBar::tab:selected { + background: white; + border-bottom-color: white; +} + +QTabBar::tab:pressed { + background: white; + border-bottom-color: white; +} + #NoteList { - border-radius : 8px; background-color: white; + border-radius: 8px; } #NoteWidget { diff --git a/ui/main-window/include/mainwindow.h b/ui/main-window/include/mainwindow.h index 31207fc..94788f0 100644 --- a/ui/main-window/include/mainwindow.h +++ b/ui/main-window/include/mainwindow.h @@ -13,6 +13,7 @@ #include "projectlist.h" #include "storage.hpp" #include +#include #include "profile_window.h" namespace Ui { @@ -25,10 +26,14 @@ class MainWindow : public QWidget { std::string username; std::string font_size_ = "medium"; QVBoxLayout *main_layout_; + QTabWidget* tab_widget_; BottomBar *top_bar_; QHBoxLayout *content_layout_; ProjectList *project_list_; - NoteList *note_list_; + NoteList *actual_notes_; + NoteList *overdue_notes_ ; + NoteList *completed_notes_; + NoteList *deleted_notes_; QWidget *content_widget_; QPushButton *new_project_button_; QPushButton *new_note_button_; @@ -55,6 +60,7 @@ private slots: void handle_theme_changed(int theme); void handle_language_changed(std::string new_language); void handle_font_size_changed(std::string font_size_); + QScrollArea* create_scroll_area(NoteList* note_list); }; } // namespace Ui #endif // MAINWINDOW_H \ No newline at end of file diff --git a/ui/main-window/include/notelist.h b/ui/main-window/include/notelist.h index f406536..a5ad5c5 100644 --- a/ui/main-window/include/notelist.h +++ b/ui/main-window/include/notelist.h @@ -5,7 +5,8 @@ #include #include #include "note.hpp" - +#include "notewidget.h" +#include "projectitem.h" namespace Ui { class NoteList : public QWidget { friend class MainWindow; @@ -16,11 +17,12 @@ class NoteList : public QWidget { std::vector vertical_layouts_; int note_counter_ = 0; + const std::string type_; public: - void add_note_widget(const project_storage_model::Note *note); + void add_note_widget(const project_storage_model::Note *note, QListWidgetItem *p); void clear_note_list(); - NoteList(QWidget *parent); + NoteList(QWidget *parent, const std::string type_); public slots: void load_project_notes(QListWidgetItem *project); diff --git a/ui/main-window/include/notewidget.h b/ui/main-window/include/notewidget.h index d7c28b9..6a182f6 100644 --- a/ui/main-window/include/notewidget.h +++ b/ui/main-window/include/notewidget.h @@ -7,6 +7,7 @@ #include #include #include "note.hpp" +#include "projectitem.h" namespace Ui { class NoteWidget : public QWidget { @@ -14,6 +15,7 @@ class NoteWidget : public QWidget { const project_storage_model::Note *model_note_; QVBoxLayout *main_layout_; QPushButton *open_button_; + QPushButton *delete_button_; QLabel *title_label_; QLabel *text_label_; @@ -21,15 +23,22 @@ class NoteWidget : public QWidget { explicit NoteWidget( QWidget *parent = nullptr, const project_storage_model::Note *model_note = nullptr, - int number_of_theme_ = 0 + const std::string type = "actual", + QListWidgetItem *p = nullptr ); - int number_of_theme; + std::string type_; + QListWidgetItem *project_; void handle_font_size_changed(std::string font_size_); void handle_language_changed(std::string new_language); + QListWidgetItem* get_project() const; private slots: void open_note_window() const; + void delete_note(); + void change_type(std::string new_type); +signals: + void change_type_requested(QListWidgetItem *project); }; } // namespace Ui #endif // NOTEWIDGET_H \ No newline at end of file diff --git a/ui/main-window/include/projectitem.h b/ui/main-window/include/projectitem.h index 8b4a4a2..c439f4b 100644 --- a/ui/main-window/include/projectitem.h +++ b/ui/main-window/include/projectitem.h @@ -7,9 +7,11 @@ #include "project.hpp" namespace Ui { + +class NoteWidget; class ProjectItem : public QListWidgetItem { project_storage_model::Project *project_; - friend NoteList; + friend class NoteList; friend class MainWindow; public: diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index 645940c..c8fa5c8 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -9,7 +9,6 @@ #include #include #include -#include #include #include #include @@ -51,34 +50,68 @@ MainWindow::MainWindow( top_bar_(new BottomBar(this, username, "EFFICIO :: Task-Tracker")), content_layout_(new QHBoxLayout(this)), project_list_(new ProjectList(this)), - note_list_(new NoteList(this)), + actual_notes_(new NoteList(this, "actual")), + overdue_notes_(new NoteList(this, "overdue")), + completed_notes_(new NoteList(this, "completed")), + deleted_notes_(new NoteList(this, "deleted")), content_widget_(new QWidget(this)), new_project_button_(new QPushButton("Новый проект", this)), new_note_button_(new QPushButton("Новая заметка", this)), - storage_(storage) { + storage_(storage), + tab_widget_(new QTabWidget(this)) { this->setObjectName("main-window"); this->setAttribute(Qt::WA_StyledBackground); + + tab_widget_->addTab(create_scroll_area(actual_notes_), "Актуальные"); + tab_widget_->addTab(create_scroll_area(overdue_notes_), "Просроченные"); + tab_widget_->addTab(create_scroll_area(completed_notes_), "Выполненные"); + tab_widget_->addTab(create_scroll_area(deleted_notes_), "Удаленные"); + + tab_widget_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); + + actual_notes_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); + overdue_notes_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); + completed_notes_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); + deleted_notes_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); + main_layout_->addWidget(top_bar_, Qt::AlignTop); main_layout_->setAlignment(Qt::AlignCenter); - main_layout_->addWidget(content_widget_); - content_widget_->setLayout(content_layout_); - auto right_layout = new QVBoxLayout(content_widget_); + + + QWidget* right_panel = new QWidget(this); + QVBoxLayout* right_layout = new QVBoxLayout(right_panel); + //right_layout->setContentsMargins(0, 34, 0, 0); // Верхний отступ 10px right_layout->addWidget(project_list_); right_layout->addWidget(new_project_button_); right_layout->addWidget(new_note_button_); - QScrollArea* scrollArea = new QScrollArea(content_widget_); - scrollArea->setWidgetResizable(true); - scrollArea->setWidget(note_list_); - content_layout_->addWidget(scrollArea, Qt::AlignRight); - content_layout_->addLayout(right_layout); - main_layout_->addWidget(content_widget_); - this->setLayout(main_layout_); - this->project_list_->load_projects(storage); + right_panel->setFixedWidth(210); + tab_widget_->tabBar()->setExpanding(true); + + content_layout_->addWidget(tab_widget_); + content_layout_->addWidget(right_panel); + main_layout_->addWidget(top_bar_); + main_layout_->addLayout(content_layout_); + + project_list_->load_projects(storage); + + connect( + project_list_, &QListWidget::itemClicked, actual_notes_, + &NoteList::load_project_notes + ); connect( - project_list_, &QListWidget::itemClicked, note_list_, + project_list_, &QListWidget::itemClicked, overdue_notes_, &NoteList::load_project_notes ); + connect( + project_list_, &QListWidget::itemClicked, completed_notes_, + &NoteList::load_project_notes + ); + connect( + project_list_, &QListWidget::itemClicked, deleted_notes_, + &NoteList::load_project_notes + ); + connect( new_note_button_, &QPushButton::clicked, this, &Ui::MainWindow::add_note ); @@ -106,6 +139,14 @@ MainWindow::MainWindow( handle_language_changed(LanguageManager::instance()->current_language()); } +QScrollArea* MainWindow::create_scroll_area(NoteList* note_list) { + QScrollArea* scrollArea = new QScrollArea(); + scrollArea->setWidgetResizable(true); + scrollArea->setWidget(note_list); + scrollArea->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); + scrollArea->setFrameShape(QFrame::NoFrame); + return scrollArea; +} void MainWindow::handle_language_changed(std::string new_language) { if (new_language == "RU") { @@ -211,7 +252,7 @@ void MainWindow::add_note() { ); auto ¬e = project_item->project_->add_note({id, "Пустая заметка", ""}); - note_list_->add_note_widget(¬e); + actual_notes_->add_note_widget(¬e, project_list_->currentItem()); } } else { QMessageBox msg; @@ -222,7 +263,6 @@ void MainWindow::add_note() { } msg.exec(); } - handle_font_size_changed(StyleManager::instance()->current_font_size()); } } // namespace Ui \ No newline at end of file diff --git a/ui/main-window/src/notelist.cpp b/ui/main-window/src/notelist.cpp index 4af7558..52992c4 100644 --- a/ui/main-window/src/notelist.cpp +++ b/ui/main-window/src/notelist.cpp @@ -5,19 +5,18 @@ #include #include #include "note.hpp" -#include "notewidget.h" -#include "projectitem.h" namespace Ui { -NoteList::NoteList(QWidget *parent) +NoteList::NoteList(QWidget *parent, const std::string type) : QWidget(parent), main_layout_(new QHBoxLayout(this)), - vertical_layouts_(std::vector()){ + vertical_layouts_(std::vector()), + type_(type) { this->setAttribute(Qt::WA_StyledBackground); this->setObjectName("NoteList"); this->setLayout(main_layout_); - vertical_layouts_.resize(4, nullptr); + vertical_layouts_.resize(3, nullptr); for (auto &layout : vertical_layouts_) { layout = new QVBoxLayout(this); @@ -25,15 +24,20 @@ NoteList::NoteList(QWidget *parent) } } -void NoteList::add_note_widget(const project_storage_model::Note *note) { - auto current_layout = vertical_layouts_[note_counter_ % 4]; +void NoteList::add_note_widget(const project_storage_model::Note *note, QListWidgetItem *project) { + auto current_layout = vertical_layouts_[note_counter_ % 3]; if (current_layout->count() > 1) { current_layout->removeItem( current_layout->itemAt(current_layout->count() - 1) ); } - vertical_layouts_[note_counter_ % 4]->addWidget( - new NoteWidget(this, note), 0, Qt::AlignTop + auto* new_note = new NoteWidget(this, note, this->type_, project); + vertical_layouts_[note_counter_ % 3]->addWidget( + new_note, 0, Qt::AlignTop + ); + connect( + new_note, &NoteWidget::change_type_requested, + this, &NoteList::load_project_notes ); current_layout->addStretch(); note_counter_++; @@ -41,14 +45,11 @@ void NoteList::add_note_widget(const project_storage_model::Note *note) { void NoteList::load_project_notes(QListWidgetItem *project) { ProjectItem *p = dynamic_cast(project); - assert(p != nullptr); - qDebug() << "Адрес проекта" - << QString::fromStdString(p->project_->get_name()) << ":" - << p->project_; this->clear_note_list(); note_counter_ = 0; for (const auto ¬e : p->project_->get_notes()) { - this->add_note_widget(¬e); + if (note.get_type() == this->type_) + this->add_note_widget(¬e, project); } } diff --git a/ui/main-window/src/notewidget.cpp b/ui/main-window/src/notewidget.cpp index 21f4cc6..6f2d47d 100644 --- a/ui/main-window/src/notewidget.cpp +++ b/ui/main-window/src/notewidget.cpp @@ -6,21 +6,27 @@ #include "note_edit_dialog.h" #include "style_manager.h" #include "language_manager.h" +#include namespace Ui { NoteWidget::NoteWidget( QWidget *parent, const project_storage_model::Note *model_note, - int number_of_theme_ + const std::string type, + QListWidgetItem *p ) : QWidget(parent), model_note_(model_note), main_layout_(new QVBoxLayout(this)), open_button_(new QPushButton(tr("Открыть"))), - number_of_theme(number_of_theme_) { + delete_button_(new QPushButton(tr("Удалить"))), + type_(type), + project_(p) +{ this->setObjectName("NoteWidget"); this->setMinimumWidth(100); this->setFixedHeight(100); + title_label_ = new QLabel(QString::fromStdString(model_note_->get_title()), this); text_label_ = new QLabel(QString::fromStdString(model_note_->get_text()), this); @@ -34,11 +40,23 @@ NoteWidget::NoteWidget( title_label_->setWordWrap(false); text_label_->setTextInteractionFlags(Qt::TextSelectableByMouse); - main_layout_->addWidget(open_button_); + QHBoxLayout *buttons_layout = new QHBoxLayout; + + buttons_layout->addWidget(open_button_); + buttons_layout->addWidget(delete_button_); + + if (type_ == "deleted"){ + delete_button_->setText("Восстановить"); + } + + main_layout_->addLayout(buttons_layout); connect( open_button_, &QPushButton::clicked, this, &NoteWidget::open_note_window ); + connect( + delete_button_, &QPushButton::clicked, this, &NoteWidget::delete_note + ); connect( StyleManager::instance(), &StyleManager::font_size_changed, this, &NoteWidget::handle_font_size_changed @@ -49,6 +67,7 @@ NoteWidget::NoteWidget( this, &NoteWidget::handle_language_changed ); handle_language_changed(LanguageManager::instance()->current_language()); + handle_font_size_changed(StyleManager::instance()->current_font_size()); } void NoteWidget::handle_language_changed(std::string new_language) { @@ -57,18 +76,22 @@ void NoteWidget::handle_language_changed(std::string new_language) { if (title_label_->text() == "Empty note") { title_label_->setText("Пустая заметка"); } - // if (text_label_->text() == "Add a detailed description of your note") { - // title_label_->setText("Добавьте подробное описание вашей заметки"); - // } + if (type_ == "deleted"){ + delete_button_->setText("Восстановить"); + } else { + delete_button_->setText("Удалить"); + } } else if (new_language == "EN") { open_button_->setText(tr("Open")); if (title_label_->text() == "Пустая заметка") { title_label_->setText("Empty note"); } - // if (text_label_->text() == "Добавьте подробное описание вашей заметки") { - // title_label_->setText("Add a detailed description of your note"); - // } + if (type_ == "deleted"){ + delete_button_->setText("Восстановить"); + } else { + delete_button_->setText("Удалить"); + } } } @@ -76,15 +99,12 @@ void NoteWidget::handle_font_size_changed(std::string font_size_){ QString font_rule; if (font_size_ == "small") { title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 13px;"); - // text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 11px;"); } else if (font_size_ == "medium") { title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); - // text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 13px;"); } else if (font_size_ == "big") { title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 17px;"); - // text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); } } @@ -95,8 +115,27 @@ void NoteWidget::open_note_window() const { ); dialog->setAttribute(Qt::WA_DeleteOnClose); dialog->exec(); -// text_label_->setText(QString::fromStdString(model_note_->get_text())); title_label_->setText(QString::fromStdString(model_note_->get_title())); main_layout_->update(); } + +void NoteWidget::change_type(std::string new_type) { + type_ = new_type; + handle_language_changed(LanguageManager::instance()->current_language()); + main_layout_->update(); + emit change_type_requested(this->project_); +} + +void NoteWidget::delete_note() { + if(type_ == "deleted"){ + this->change_type("actual"); + } else { + this->change_type("deleted"); + } +} + +QListWidgetItem* NoteWidget::get_project() const{ + return this->project_; +} + } // namespace Ui \ No newline at end of file diff --git a/ui/note-widget/include/note_edit_dialog.h b/ui/note-widget/include/note_edit_dialog.h index 14dde57..6a4948a 100644 --- a/ui/note-widget/include/note_edit_dialog.h +++ b/ui/note-widget/include/note_edit_dialog.h @@ -37,8 +37,6 @@ private slots: void on_join_button_click(); void on_add_members_button_click(); void on_add_tags_button_click(); - void on_switch_theme_button_click(); - void on_delete_button_click(); private: void init_basic_fields(); @@ -55,7 +53,6 @@ private slots: [[nodiscard]] bool try_save_note() const; Ui::NoteEditDialog* ui_{}; - QPushButton *deleteButton; std::vector> member_avatars_; std::vector> tag_labels_; QList selected_tags_; diff --git a/ui/note-widget/src/note_edit_dialog.cpp b/ui/note-widget/src/note_edit_dialog.cpp index e1fe52e..08d9aed 100644 --- a/ui/note-widget/src/note_edit_dialog.cpp +++ b/ui/note-widget/src/note_edit_dialog.cpp @@ -25,13 +25,10 @@ const std::vector NoteEditDialog::THEMES = { NoteEditDialog::NoteEditDialog(QWidget* parent, Note* note) : QDialog(parent), ui_(new Ui::NoteEditDialog), - note_(note), - deleteButton(new QPushButton("Удалить", this)) { + note_(note) { ui_->setupUi(this); setWindowTitle("EFFICIO"); - deleteButton->setGeometry(width() - 80, height() - 40, 100, width() - 100); - deleteButton->setFixedSize(100, 30); init_basic_fields(); init_additional_fields(); setup_connections(); @@ -51,11 +48,6 @@ void NoteEditDialog::init_basic_fields() { ui_->descriptionTextEdit->setText(QString::fromStdString(note_->get_text())); } -void NoteEditDialog::on_switch_theme_button_click() { - int next_theme = (StyleManager::instance()->current_theme() + 1) % 5; - StyleManager::instance()->apply_theme(next_theme); -} - NoteEditDialog::~NoteEditDialog() { delete ui_; @@ -106,9 +98,6 @@ void NoteEditDialog::setup_connections() { ui_->dateLabel->setVisible(!is_visible); ui_->dateEdit->setVisible(!is_visible); }); - connect(ui_->switch_theme, &QPushButton::clicked, this, - &NoteEditDialog::on_switch_theme_button_click - ); connect(StyleManager::instance(), &StyleManager::theme_changed, this, &NoteEditDialog::handle_theme_changed); connect(ui_->addTagsButton, &QPushButton::clicked, this, &NoteEditDialog::on_add_tags_button_click); @@ -125,14 +114,13 @@ void NoteEditDialog::handle_language_changed(std::string new_language) { if (new_language == "RU") { setWindowTitle("EFFICIO"); ui_->saveButton->setText("Сохранить"); - deleteButton->setText("Удалить"); ui_->dateLabel->setText("Срок"); ui_->cancelButton->setText("Отмена"); ui_->joinButton->setText(ui_->membersLabel->isVisible() ? "Покинуть" : "Присоединиться"); - ui_->addMembersButton->setText("Добавить участников"); - ui_->addDateButton->setText("Добавить дату"); - ui_->addTagsButton->setText("Добавить теги"); - ui_->projectNameLabel->setText("Проект:"); + ui_->addMembersButton->setText("Участники"); + ui_->addDateButton->setText("Дата"); + ui_->addTagsButton->setText("Теги"); + ui_->projectNameLabel->setText("Проект:" ); ui_->descriptionLabel->setText("Описание:"); if(note_->get_title() == "" or note_->get_title() == "Empty note"){ ui_->titleLineEdit->setText("Пустая заметка"); @@ -140,19 +128,18 @@ void NoteEditDialog::handle_language_changed(std::string new_language) { if(note_->get_text() == "" or note_->get_text() == "Add a detailed description of your note"){ ui_->descriptionTextEdit->setPlaceholderText("Добавьте подробное описание вашей заметки"); } - ui_->sidePanelLabel->setText("Участники:"); - ui_->sidePanelLabel_2->setText("Теги:"); + ui_->sidePanelLabel->setText("Добавить к заметке"); + ui_->sidePanelLabel_2->setText("Предложения"); } else if(new_language == "EN") { setWindowTitle("EFFICIO"); ui_->saveButton->setText("Save"); - ui_->dateLabel->setText("Deadline"); - deleteButton->setText("Delete"); + ui_->dateLabel->setText("Deadline"); ui_->cancelButton->setText("Cancel"); ui_->joinButton->setText(ui_->membersLabel->isVisible() ? "Leave" : "Join"); - ui_->addMembersButton->setText("Add members"); - ui_->addDateButton->setText("Add date"); - ui_->addTagsButton->setText("Add tags"); + ui_->addMembersButton->setText("Members"); + ui_->addDateButton->setText("Date"); + ui_->addTagsButton->setText("Tags"); ui_->projectNameLabel->setText("Project:"); ui_->descriptionLabel->setText("Description:"); if(note_->get_title() == "" or note_->get_title() == "Пустая заметка"){ @@ -162,8 +149,8 @@ void NoteEditDialog::handle_language_changed(std::string new_language) { if(note_->get_text() == "" or note_->get_text() == "Добавьте подробное описание вашей заметки"){ ui_->descriptionTextEdit->setPlaceholderText("Add a detailed description of your note"); } - ui_->sidePanelLabel->setText("Members:"); - ui_->sidePanelLabel_2->setText("Tags:"); + ui_->sidePanelLabel->setText("Add to note"); + ui_->sidePanelLabel_2->setText("Suggestions"); } } @@ -220,22 +207,6 @@ void NoteEditDialog::on_save_button_click() { close(); } -void NoteEditDialog::on_delete_button_click() { - QMessageBox::StandardButton reply = QMessageBox::question( - this, - tr("Удаление заметки"), - tr("Вы уверены, что хотите удалить заметку?"), - QMessageBox::Yes | QMessageBox::No - ); - - if (reply == QMessageBox::Yes) { // здесь должен выполняться запрос на удаление заметки - this->deleteLater(); - } else if (reply == QMessageBox::Yes) { - QMessageBox::critical(this, tr("Ошибка"), tr("Не удалось удалить заметку")); - } - close(); -} - void NoteEditDialog::on_join_button_click() { const bool is_joined = ui_->membersLabel->isVisible(); ui_->membersLabel->setVisible(!is_joined); diff --git a/ui/settings-window/include/settings_window_style_sheet.h b/ui/settings-window/include/settings_window_style_sheet.h index 416d05d..be57728 100644 --- a/ui/settings-window/include/settings_window_style_sheet.h +++ b/ui/settings-window/include/settings_window_style_sheet.h @@ -23,7 +23,7 @@ namespace Ui { font-size: 35px; } - QPushButton#switch_theme { + QPushButton#theme_button { background-color: #fea36b; width: 50px; height: 30px; @@ -33,10 +33,10 @@ namespace Ui { border-radius: 7px; } - QPushButton#switch_theme:hover { + QPushButton#theme_button:hover { background-color:rgb(245, 148, 89); } - QPushButton#switch_theme:pressed { + QPushButton#theme_button:pressed { background-color:rgb(238, 122, 50); } From 43b749aab981a45f71b869eaa0190b6a04e5ba0f Mon Sep 17 00:00:00 2001 From: mirotvoretts Date: Sun, 8 Jun 2025 16:31:39 +0300 Subject: [PATCH 17/17] feat: display project name in note edit window --- ui/main-window/include/bottombar.h | 10 +- ui/main-window/include/main_window_style.hpp | 1 - ui/main-window/include/mainwindow.h | 14 +- ui/main-window/include/notelist.h | 6 +- ui/main-window/include/notewidget.h | 2 +- ui/main-window/include/projectitem.h | 2 + ui/main-window/src/bottombar.cpp | 18 +- ui/main-window/src/mainwindow.cpp | 134 ++++++------ ui/main-window/src/notelist.cpp | 21 +- ui/main-window/src/notewidget.cpp | 58 +++--- ui/note-widget/include/note_edit_dialog.h | 16 +- ui/note-widget/include/tags_dialog.h | 3 +- ui/note-widget/include/tags_dialog_styles.h | 2 +- ui/note-widget/src/note_edit_dialog.cpp | 202 ++++++++++++------- ui/note-widget/src/tags_dialog.cpp | 36 ++-- ui/note-widget/ui/note_edit_dialog.ui | 1 - 16 files changed, 305 insertions(+), 221 deletions(-) diff --git a/ui/main-window/include/bottombar.h b/ui/main-window/include/bottombar.h index 0663d39..8ac2cb7 100644 --- a/ui/main-window/include/bottombar.h +++ b/ui/main-window/include/bottombar.h @@ -4,9 +4,9 @@ #include #include #include +#include #include #include -#include namespace Ui { class BottomBar : public QWidget { @@ -15,18 +15,18 @@ class BottomBar : public QWidget { public: BottomBar( QWidget *parent, - const std::string& username, + const std::string &username, QString project_name ); - + signals: - void profile_button_clicked(); + void profile_button_clicked(); private: QHBoxLayout *main_layout_; QLabel *project_name_; QLabel *username_; - QPushButton *profile_button_; + QPushButton *profile_button_; }; } // namespace Ui diff --git a/ui/main-window/include/main_window_style.hpp b/ui/main-window/include/main_window_style.hpp index 54cb417..5651dc5 100644 --- a/ui/main-window/include/main_window_style.hpp +++ b/ui/main-window/include/main_window_style.hpp @@ -428,7 +428,6 @@ QString main_window_dark_autumn_theme = R"( } )"; - QString main_window_light_purple_theme = R"( #main-window { background: #9882B9; diff --git a/ui/main-window/include/mainwindow.h b/ui/main-window/include/mainwindow.h index 94788f0..24fb581 100644 --- a/ui/main-window/include/mainwindow.h +++ b/ui/main-window/include/mainwindow.h @@ -6,18 +6,18 @@ #include #include #include +#include #include #include +#include #include "bottombar.h" #include "notelist.h" +#include "profile_window.h" #include "projectlist.h" #include "storage.hpp" -#include -#include -#include "profile_window.h" namespace Ui { - class MainWindow; +class MainWindow; } namespace Ui { @@ -26,12 +26,12 @@ class MainWindow : public QWidget { std::string username; std::string font_size_ = "medium"; QVBoxLayout *main_layout_; - QTabWidget* tab_widget_; + QTabWidget *tab_widget_; BottomBar *top_bar_; QHBoxLayout *content_layout_; ProjectList *project_list_; NoteList *actual_notes_; - NoteList *overdue_notes_ ; + NoteList *overdue_notes_; NoteList *completed_notes_; NoteList *deleted_notes_; QWidget *content_widget_; @@ -60,7 +60,7 @@ private slots: void handle_theme_changed(int theme); void handle_language_changed(std::string new_language); void handle_font_size_changed(std::string font_size_); - QScrollArea* create_scroll_area(NoteList* note_list); + QScrollArea *create_scroll_area(NoteList *note_list); }; } // namespace Ui #endif // MAINWINDOW_H \ No newline at end of file diff --git a/ui/main-window/include/notelist.h b/ui/main-window/include/notelist.h index a5ad5c5..534d837 100644 --- a/ui/main-window/include/notelist.h +++ b/ui/main-window/include/notelist.h @@ -7,6 +7,7 @@ #include "note.hpp" #include "notewidget.h" #include "projectitem.h" + namespace Ui { class NoteList : public QWidget { friend class MainWindow; @@ -20,7 +21,10 @@ class NoteList : public QWidget { const std::string type_; public: - void add_note_widget(const project_storage_model::Note *note, QListWidgetItem *p); + void add_note_widget( + const project_storage_model::Note *note, + QListWidgetItem *p + ); void clear_note_list(); NoteList(QWidget *parent, const std::string type_); diff --git a/ui/main-window/include/notewidget.h b/ui/main-window/include/notewidget.h index 6a182f6..a0f31b9 100644 --- a/ui/main-window/include/notewidget.h +++ b/ui/main-window/include/notewidget.h @@ -30,7 +30,7 @@ class NoteWidget : public QWidget { QListWidgetItem *project_; void handle_font_size_changed(std::string font_size_); void handle_language_changed(std::string new_language); - QListWidgetItem* get_project() const; + QListWidgetItem *get_project() const; private slots: diff --git a/ui/main-window/include/projectitem.h b/ui/main-window/include/projectitem.h index c439f4b..c74ceef 100644 --- a/ui/main-window/include/projectitem.h +++ b/ui/main-window/include/projectitem.h @@ -9,10 +9,12 @@ namespace Ui { class NoteWidget; + class ProjectItem : public QListWidgetItem { project_storage_model::Project *project_; friend class NoteList; friend class MainWindow; + friend class NoteWidget; public: ProjectItem(QListWidget *listview, project_storage_model::Project *project); diff --git a/ui/main-window/src/bottombar.cpp b/ui/main-window/src/bottombar.cpp index 8b5052d..1407c5d 100644 --- a/ui/main-window/src/bottombar.cpp +++ b/ui/main-window/src/bottombar.cpp @@ -2,19 +2,17 @@ #include #include #include -#include namespace Ui { BottomBar::BottomBar( QWidget *parent, - const std::string& username, + const std::string &username, QString project_name ) : QWidget(parent), main_layout_(new QHBoxLayout()), project_name_(new QLabel(project_name)), - profile_button_(new QPushButton(username.c_str())) -{ + profile_button_(new QPushButton(username.c_str())) { this->setObjectName("BottomBar"); this->setLayout(main_layout_); this->setFixedHeight(40); @@ -22,14 +20,16 @@ BottomBar::BottomBar( profile_button_->setObjectName("profile_button"); project_name_->setAlignment(Qt::AlignLeft | Qt::AlignVCenter); - + main_layout_->addWidget(project_name_); - main_layout_->addStretch(); + main_layout_->addStretch(); main_layout_->addWidget(profile_button_); - connect(profile_button_, &QPushButton::clicked, - this, &BottomBar::profile_button_clicked); - + connect( + profile_button_, &QPushButton::clicked, this, + &BottomBar::profile_button_clicked + ); + this->setLayout(main_layout_); this->setAttribute(Qt::WA_StyledBackground); } diff --git a/ui/main-window/src/mainwindow.cpp b/ui/main-window/src/mainwindow.cpp index c8fa5c8..d956e3e 100644 --- a/ui/main-window/src/mainwindow.cpp +++ b/ui/main-window/src/mainwindow.cpp @@ -1,19 +1,22 @@ #include "mainwindow.h" +#include #include #include #include #include +#include #include -#include -#include #include +#include +#include #include #include #include -#include -#include +#include #include "applicationwindow.h" #include "bottombar.h" +#include "language_manager.h" +#include "login_window.h" #include "lr_dao.hpp" #include "main_window_style.hpp" #include "note_dao.hpp" @@ -22,20 +25,14 @@ #include "project_dao.hpp" #include "projectitem.h" #include "projectlist.h" -#include "style_manager.h" -#include "language_manager.h" #include "registration_window.h" -#include "login_window.h" -#include -#include +#include "style_manager.h" namespace Ui { const std::vector MainWindow::THEMES = { - Ui::main_window_light_autumn_theme, - Ui::main_window_dark_autumn_theme, - Ui::main_window_dark_purple_theme, - Ui::main_window_light_purple_theme, + Ui::main_window_light_autumn_theme, Ui::main_window_dark_autumn_theme, + Ui::main_window_dark_purple_theme, Ui::main_window_light_purple_theme, Ui::main_window_blue_theme }; @@ -66,27 +63,34 @@ MainWindow::MainWindow( tab_widget_->addTab(create_scroll_area(overdue_notes_), "Просроченные"); tab_widget_->addTab(create_scroll_area(completed_notes_), "Выполненные"); tab_widget_->addTab(create_scroll_area(deleted_notes_), "Удаленные"); - + tab_widget_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); - - actual_notes_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); - overdue_notes_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); - completed_notes_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); - deleted_notes_->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); + + actual_notes_->setSizePolicy( + QSizePolicy::Expanding, QSizePolicy::Expanding + ); + overdue_notes_->setSizePolicy( + QSizePolicy::Expanding, QSizePolicy::Expanding + ); + completed_notes_->setSizePolicy( + QSizePolicy::Expanding, QSizePolicy::Expanding + ); + deleted_notes_->setSizePolicy( + QSizePolicy::Expanding, QSizePolicy::Expanding + ); main_layout_->addWidget(top_bar_, Qt::AlignTop); main_layout_->setAlignment(Qt::AlignCenter); - - QWidget* right_panel = new QWidget(this); - QVBoxLayout* right_layout = new QVBoxLayout(right_panel); - //right_layout->setContentsMargins(0, 34, 0, 0); // Верхний отступ 10px + QWidget *right_panel = new QWidget(this); + QVBoxLayout *right_layout = new QVBoxLayout(right_panel); + // right_layout->setContentsMargins(0, 34, 0, 0); // Верхний отступ 10px right_layout->addWidget(project_list_); right_layout->addWidget(new_project_button_); right_layout->addWidget(new_note_button_); right_panel->setFixedWidth(210); tab_widget_->tabBar()->setExpanding(true); - + content_layout_->addWidget(tab_widget_); content_layout_->addWidget(right_panel); @@ -120,27 +124,28 @@ MainWindow::MainWindow( &Ui::MainWindow::add_project ); connect( - top_bar_, &Ui::BottomBar::profile_button_clicked, - this, &MainWindow::on_profile_button_click + top_bar_, &Ui::BottomBar::profile_button_clicked, this, + &MainWindow::on_profile_button_click ); connect( - StyleManager::instance(), &StyleManager::theme_changed, - this, &MainWindow::handle_theme_changed + StyleManager::instance(), &StyleManager::theme_changed, this, + &MainWindow::handle_theme_changed ); connect( - StyleManager::instance(), &StyleManager::font_size_changed, - this, &MainWindow::handle_font_size_changed + StyleManager::instance(), &StyleManager::font_size_changed, this, + &MainWindow::handle_font_size_changed ); - connect(LanguageManager::instance(), &LanguageManager::language_changed, - this, &MainWindow::handle_language_changed + connect( + LanguageManager::instance(), &LanguageManager::language_changed, this, + &MainWindow::handle_language_changed ); handle_theme_changed(StyleManager::instance()->current_theme()); handle_font_size_changed(StyleManager::instance()->current_font_size()); handle_language_changed(LanguageManager::instance()->current_language()); } -QScrollArea* MainWindow::create_scroll_area(NoteList* note_list) { - QScrollArea* scrollArea = new QScrollArea(); +QScrollArea *MainWindow::create_scroll_area(NoteList *note_list) { + QScrollArea *scrollArea = new QScrollArea(); scrollArea->setWidgetResizable(true); scrollArea->setWidget(note_list); scrollArea->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); @@ -152,8 +157,7 @@ void MainWindow::handle_language_changed(std::string new_language) { if (new_language == "RU") { new_project_button_->setText("Новый проект"); new_note_button_->setText("Новая заметка"); - } - else if(new_language == "EN") { + } else if (new_language == "EN") { new_project_button_->setText("New project"); new_note_button_->setText("New note"); } @@ -174,37 +178,45 @@ void MainWindow::handle_theme_changed(int theme) { } void MainWindow::handle_font_size_changed(std::string font_size_) { - QString font_rule; if (font_size_ == "small") { - font_rule = "#ProjectList, #BottomBar QLabel, #BottomBar QPushButton, #NoteWidget QPushButton, QPushButton { font-size: 11px; }"; - } - else if (font_size_ == "medium") { - font_rule = "#ProjectList, #BottomBar QLabel, #BottomBar QPushButton, #NoteWidget QPushButton, QPushButton { font-size: 13px; }"; - } - else if (font_size_ == "big") { - font_rule = "#ProjectList, #BottomBar QLabel, #BottomBar QPushButton, #NoteWidget QPushButton, QPushButton { font-size: 15px; }"; + font_rule = + "#ProjectList, #BottomBar QLabel, #BottomBar QPushButton, " + "#NoteWidget QPushButton, QPushButton { font-size: 11px; }"; + } else if (font_size_ == "medium") { + font_rule = + "#ProjectList, #BottomBar QLabel, #BottomBar QPushButton, " + "#NoteWidget QPushButton, QPushButton { font-size: 13px; }"; + } else if (font_size_ == "big") { + font_rule = + "#ProjectList, #BottomBar QLabel, #BottomBar QPushButton, " + "#NoteWidget QPushButton, QPushButton { font-size: 15px; }"; } - this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_rule); + this->setStyleSheet( + THEMES[StyleManager::instance()->current_theme()] + font_rule + ); } void MainWindow::on_profile_button_click() { this->setEnabled(false); - ProfileWindow *new_profile_window = new ProfileWindow(QString::fromStdString(this->username), this->parentWidget()); + ProfileWindow *new_profile_window = new ProfileWindow( + QString::fromStdString(this->username), this->parentWidget() + ); new_profile_window->setAttribute(Qt::WA_DeleteOnClose); connect( - new_profile_window, &ProfileWindow::logout_requested, - this, &MainWindow::on_logout_button_click + new_profile_window, &ProfileWindow::logout_requested, this, + &MainWindow::on_logout_button_click ); connect( - new_profile_window, &ProfileWindow::delete_account_requested, - this, &MainWindow::on_delete_account_button_click - ); - connect(new_profile_window, &ProfileWindow::destroyed, - this, [this]() { this->setEnabled(true); }); + new_profile_window, &ProfileWindow::delete_account_requested, this, + &MainWindow::on_delete_account_button_click + ); + connect(new_profile_window, &ProfileWindow::destroyed, this, [this]() { + this->setEnabled(true); + }); new_profile_window->show(); - new_profile_window->raise(); + new_profile_window->raise(); new_profile_window->activateWindow(); } @@ -213,8 +225,8 @@ void MainWindow::add_project() { QString name_of_project; if (LanguageManager::instance()->current_language() == "RU") { name_of_project = QInputDialog::getText( - nullptr, "Название проекта:", "Введите название", QLineEdit::Normal, "", - &ok + nullptr, "Название проекта:", "Введите название", QLineEdit::Normal, + "", &ok ); } else if (LanguageManager::instance()->current_language() == "EN") { name_of_project = QInputDialog::getText( @@ -222,16 +234,18 @@ void MainWindow::add_project() { &ok ); } - if (ok && name_of_project.trimmed()== ""){ + if (ok && name_of_project.trimmed() == "") { if (LanguageManager::instance()->current_language() == "RU") { QMessageBox::warning(this, "Ошибка", "Введите название!"); } else { QMessageBox::warning(this, "Error", "Please enter a name!"); } - } else if (ok){ - int id = 0; + } else if (ok) { + int id = 0; - if (DB::ProjectDAO::create_project(name_of_project.trimmed().toStdString(), id)) { + if (DB::ProjectDAO::create_project( + name_of_project.trimmed().toStdString(), id + )) { LRDao::add_project_to_user(username, id); auto &project = storage_->add_project( Project(id, name_of_project.trimmed().toStdString(), "") diff --git a/ui/main-window/src/notelist.cpp b/ui/main-window/src/notelist.cpp index 52992c4..dd9083a 100644 --- a/ui/main-window/src/notelist.cpp +++ b/ui/main-window/src/notelist.cpp @@ -12,7 +12,6 @@ NoteList::NoteList(QWidget *parent, const std::string type) main_layout_(new QHBoxLayout(this)), vertical_layouts_(std::vector()), type_(type) { - this->setAttribute(Qt::WA_StyledBackground); this->setObjectName("NoteList"); this->setLayout(main_layout_); @@ -24,20 +23,21 @@ NoteList::NoteList(QWidget *parent, const std::string type) } } -void NoteList::add_note_widget(const project_storage_model::Note *note, QListWidgetItem *project) { +void NoteList::add_note_widget( + const project_storage_model::Note *note, + QListWidgetItem *project +) { auto current_layout = vertical_layouts_[note_counter_ % 3]; if (current_layout->count() > 1) { current_layout->removeItem( current_layout->itemAt(current_layout->count() - 1) ); } - auto* new_note = new NoteWidget(this, note, this->type_, project); - vertical_layouts_[note_counter_ % 3]->addWidget( - new_note, 0, Qt::AlignTop - ); + auto *new_note = new NoteWidget(this, note, this->type_, project); + vertical_layouts_[note_counter_ % 3]->addWidget(new_note, 0, Qt::AlignTop); connect( - new_note, &NoteWidget::change_type_requested, - this, &NoteList::load_project_notes + new_note, &NoteWidget::change_type_requested, this, + &NoteList::load_project_notes ); current_layout->addStretch(); note_counter_++; @@ -48,8 +48,9 @@ void NoteList::load_project_notes(QListWidgetItem *project) { this->clear_note_list(); note_counter_ = 0; for (const auto ¬e : p->project_->get_notes()) { - if (note.get_type() == this->type_) - this->add_note_widget(¬e, project); + if (note.get_type() == this->type_) { + this->add_note_widget(¬e, project); + } } } diff --git a/ui/main-window/src/notewidget.cpp b/ui/main-window/src/notewidget.cpp index 6f2d47d..f4a5c77 100644 --- a/ui/main-window/src/notewidget.cpp +++ b/ui/main-window/src/notewidget.cpp @@ -1,17 +1,17 @@ #include "notewidget.h" #include +#include #include #include +#include "language_manager.h" #include "note.hpp" #include "note_edit_dialog.h" #include "style_manager.h" -#include "language_manager.h" -#include namespace Ui { NoteWidget::NoteWidget( QWidget *parent, - const project_storage_model::Note *model_note, + const Note *model_note, const std::string type, QListWidgetItem *p ) @@ -20,19 +20,20 @@ NoteWidget::NoteWidget( main_layout_(new QVBoxLayout(this)), open_button_(new QPushButton(tr("Открыть"))), delete_button_(new QPushButton(tr("Удалить"))), - type_(type), - project_(p) -{ + type_(type), + project_(p) { this->setObjectName("NoteWidget"); this->setMinimumWidth(100); this->setFixedHeight(100); - - title_label_ = new QLabel(QString::fromStdString(model_note_->get_title()), this); - text_label_ = new QLabel(QString::fromStdString(model_note_->get_text()), this); - + + title_label_ = + new QLabel(QString::fromStdString(model_note_->get_title()), this); + text_label_ = + new QLabel(QString::fromStdString(model_note_->get_text()), this); + title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); text_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); - + main_layout_->addWidget(title_label_); main_layout_->addWidget(text_label_); @@ -45,10 +46,10 @@ NoteWidget::NoteWidget( buttons_layout->addWidget(open_button_); buttons_layout->addWidget(delete_button_); - if (type_ == "deleted"){ - delete_button_->setText("Восстановить"); + if (type_ == "deleted") { + delete_button_->setText("Восстановить"); } - + main_layout_->addLayout(buttons_layout); connect( @@ -58,13 +59,14 @@ NoteWidget::NoteWidget( delete_button_, &QPushButton::clicked, this, &NoteWidget::delete_note ); connect( - StyleManager::instance(), &StyleManager::font_size_changed, - this, &NoteWidget::handle_font_size_changed + StyleManager::instance(), &StyleManager::font_size_changed, this, + &NoteWidget::handle_font_size_changed ); this->setLayout(main_layout_); this->setAttribute(Qt::WA_StyledBackground); - connect(LanguageManager::instance(), &LanguageManager::language_changed, - this, &NoteWidget::handle_language_changed + connect( + LanguageManager::instance(), &LanguageManager::language_changed, this, + &NoteWidget::handle_language_changed ); handle_language_changed(LanguageManager::instance()->current_language()); handle_font_size_changed(StyleManager::instance()->current_font_size()); @@ -76,18 +78,17 @@ void NoteWidget::handle_language_changed(std::string new_language) { if (title_label_->text() == "Empty note") { title_label_->setText("Пустая заметка"); } - if (type_ == "deleted"){ + if (type_ == "deleted") { delete_button_->setText("Восстановить"); } else { delete_button_->setText("Удалить"); } - } - else if (new_language == "EN") { + } else if (new_language == "EN") { open_button_->setText(tr("Open")); if (title_label_->text() == "Пустая заметка") { title_label_->setText("Empty note"); } - if (type_ == "deleted"){ + if (type_ == "deleted") { delete_button_->setText("Восстановить"); } else { delete_button_->setText("Удалить"); @@ -95,21 +96,20 @@ void NoteWidget::handle_language_changed(std::string new_language) { } } -void NoteWidget::handle_font_size_changed(std::string font_size_){ +void NoteWidget::handle_font_size_changed(std::string font_size_) { QString font_rule; if (font_size_ == "small") { title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 13px;"); - } - else if (font_size_ == "medium") { + } else if (font_size_ == "medium") { title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 15px;"); - } - else if (font_size_ == "big") { + } else if (font_size_ == "big") { title_label_->setStyleSheet("color: rgb(33, 44, 50); font-size: 17px;"); } } void NoteWidget::open_note_window() const { auto dialog = new ::NoteEditDialog( + dynamic_cast(project_)->project_->get_name(), const_cast(qobject_cast(this)), const_cast(model_note_) ); @@ -127,14 +127,14 @@ void NoteWidget::change_type(std::string new_type) { } void NoteWidget::delete_note() { - if(type_ == "deleted"){ + if (type_ == "deleted") { this->change_type("actual"); } else { this->change_type("deleted"); } } -QListWidgetItem* NoteWidget::get_project() const{ +QListWidgetItem *NoteWidget::get_project() const { return this->project_; } diff --git a/ui/note-widget/include/note_edit_dialog.h b/ui/note-widget/include/note_edit_dialog.h index 6a4948a..0dbcda5 100644 --- a/ui/note-widget/include/note_edit_dialog.h +++ b/ui/note-widget/include/note_edit_dialog.h @@ -23,8 +23,9 @@ class NoteEditDialog final : public QDialog { public: explicit NoteEditDialog( - QWidget* parent = nullptr, - Note* note = new Note(0, "NULL", "NULL") + std::string project_name = "TODO", + QWidget *parent = nullptr, + Note *note = new Note(0, "NULL", "NULL") ); ~NoteEditDialog() override; static const std::vector THEMES; @@ -44,19 +45,20 @@ private slots: void setup_connections(); void setup_ui(); - void add_member_avatar(const std::string& member); + void add_member_avatar(const std::string &member); void clear_member_avatars(); void update_tags_display(); - static QString create_tag_style_sheet(const QString& color); + static QString create_tag_style_sheet(const QString &color); [[nodiscard]] bool try_save_note() const; - Ui::NoteEditDialog* ui_{}; + Ui::NoteEditDialog *ui_{}; std::vector> member_avatars_; std::vector> tag_labels_; QList selected_tags_; - Note* note_; + Note *note_; + std::string project_name_; }; -#endif // NOTE_EDIT_DIALOG_H \ No newline at end of file +#endif // NOTE_EDIT_DIALOG_H \ No newline at end of file diff --git a/ui/note-widget/include/tags_dialog.h b/ui/note-widget/include/tags_dialog.h index df23a47..b4dcea1 100644 --- a/ui/note-widget/include/tags_dialog.h +++ b/ui/note-widget/include/tags_dialog.h @@ -6,10 +6,9 @@ #include #include #include +#include #include #include -#include - class TagsDialog final : public QDialog { Q_OBJECT diff --git a/ui/note-widget/include/tags_dialog_styles.h b/ui/note-widget/include/tags_dialog_styles.h index b73854f..dd9f013 100644 --- a/ui/note-widget/include/tags_dialog_styles.h +++ b/ui/note-widget/include/tags_dialog_styles.h @@ -546,6 +546,6 @@ QString tags_dialog_blue_theme = R"( color: #07142B; } )"; -} +} // namespace Ui #endif // TAGS_DIALOG_STYLES_H \ No newline at end of file diff --git a/ui/note-widget/src/note_edit_dialog.cpp b/ui/note-widget/src/note_edit_dialog.cpp index 08d9aed..28d23a6 100644 --- a/ui/note-widget/src/note_edit_dialog.cpp +++ b/ui/note-widget/src/note_edit_dialog.cpp @@ -1,4 +1,5 @@ #include "note_edit_dialog.h" +#include #include #include #include @@ -6,26 +7,29 @@ #include #include #include -#include +#include #include "./ui_note_edit_dialog.h" +#include "language_manager.h" #include "note_edit_dialog_styles.h" -#include "tags_dialog.h" #include "style_manager.h" -#include "language_manager.h" - +#include "tags_dialog.h" const std::vector NoteEditDialog::THEMES = { Ui::note_edit_dialog_light_autumn_theme, Ui::note_edit_dialog_dark_autumn_theme, Ui::note_edit_dialog_dark_purple_theme, - Ui::note_edit_dialog_light_purple_theme, - Ui::note_edit_dialog_blue_theme + Ui::note_edit_dialog_light_purple_theme, Ui::note_edit_dialog_blue_theme }; -NoteEditDialog::NoteEditDialog(QWidget* parent, Note* note) +NoteEditDialog::NoteEditDialog( + std::string project_name, + QWidget *parent, + Note *note +) : QDialog(parent), ui_(new Ui::NoteEditDialog), - note_(note) { + note_(note), + project_name_(std::move(project_name)) { ui_->setupUi(this); setWindowTitle("EFFICIO"); @@ -36,7 +40,6 @@ NoteEditDialog::NoteEditDialog(QWidget* parent, Note* note) handle_theme_changed(StyleManager::instance()->current_theme()); handle_font_size_changed(StyleManager::instance()->current_font_size()); - } void NoteEditDialog::handle_theme_changed(int theme) { @@ -45,17 +48,20 @@ void NoteEditDialog::handle_theme_changed(int theme) { void NoteEditDialog::init_basic_fields() { ui_->titleLineEdit->setText(QString::fromStdString(note_->get_title())); - ui_->descriptionTextEdit->setText(QString::fromStdString(note_->get_text())); + ui_->descriptionTextEdit->setText(QString::fromStdString(note_->get_text()) + ); + ui_->projectNameLabel->setTextFormat(Qt::RichText); } - NoteEditDialog::~NoteEditDialog() { delete ui_; } void NoteEditDialog::init_additional_fields() { if (!note_->get_date().empty()) { - QDate date = QDate::fromString(QString::fromStdString(note_->get_date()), "yyyy-MM-dd"); + QDate date = QDate::fromString( + QString::fromStdString(note_->get_date()), "yyyy-MM-dd" + ); if (date.isValid()) { ui_->dateEdit->setDate(date); ui_->dateLabel->setVisible(true); @@ -65,7 +71,7 @@ void NoteEditDialog::init_additional_fields() { if (!note_->get_members().empty()) { ui_->membersLabel->setVisible(true); - for (const auto& member : note_->get_members()) { + for (const auto &member : note_->get_members()) { add_member_avatar(member); } ui_->joinButton->setText("Покинуть"); @@ -73,7 +79,7 @@ void NoteEditDialog::init_additional_fields() { if (!note_->get_tags().empty()) { ui_->tagsLabel->setVisible(true); - for (const auto& tag : note_->get_tags()) { + for (const auto &tag : note_->get_tags()) { TagsDialog::Tag tag_info; tag_info.is_checked = true; tag_info.color = QString::fromStdString(tag.color); @@ -89,23 +95,41 @@ void NoteEditDialog::init_additional_fields() { } void NoteEditDialog::setup_connections() { - connect(ui_->saveButton, &QPushButton::clicked, this, &NoteEditDialog::on_save_button_click); - connect(ui_->cancelButton, &QPushButton::clicked, this, &NoteEditDialog::reject); - connect(ui_->joinButton, &QPushButton::clicked, this, &NoteEditDialog::on_join_button_click); - connect(ui_->addMembersButton, &QPushButton::clicked, this, &NoteEditDialog::on_add_members_button_click); + connect( + ui_->saveButton, &QPushButton::clicked, this, + &NoteEditDialog::on_save_button_click + ); + connect( + ui_->cancelButton, &QPushButton::clicked, this, &NoteEditDialog::reject + ); + connect( + ui_->joinButton, &QPushButton::clicked, this, + &NoteEditDialog::on_join_button_click + ); + connect( + ui_->addMembersButton, &QPushButton::clicked, this, + &NoteEditDialog::on_add_members_button_click + ); connect(ui_->addDateButton, &QPushButton::clicked, this, [this]() { const bool is_visible = ui_->dateLabel->isVisible(); ui_->dateLabel->setVisible(!is_visible); ui_->dateEdit->setVisible(!is_visible); }); - connect(StyleManager::instance(), &StyleManager::theme_changed, - this, &NoteEditDialog::handle_theme_changed); - connect(ui_->addTagsButton, &QPushButton::clicked, this, &NoteEditDialog::on_add_tags_button_click); - connect(StyleManager::instance(), &StyleManager::font_size_changed, - this, &NoteEditDialog::handle_font_size_changed + connect( + StyleManager::instance(), &StyleManager::theme_changed, this, + &NoteEditDialog::handle_theme_changed + ); + connect( + ui_->addTagsButton, &QPushButton::clicked, this, + &NoteEditDialog::on_add_tags_button_click ); - connect(LanguageManager::instance(), &LanguageManager::language_changed, - this, &NoteEditDialog::handle_language_changed + connect( + StyleManager::instance(), &StyleManager::font_size_changed, this, + &NoteEditDialog::handle_font_size_changed + ); + connect( + LanguageManager::instance(), &LanguageManager::language_changed, this, + &NoteEditDialog::handle_language_changed ); handle_language_changed(LanguageManager::instance()->current_language()); } @@ -116,38 +140,54 @@ void NoteEditDialog::handle_language_changed(std::string new_language) { ui_->saveButton->setText("Сохранить"); ui_->dateLabel->setText("Срок"); ui_->cancelButton->setText("Отмена"); - ui_->joinButton->setText(ui_->membersLabel->isVisible() ? "Покинуть" : "Присоединиться"); + ui_->joinButton->setText( + ui_->membersLabel->isVisible() ? "Покинуть" : "Присоединиться" + ); ui_->addMembersButton->setText("Участники"); ui_->addDateButton->setText("Дата"); ui_->addTagsButton->setText("Теги"); - ui_->projectNameLabel->setText("Проект:" ); + ui_->projectNameLabel->setText( + QString("в проекте: %1") + .arg(QString::fromStdString(project_name_)) + ); ui_->descriptionLabel->setText("Описание:"); - if(note_->get_title() == "" or note_->get_title() == "Empty note"){ + if (note_->get_title() == "" or note_->get_title() == "Empty note") { ui_->titleLineEdit->setText("Пустая заметка"); } - if(note_->get_text() == "" or note_->get_text() == "Add a detailed description of your note"){ - ui_->descriptionTextEdit->setPlaceholderText("Добавьте подробное описание вашей заметки"); + if (note_->get_text() == "" or + note_->get_text() == "Add a detailed description of your note") { + ui_->descriptionTextEdit->setPlaceholderText( + "Добавьте подробное описание вашей заметки" + ); } ui_->sidePanelLabel->setText("Добавить к заметке"); ui_->sidePanelLabel_2->setText("Предложения"); - } - else if(new_language == "EN") { + } else if (new_language == "EN") { setWindowTitle("EFFICIO"); ui_->saveButton->setText("Save"); - ui_->dateLabel->setText("Deadline"); + ui_->dateLabel->setText("Deadline"); ui_->cancelButton->setText("Cancel"); - ui_->joinButton->setText(ui_->membersLabel->isVisible() ? "Leave" : "Join"); + ui_->joinButton->setText( + ui_->membersLabel->isVisible() ? "Leave" : "Join" + ); ui_->addMembersButton->setText("Members"); ui_->addDateButton->setText("Date"); ui_->addTagsButton->setText("Tags"); - ui_->projectNameLabel->setText("Project:"); + ui_->projectNameLabel->setText( + QString("in project: %1") + .arg(QString::fromStdString(project_name_)) + ); ui_->descriptionLabel->setText("Description:"); - if(note_->get_title() == "" or note_->get_title() == "Пустая заметка"){ + if (note_->get_title() == "" or + note_->get_title() == "Пустая заметка") { ui_->titleLineEdit->setText("Empty note"); } - if(note_->get_text() == "" or note_->get_text() == "Добавьте подробное описание вашей заметки"){ - ui_->descriptionTextEdit->setPlaceholderText("Add a detailed description of your note"); + if (note_->get_text() == "" or + note_->get_text() == "Добавьте подробное описание вашей заметки") { + ui_->descriptionTextEdit->setPlaceholderText( + "Add a detailed description of your note" + ); } ui_->sidePanelLabel->setText("Add to note"); ui_->sidePanelLabel_2->setText("Suggestions"); @@ -156,28 +196,31 @@ void NoteEditDialog::handle_language_changed(std::string new_language) { void NoteEditDialog::handle_font_size_changed(std::string font_size_) { QString current_style = this->styleSheet(); - + QString font_rules; - if(font_size_ == "small") { - font_rules = + if (font_size_ == "small") { + font_rules = "QLineEdit#titleLineEdit { font-size: 20px; }" "QLabel#projectNameLabel { font-size: 11px; }" "QLabel#descriptionLabel { font-size: 14px; }" - "QLabel#sidePanelLabel, QLabel#sidePanelLabel_2 { font-size: 12px; }" + "QLabel#sidePanelLabel, QLabel#sidePanelLabel_2 { font-size: 12px; " + "}" "QMessageBox QLabel { font-size: 12px; }" "QMessageBox QPushButton { font-size: 11px; }"; - } - else if(font_size_ == "big") { - font_rules = + } else if (font_size_ == "big") { + font_rules = "QLineEdit#titleLineEdit { font-size: 30px; }" "QLabel#projectNameLabel { font-size: 16px; }" "QLabel#descriptionLabel { font-size: 21px; }" - "QLabel#sidePanelLabel, QLabel#sidePanelLabel_2 { font-size: 17px; }" + "QLabel#sidePanelLabel, QLabel#sidePanelLabel_2 { font-size: 17px; " + "}" "QMessageBox QLabel { font-size: 17px; }" "QMessageBox QPushButton { font-size: 16px; }"; } - this->setStyleSheet(THEMES[StyleManager::instance()->current_theme()] + font_rules); + this->setStyleSheet( + THEMES[StyleManager::instance()->current_theme()] + font_rules + ); } void NoteEditDialog::setup_ui() { @@ -188,18 +231,30 @@ void NoteEditDialog::setup_ui() { void NoteEditDialog::on_save_button_click() { if (try_save_note()) { - if(LanguageManager::instance()->current_language() == "RU"){ - QMessageBox::information(this, "Заметка сохранена", + if (LanguageManager::instance()->current_language() == "RU") { + QMessageBox::information( + this, "Заметка сохранена", QString("Заголовок: %1\nСодержимое: %2") - .arg(ui_->titleLineEdit->text(), ui_->descriptionTextEdit->toPlainText())); + .arg( + ui_->titleLineEdit->text(), + ui_->descriptionTextEdit->toPlainText() + ) + ); } else { - QMessageBox::information(this, "Note Saved", + QMessageBox::information( + this, "Note Saved", QString("Title: %1\nDescription: %2") - .arg(ui_->titleLineEdit->text(), ui_->descriptionTextEdit->toPlainText())); + .arg( + ui_->titleLineEdit->text(), + ui_->descriptionTextEdit->toPlainText() + ) + ); } } else { - if(LanguageManager::instance()->current_language() == "RU"){ - QMessageBox::information(this, "Ошибка", "Не удалось сохранить заметку"); + if (LanguageManager::instance()->current_language() == "RU") { + QMessageBox::information( + this, "Ошибка", "Не удалось сохранить заметку" + ); } else { QMessageBox::information(this, "Error", "Failed to save the note"); } @@ -223,7 +278,7 @@ void NoteEditDialog::on_join_button_click() { } } -void NoteEditDialog::add_member_avatar(const std::string& member) { +void NoteEditDialog::add_member_avatar(const std::string &member) { QPixmap pixmap(32, 32); pixmap.fill(Qt::transparent); QPainter painter(&pixmap); @@ -239,17 +294,21 @@ void NoteEditDialog::add_member_avatar(const std::string& member) { } void NoteEditDialog::clear_member_avatars() { - for (auto& avatar : member_avatars_) { + for (auto &avatar : member_avatars_) { ui_->avatarsLayout->removeWidget(avatar.get()); } member_avatars_.clear(); } void NoteEditDialog::on_add_members_button_click() { - if(LanguageManager::instance()->current_language() == "RU"){ - QMessageBox::information(this, "Ошибка", "Другие участники не найдены."); + if (LanguageManager::instance()->current_language() == "RU") { + QMessageBox::information( + this, "Ошибка", "Другие участники не найдены." + ); } else { - QMessageBox::information(this, "Error", "No other participants were found."); + QMessageBox::information( + this, "Error", "No other participants were found." + ); } } @@ -262,7 +321,7 @@ void NoteEditDialog::on_add_tags_button_click() { } void NoteEditDialog::update_tags_display() { - for (auto& tag_label : tag_labels_) { + for (auto &tag_label : tag_labels_) { ui_->tagsLayout->removeWidget(tag_label.get()); } tag_labels_.clear(); @@ -278,18 +337,19 @@ void NoteEditDialog::update_tags_display() { } } -QString NoteEditDialog::create_tag_style_sheet(const QString& color) { +QString NoteEditDialog::create_tag_style_sheet(const QString &color) { return QString( - "background-color: %1; " - "color: white; " - "padding: 9px 10px; " - "border-radius: 5px; " - "font-family: 'Arial'; " - "font-size: 12px; " - "font-weight: bold;" - "width: 40px;" - "height: 25px;" - ).arg(color); + "background-color: %1; " + "color: white; " + "padding: 9px 10px; " + "border-radius: 5px; " + "font-family: 'Arial'; " + "font-size: 12px; " + "font-weight: bold;" + "width: 40px;" + "height: 25px;" + ) + .arg(color); } bool NoteEditDialog::try_save_note() const { diff --git a/ui/note-widget/src/tags_dialog.cpp b/ui/note-widget/src/tags_dialog.cpp index 5287165..0459371 100644 --- a/ui/note-widget/src/tags_dialog.cpp +++ b/ui/note-widget/src/tags_dialog.cpp @@ -2,16 +2,13 @@ #include #include #include -#include "tags_dialog_styles.h" -#include "style_manager.h" #include "language_manager.h" - +#include "style_manager.h" +#include "tags_dialog_styles.h" const std::vector TagsDialog::THEMES = { - Ui::tags_dialog_light_autumn_theme, - Ui::tags_dialog_dark_autumn_theme, - Ui::tags_dialog_dark_purple_theme, - Ui::tags_dialog_light_purple_theme, + Ui::tags_dialog_light_autumn_theme, Ui::tags_dialog_dark_autumn_theme, + Ui::tags_dialog_dark_purple_theme, Ui::tags_dialog_light_purple_theme, Ui::tags_dialog_blue_theme }; @@ -35,20 +32,22 @@ TagsDialog::TagsDialog(const QList &initial_tags, QWidget *parent) setModal(true); setFixedSize(DIALOG_SIZE.first, DIALOG_SIZE.second); handle_theme_changed(StyleManager::instance()->current_theme()); - connect(LanguageManager::instance(), &LanguageManager::language_changed, - this, &TagsDialog::handle_language_changed + connect( + LanguageManager::instance(), &LanguageManager::language_changed, this, + &TagsDialog::handle_language_changed ); handle_language_changed(LanguageManager::instance()->current_language()); } - void TagsDialog::handle_language_changed(std::string new_language) { if (new_language == "RU") { setWindowTitle("Добавить теги"); ok_button_->setText(tr("OK")); cancel_button_->setText(tr("Отмена")); - const QStringList colors = {"Красный", "Синий", "Розовый", "Зеленый", "Желтый"}; + const QStringList colors = { + "Красный", "Синий", "Розовый", "Зеленый", "Желтый" + }; for (int i = 0; i < MAX_TAGS_COUNT; ++i) { if (color_combo_boxes_[i]) { color_combo_boxes_[i]->setItemText(0, colors[0]); @@ -58,7 +57,9 @@ void TagsDialog::handle_language_changed(std::string new_language) { color_combo_boxes_[i]->setItemText(4, colors[4]); } if (name_line_edits_[i]) { - name_line_edits_[i]->setPlaceholderText("Имя тега " + QString::number(i + 1)); + name_line_edits_[i]->setPlaceholderText( + "Имя тега " + QString::number(i + 1) + ); } } } else if (new_language == "EN") { @@ -76,13 +77,14 @@ void TagsDialog::handle_language_changed(std::string new_language) { color_combo_boxes_[i]->setItemText(4, colors[4]); } if (name_line_edits_[i]) { - name_line_edits_[i]->setPlaceholderText("Tag name " + QString::number(i + 1)); + name_line_edits_[i]->setPlaceholderText( + "Tag name " + QString::number(i + 1) + ); } } } } - void TagsDialog::setup_ui() { auto *main_layout = new QVBoxLayout(this); @@ -126,8 +128,10 @@ void TagsDialog::setup_ui() { connect( cancel_button_.get(), &QPushButton::clicked, this, &TagsDialog::reject ); - connect(StyleManager::instance(), &StyleManager::theme_changed, - this, &TagsDialog::handle_theme_changed); + connect( + StyleManager::instance(), &StyleManager::theme_changed, this, + &TagsDialog::handle_theme_changed + ); } void TagsDialog::handle_theme_changed(int theme) { diff --git a/ui/note-widget/ui/note_edit_dialog.ui b/ui/note-widget/ui/note_edit_dialog.ui index d82f559..a0e0cbd 100644 --- a/ui/note-widget/ui/note_edit_dialog.ui +++ b/ui/note-widget/ui/note_edit_dialog.ui @@ -45,7 +45,6 @@ Arial 10 false - true