diff --git a/src/blackgui/guiapplication.cpp b/src/blackgui/guiapplication.cpp index 304989f4d..8837e3bd6 100644 --- a/src/blackgui/guiapplication.cpp +++ b/src/blackgui/guiapplication.cpp @@ -48,7 +48,7 @@ namespace BlackGui CApplication::init(false); // base class without metadata this->setWindowIcon(icon); sGui = this; - connect(sGui, &CGuiApplication::styleSheetsChanged, this, &CGuiApplication::styleSheetsChanged); + connect(&this->m_styleSheetUtility, &CStyleSheetUtility::styleSheetsChanged, this, &CGuiApplication::styleSheetsChanged); } } diff --git a/src/blackgui/stylesheetutility.cpp b/src/blackgui/stylesheetutility.cpp index fea24eeac..639272224 100644 --- a/src/blackgui/stylesheetutility.cpp +++ b/src/blackgui/stylesheetutility.cpp @@ -8,6 +8,7 @@ */ #include "stylesheetutility.h" +#include "blackmisc/fileutils.h" #include #include #include @@ -17,11 +18,15 @@ #include #include +using namespace BlackMisc; + namespace BlackGui { CStyleSheetUtility::CStyleSheetUtility(BlackMisc::Restricted, QObject *parent) : QObject(parent) { this->read(); + this->m_fileWatcher.addPath(qssDirectory()); + connect(&this->m_fileWatcher, &QFileSystemWatcher::directoryChanged, this, &CStyleSheetUtility::ps_qssDirectoryChanged); } const QString &CStyleSheetUtility::fontStyleAsString(const QFont &font) @@ -97,24 +102,23 @@ namespace BlackGui if (!directory.exists()) { return false; } // ini file - QString iniFile = directory.absolutePath().append("/").append(fileNameIniFile()); + const QString iniFile = CFileUtils::appendFilePaths(directory.absolutePath(), fileNameIniFile()); m_iniFile.reset(new QSettings(iniFile, QSettings::IniFormat)); // qss/css files directory.setNameFilters({"*.qss", "*.css"}); directory.setFilter(QDir::Files | QDir::Hidden | QDir::NoSymLinks); - QFileInfoList fileInfoList = directory.entryInfoList(); - - for (int i = 0; i < fileInfoList.size(); ++i) + this->m_styleSheets.clear(); + const QFileInfoList fileInfoList = directory.entryInfoList(); + for (const QFileInfo &fileInfo : fileInfoList) { - QFileInfo fileInfo = fileInfoList.at(i); QFile file(fileInfo.absoluteFilePath()); if (file.open(QFile::QIODevice::ReadOnly | QIODevice::Text)) { QTextStream in(&file); - QString c = in.readAll(); - QString f = fileInfo.fileName().toLower(); + const QString c = in.readAll(); + const QString f = fileInfo.fileName().toLower(); // keep even empty files as placeholders this->m_styleSheets.insert(f, c); @@ -133,11 +137,28 @@ namespace BlackGui QString CStyleSheetUtility::styles(const QStringList &fileNames) const { + const bool hasModifiedFont = this->containsStyle(fileNameFontsModified()); + bool fontAdded = false; + QString style; for (const QString &fileName : fileNames) { - if (!this->containsStyle(fileName)) { continue; } - QString s = this->m_styleSheets[fileName.toLower()].trimmed(); + const QString key = fileName.toLower().trimmed(); + if (!this->containsStyle(key)) { continue; } + + QString s; + if (fileName == fileNameFonts() || fileName == fileNameFontsModified()) + { + if (fontAdded) { continue; } + fontAdded = true; + s = hasModifiedFont ? + this->m_styleSheets[fileNameFontsModified().toLower()] : + this->m_styleSheets[fileNameFonts()]; + } + else + { + s = this->m_styleSheets[key]; + } if (s.isEmpty()) continue; if (!style.isEmpty()) style.append("\n\n"); style.append("/** file: ").append(fileName).append(" **/\n"); @@ -149,7 +170,7 @@ namespace BlackGui bool CStyleSheetUtility::containsStyle(const QString &fileName) const { if (fileName.isEmpty()) return false; - return this->m_styleSheets.contains(fileName.toLower()); + return this->m_styleSheets.contains(fileName.toLower().trimmed()); } bool CStyleSheetUtility::updateFonts(const QFont &font) @@ -180,7 +201,7 @@ namespace BlackGui qss.append(fontStyleSheet); qss.append("}\n"); - QFile fontFile(qssDirectory().append("/").append(fileNameFonts())); + QFile fontFile(qssDirectory().append("/").append(fileNameFontsModified())); bool ok = fontFile.open(QFile::Text | QFile::WriteOnly); if (ok) { @@ -196,7 +217,7 @@ namespace BlackGui { static const QString n("normal"); QString c = combinedStyleAndWeight.toLower(); - foreach (QString s, fontStyles()) + for (const QString &s : fontStyles()) { if (c.contains(s)) { @@ -210,7 +231,7 @@ namespace BlackGui { static const QString n("normal"); QString c = combinedStyleAndWeight.toLower(); - foreach (QString w, fontWeights()) + for (const QString &w : fontWeights()) { if (c.contains(w)) { @@ -226,6 +247,23 @@ namespace BlackGui return f; } + const QString &CStyleSheetUtility::fileNameFontsModified() + { + static const QString f("fonts.modified.qss"); + return f; + } + + bool CStyleSheetUtility::deleteModifiedFontFile() + { + const QString fn = CFileUtils::appendFilePaths(qssDirectory(), fileNameFontsModified()); + QFile file(fn); + if (!file.exists()) { return false; } + bool r = file.remove(); + if (!r) { return false; } + this->read(); + return true; + } + const QString &CStyleSheetUtility::fileNameSwiftStandardGui() { static const QString f("swiftstdgui.qss"); @@ -312,9 +350,14 @@ namespace BlackGui QString CStyleSheetUtility::qssDirectory() { - QString dirPath = QCoreApplication::applicationDirPath(); - if (!dirPath.endsWith('/')) dirPath.append('/'); - dirPath.append("../qss"); + static QString dirPath; + if (!dirPath.isEmpty()) { return dirPath; } + QDir dir(QCoreApplication::applicationDirPath()); + bool ok = dir.cdUp(); + Q_ASSERT_X(ok, Q_FUNC_INFO, "Wrong directory structure"); + if (!ok) { return ""; } + dirPath = CFileUtils::appendFilePaths(dir.absolutePath(), "qss"); + Q_ASSERT_X(QDir(dirPath).exists(), Q_FUNC_INFO, "Wrong directory structure"); return dirPath; } @@ -362,4 +405,10 @@ namespace BlackGui if (!s1.endsWith(";")) { s1 = s1.append(";"); } return s1; } + + void CStyleSheetUtility::ps_qssDirectoryChanged(const QString &file) + { + Q_UNUSED(file); + this->read(); + } } diff --git a/src/blackgui/stylesheetutility.h b/src/blackgui/stylesheetutility.h index 0706c360f..bbfd0ef87 100644 --- a/src/blackgui/stylesheetutility.h +++ b/src/blackgui/stylesheetutility.h @@ -21,6 +21,7 @@ #include #include #include +#include namespace BlackGui { @@ -68,6 +69,12 @@ namespace BlackGui //! File name fonts.qss static const QString &fileNameFonts(); + //! Name for user modified file + static const QString &fileNameFontsModified(); + + //! Delete the modified file for fonts + bool deleteModifiedFontFile(); + //! File name infobar.qss static const QString &fileNameInfoBar(); @@ -137,9 +144,14 @@ namespace BlackGui //! \deprecated use BlackGui::CGuiApplication::styleSheetsChanged void styleSheetsChanged(); + private slots: + //! File changed + void ps_qssDirectoryChanged(const QString &file); + private: - QMap m_styleSheets; //!< filename, stylesheet + QMap m_styleSheets; //!< filename, stylesheet QScopedPointer m_iniFile; + QFileSystemWatcher m_fileWatcher {this}; //!< Monitor my qss files }; } #endif // guard diff --git a/src/swiftguistandard/swiftguistdinit.cpp b/src/swiftguistandard/swiftguistdinit.cpp index e1d355c4e..44fcb7a25 100644 --- a/src/swiftguistandard/swiftguistdinit.cpp +++ b/src/swiftguistandard/swiftguistdinit.cpp @@ -12,7 +12,6 @@ #include "blackcore/contextallinterfaces.h" #include "blackgui/guiapplication.h" #include "blackgui/guiutility.h" -#include "blackgui/stylesheetutility.h" #include "blackgui/components/allmaininfoareacomponents.h" #include "blackgui/models/atcstationlistmodel.h" #include "blackmisc/dbusserver.h"