From e66288b4defc680070037784aabf1613761de085 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Tue, 7 Jan 2025 17:55:49 +0100
Subject: [PATCH 01/18] Add basic support for loading icons from a single file
---
novelwriter/gui/theme.py | 58 ++++++++++++++++++++++++++++++++++------
1 file changed, 50 insertions(+), 8 deletions(-)
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index 11dd1fa8..553786c2 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -38,6 +38,7 @@ from novelwriter.common import NWConfigParser, cssCol, minmax
from novelwriter.constants import nwLabels
from novelwriter.enum import nwItemClass, nwItemLayout, nwItemType
from novelwriter.error import logException
+from novelwriter.types import QtTransparent
logger = logging.getLogger(__name__)
@@ -245,6 +246,18 @@ class GuiTheme:
self.themeLicenseUrl = parser.rdStr(sec, "licenseurl", "")
self.themeIcons = parser.rdStr(sec, "icontheme", "")
+ # Icons
+ sec = "Icons"
+ if parser.has_section(sec):
+ self.iconCache.setIconColor("default", self._parseColour(parser, sec, "default"))
+ self.iconCache.setIconColor("red", self._parseColour(parser, sec, "red"))
+ self.iconCache.setIconColor("orange", self._parseColour(parser, sec, "orange"))
+ self.iconCache.setIconColor("yellow", self._parseColour(parser, sec, "yellow"))
+ self.iconCache.setIconColor("green", self._parseColour(parser, sec, "green"))
+ self.iconCache.setIconColor("aqua", self._parseColour(parser, sec, "aqua"))
+ self.iconCache.setIconColor("blue", self._parseColour(parser, sec, "blue"))
+ self.iconCache.setIconColor("purple", self._parseColour(parser, sec, "purple"))
+
# Palette
sec = "Palette"
if parser.has_section(sec):
@@ -294,6 +307,7 @@ class GuiTheme:
# Icons
defaultIcons = "typicons_light" if backLNess >= 0.5 else "typicons_dark"
self.iconCache.loadTheme(self.themeIcons or defaultIcons)
+ self.iconCache.loadNewTheme("")
# Apply Styles
QApplication.setPalette(self._guiPalette)
@@ -540,6 +554,9 @@ class GuiIcons:
self.mainTheme = mainTheme
# Storage
+ self._svgData: dict[str, bytes] = {}
+ self._svgColours: dict[str, bytes] = {}
+
self._qIcons: dict[str, QIcon] = {}
self._themeMap: dict[str, Path] = {}
self._headerDec: list[QPixmap] = []
@@ -638,6 +655,22 @@ class GuiIcons:
return True
+ def loadNewTheme(self, iconTheme: str) -> bool:
+ """Load new style theme."""
+ themePath = self._iconPath / "material_outline_normal.icons"
+ with open(themePath, mode="r", encoding="utf-8") as icons:
+ for icon in icons:
+ key, _, svg = icon.partition(" = ")
+ if key and svg:
+ self._svgData[key.strip()] = svg.strip().encode("utf-8")
+
+ return True
+
+ def setIconColor(self, key: str, color: QColor) -> None:
+ """Set an icon colour for a named colour."""
+ self._svgColours[key] = color.name(QColor.NameFormat.HexRgb).encode("utf-8")
+ return
+
##
# Access Functions
##
@@ -670,13 +703,14 @@ class GuiIcons:
return pixmap
- def getIcon(self, name: str) -> QIcon:
+ def getIcon(self, name: str, color: str | None = None) -> QIcon:
"""Return an icon from the icon buffer, or load it."""
- if name in self._qIcons:
+ key = f"{name}_{color}" if color else name
+ if key in self._qIcons:
return self._qIcons[name]
else:
- icon = self._loadIcon(name)
- self._qIcons[name] = icon
+ icon = self._loadIcon(name, color)
+ self._qIcons[key] = icon
return icon
def getToggleIcon(self, name: str, size: tuple[int, int]) -> QIcon:
@@ -755,13 +789,13 @@ class GuiIcons:
# Internal Functions
##
- def _loadIcon(self, name: str) -> QIcon:
+ def _loadIcon(self, name: str, color: str | None = None) -> QIcon:
"""Load an icon from the assets themes folder. Is guaranteed to
return a QIcon.
"""
- if name not in self.ICON_KEYS:
- logger.error("Requested unknown icon name '%s'", name)
- return self._noIcon
+ # if name not in self.ICON_KEYS:
+ # logger.error("Requested unknown icon name '%s'", name)
+ # return self._noIcon
# If we just want the app icons, return right away
if name == "novelwriter":
@@ -769,6 +803,14 @@ class GuiIcons:
elif name == "proj_nwx":
return QIcon(str(self._iconPath / "x-novelwriter-project.svg"))
+ if svg := self._svgData.get(name, b""):
+ if fill := self._svgColours.get(color or "default"):
+ svg = svg.replace(b"#000000", fill)
+ pixmap = QPixmap(24, 24)
+ pixmap.fill(QtTransparent)
+ pixmap.loadFromData(svg, "svg")
+ return QIcon(pixmap)
+
# Otherwise, we load from the theme folder
if name in self._themeMap:
logger.debug("Loading: %s", self._themeMap[name].name)
From fafd088751b68098a0fe9036be6d973d3cb9165e Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Tue, 7 Jan 2025 17:56:41 +0100
Subject: [PATCH 02/18] Set theme icon colours
---
novelwriter/assets/syntax/cyberpunk_night.conf | 2 +-
novelwriter/assets/themes/cyberpunk_night.conf | 10 ++++++++++
novelwriter/assets/themes/default_dark.conf | 10 ++++++++++
novelwriter/assets/themes/default_light.conf | 10 ++++++++++
novelwriter/assets/themes/dracula.conf | 11 +++++++++++
novelwriter/assets/themes/solarized_dark.conf | 10 ++++++++++
novelwriter/assets/themes/solarized_light.conf | 11 +++++++++++
7 files changed, 63 insertions(+), 1 deletion(-)
diff --git a/novelwriter/assets/syntax/cyberpunk_night.conf b/novelwriter/assets/syntax/cyberpunk_night.conf
index 4a838580..57a14536 100644
--- a/novelwriter/assets/syntax/cyberpunk_night.conf
+++ b/novelwriter/assets/syntax/cyberpunk_night.conf
@@ -8,7 +8,7 @@ licenseurl = https://creativecommons.org/licenses/by-sa/4.0/
[Syntax]
background = 0, 0, 0
text = 150, 150, 150
-link = 77, 077, 255
+link = 77, 77, 255
headertext = 255, 255, 255
headertag = 50, 0, 180
emphasis = 0, 255, 255
diff --git a/novelwriter/assets/themes/cyberpunk_night.conf b/novelwriter/assets/themes/cyberpunk_night.conf
index 3cfc7c2a..ba3e8898 100644
--- a/novelwriter/assets/themes/cyberpunk_night.conf
+++ b/novelwriter/assets/themes/cyberpunk_night.conf
@@ -7,6 +7,16 @@ license = CC BY-SA 4.0
licenseurl = https://creativecommons.org/licenses/by-sa/4.0/
icontheme = typicons_dark
+[Icons]
+default = 150, 150, 150
+red = 242, 72, 23
+orange = 255, 150, 10
+yellow = 255, 255, 0
+green = 0, 255, 0
+aqua = 0, 255, 255
+blue = 77, 77, 255
+purple = 50, 0, 180
+
[Palette]
window = 0, 0, 0
windowtext = 150, 150, 150
diff --git a/novelwriter/assets/themes/default_dark.conf b/novelwriter/assets/themes/default_dark.conf
index 906cc9fe..d123ec9d 100644
--- a/novelwriter/assets/themes/default_dark.conf
+++ b/novelwriter/assets/themes/default_dark.conf
@@ -8,6 +8,16 @@ license = CC BY-SA 4.0
licenseurl = https://creativecommons.org/licenses/by-sa/4.0/
icontheme = typicons_dark
+[Icons]
+default = 204, 204, 204
+red = 242, 119, 122
+orange = 249, 145, 57
+yellow = 255, 204, 102
+green = 153, 204, 153
+aqua = 102, 204, 204
+blue = 102, 153, 204
+purple = 204, 153, 204
+
[Palette]
window = 54, 54, 54
windowtext = 204, 204, 204
diff --git a/novelwriter/assets/themes/default_light.conf b/novelwriter/assets/themes/default_light.conf
index efedea6d..99a66b37 100644
--- a/novelwriter/assets/themes/default_light.conf
+++ b/novelwriter/assets/themes/default_light.conf
@@ -8,6 +8,16 @@ license = CC BY-SA 4.0
licenseurl = https://creativecommons.org/licenses/by-sa/4.0/
icontheme = typicons_light
+[Icons]
+default = 77, 77, 76
+red = 240, 40, 41
+orange = 245, 135, 31
+yellow = 234, 183, 0
+green = 113, 140, 0
+aqua = 62, 153, 159
+blue = 66, 113, 174
+purple = 137, 89, 168
+
[Palette]
window = 239, 239, 239
windowtext = 0, 0, 0
diff --git a/novelwriter/assets/themes/dracula.conf b/novelwriter/assets/themes/dracula.conf
index a787dcd4..7e637fce 100644
--- a/novelwriter/assets/themes/dracula.conf
+++ b/novelwriter/assets/themes/dracula.conf
@@ -23,6 +23,17 @@ icontheme = typicons_dark
# Yellow = f1fa8c : 241, 250, 140
##
+[Icons]
+default = 248, 248, 242
+red = 255, 85, 85
+orange = 255, 184, 108
+yellow = 241, 250, 140
+green = 80, 250, 123
+aqua = 139, 233, 253
+blue = 255, 121, 198
+purple = 189, 147, 249
+
+
[Palette]
window = 68, 71, 90
windowtext = 248, 248, 242
diff --git a/novelwriter/assets/themes/solarized_dark.conf b/novelwriter/assets/themes/solarized_dark.conf
index 5a4df68b..8adf91b8 100644
--- a/novelwriter/assets/themes/solarized_dark.conf
+++ b/novelwriter/assets/themes/solarized_dark.conf
@@ -7,6 +7,16 @@ license = MIT
licenseurl = https://github.com/altercation/solarized/blob/master/LICENSE
icontheme = typicons_dark
+[Icons]
+default = 253, 246, 227
+red = 220, 50, 47
+orange = 203, 75, 22
+yellow = 181, 137, 0
+green = 133, 153, 0
+aqua = 42, 161, 152
+blue = 38, 139, 210
+purple = 108, 113, 196
+
[Palette]
window = 0, 43, 54
windowtext = 253, 246, 227
diff --git a/novelwriter/assets/themes/solarized_light.conf b/novelwriter/assets/themes/solarized_light.conf
index ca314428..6b5cec3f 100644
--- a/novelwriter/assets/themes/solarized_light.conf
+++ b/novelwriter/assets/themes/solarized_light.conf
@@ -7,6 +7,17 @@ license = MIT
licenseurl = https://github.com/altercation/solarized/blob/master/LICENSE
icontheme = typicons_light
+[Icons]
+default = 0, 43, 54
+red = 220, 50, 47
+orange = 203, 75, 22
+yellow = 181, 137, 0
+green = 133, 153, 0
+aqua = 42, 161, 152
+blue = 38, 139, 210
+purple = 108, 113, 196
+
+
[Palette]
window = 238, 232, 213
windowtext = 0, 43, 54
From 486b6a19d2f36081243bbbab9f7ba7dde3beff17 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Tue, 7 Jan 2025 17:57:02 +0100
Subject: [PATCH 03/18] Add script to generate theme icon files
---
pkgutils.py | 48 +++++++++++++++
utils/material_icons.py | 129 ++++++++++++++++++++++++++++++++++++++++
2 files changed, 177 insertions(+)
create mode 100644 utils/material_icons.py
diff --git a/pkgutils.py b/pkgutils.py
index 03e07af4..be32d51f 100755
--- a/pkgutils.py
+++ b/pkgutils.py
@@ -35,6 +35,8 @@ import zipfile
from pathlib import Path
+from utils.material_icons import processMaterialIcons
+
CURR_DIR = Path(__file__).parent
SETUP_DIR = CURR_DIR / "setup"
SIGN_KEY = "D6A9F6B8F227CF7C6F6D1EE84DBBE4B734B0BD08"
@@ -323,6 +325,44 @@ def buildSampleZip(args: argparse.Namespace | None = None) -> None:
return
+##
+# Import Translations (import-i18n)
+##
+
+def buildIconTheme(args: argparse.Namespace) -> None:
+ """Build an icon theme."""
+ print("")
+ print("Build Icon Theme")
+ print("================")
+ print("")
+
+ workDir = Path(args.sources).absolute()
+ if not workDir.is_dir():
+ print(f"Source directory not found: {workDir}")
+ sys.exit(1)
+
+ iconsDir = CURR_DIR / "novelwriter" / "assets" / "icons"
+
+ style = args.style
+ if style == "material":
+ processMaterialIcons(
+ workDir, iconsDir / "material_outline_normal.icons", "outlined", False, 400
+ )
+ processMaterialIcons(
+ workDir, iconsDir / "material_filled_normal.icons", "outlined", True, 400
+ )
+ processMaterialIcons(
+ workDir, iconsDir / "material_outline_bold.icons", "outlined", False, 700
+ )
+ processMaterialIcons(
+ workDir, iconsDir / "material_filled_bold.icons", "outlined", True, 700
+ )
+
+ print("")
+
+ return
+
+
##
# Import Translations (import-i18n)
##
@@ -1414,6 +1454,14 @@ if __name__ == "__main__":
# Additional Builds
# =================
+ # Build Icons
+ cmdIcons = parsers.add_parser(
+ "icons", help="Build icon theme files from source."
+ )
+ cmdIcons.add_argument("sources", help="Working directory for sources.")
+ cmdIcons.add_argument("style", help="What icon style to build.")
+ cmdIcons.set_defaults(func=buildIconTheme)
+
# Import Translations
cmdImportTS = parsers.add_parser(
"qtlimport", help="Import updated i18n files from a Crowdin zip file."
diff --git a/utils/material_icons.py b/utils/material_icons.py
new file mode 100644
index 00000000..45292969
--- /dev/null
+++ b/utils/material_icons.py
@@ -0,0 +1,129 @@
+"""
+novelWriter – Material Icon Theme
+=================================
+
+This file is a part of novelWriter
+Copyright (C) 2019 Veronica Berglyd Olsen and novelWriter contributors
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see .
+"""
+from __future__ import annotations
+
+import subprocess
+
+from pathlib import Path
+
+from lxml import etree
+
+MATERIAL_REPO = "https://github.com/google/material-design-icons.git"
+GRADE = ""
+
+ICON_MAP = {
+ "alert_error": "error",
+ "alert_info": "info",
+ "alert_question": "help",
+ "alert_warn": "warning",
+
+ "cls_archive": "archive",
+ "cls_character": "group",
+ "cls_custom": "label",
+ "cls_entity": "apartment",
+ "cls_none": "close",
+ "cls_novel": "book_2",
+ "cls_object": "key",
+ "cls_plot": "extension",
+ "cls_template": "topic",
+ "cls_timeline": "hourglass_empty",
+ "cls_trash": "delete",
+ "cls_world": "globe",
+
+ "fmt_bold": "format_bold",
+ "fmt_italic": "format_italic",
+ "fmt_mark": "format_ink_highlighter",
+ "fmt_strike": "format_strikethrough",
+ "fmt_subscript": "subscript",
+ "fmt_superscript": "superscript",
+ "fmt_underline": "format_underlined",
+ "fmt_toolbar": "text_format",
+
+ "search_cancel": "close",
+ "search_case": "match_case",
+ "search_loop": "laps",
+ "search_preserve": "text_fields",
+ "search_project": "document_search",
+ "search_regex": "regular_expression",
+ "search_replace": "find_replace",
+ "search_word": "match_word",
+ "search": "search",
+
+ "bullet-off": "radio_button_unchecked",
+ "bullet-on": "radio_button_checked",
+
+ "bookmarks": "bookmarks",
+ "checked": "select_check_box",
+ "chevron_down": "keyboard_arrow_down",
+ "chevron_left": "arrow_back_ios",
+ "chevron_right": "arrow_forward_ios",
+ "chevron_up": "keyboard_arrow_up",
+ "close": "close",
+ "document_add": "note_add",
+ "document": "description",
+ "edit": "edit",
+ "folder": "folder",
+ "item_add": "add",
+ "list": "format_list_bulleted",
+ "maximise": "fullscreen",
+ "minimise": "close_fullscreen",
+ "more_vertical": "more_vert",
+ "noncheckable": "indeterminate_check_box",
+ "project_copy": "folder_copy",
+ "refresh": "refresh",
+ "unchecked": "disabled_by_default",
+}
+
+
+def _fixXml(svg: str) -> str:
+ """Clean up the SVG XML and add needed fields."""
+ xSvg = etree.fromstring(svg) # type: ignore
+ xSvg.set("fill", "#000000")
+ xSvg.set("height", "128")
+ xSvg.set("width", "128")
+ return etree.tostring(xSvg).decode()
+
+
+def processMaterialIcons(workDir: Path, output: Path, style: str, fill: bool, weight: int) -> None:
+ """Process material icons of a given spec and write output file."""
+ srcRepo = workDir / "material-design-icons"
+ if not srcRepo.is_dir():
+ subprocess.call(["git", "clone", MATERIAL_REPO, "--depth", "50"], cwd=workDir)
+ else:
+ subprocess.call(["git", "pull"], cwd=srcRepo)
+
+ kind = f"wght{weight}" if weight != 400 else ""
+ kind += "fill1" if fill else ""
+
+ with open(output, mode="w", encoding="utf-8") as icons:
+ iconSrc = srcRepo / "symbols" / "web"
+ for key, name in ICON_MAP.items():
+ if kind:
+ fileNmae = f"{name}_{kind}_24px.svg"
+ else:
+ fileNmae = f"{name}_24px.svg"
+ iconFile = iconSrc / name / f"materialsymbols{style}" / fileNmae
+ if iconFile.is_file():
+ svg = iconFile.read_text(encoding="utf-8")
+ icons.write(f"{key:<15s} = {_fixXml(svg)}\n")
+ print(f"Wrote: {iconFile.stem}")
+ else:
+ print(f"Not Found: {iconFile}")
From 8a671dee59a91c0c9be8294da7d00fc873b2a8c1 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Tue, 7 Jan 2025 19:16:56 +0100
Subject: [PATCH 04/18] Add some icon themes
---
.../assets/icons/material_filled_bold.icons | 89 +++++++++++++++++++
.../assets/icons/material_filled_normal.icons | 89 +++++++++++++++++++
.../assets/icons/material_outline_bold.icons | 89 +++++++++++++++++++
.../icons/material_outline_normal.icons | 89 +++++++++++++++++++
4 files changed, 356 insertions(+)
create mode 100644 novelwriter/assets/icons/material_filled_bold.icons
create mode 100644 novelwriter/assets/icons/material_filled_normal.icons
create mode 100644 novelwriter/assets/icons/material_outline_bold.icons
create mode 100644 novelwriter/assets/icons/material_outline_normal.icons
diff --git a/novelwriter/assets/icons/material_filled_bold.icons b/novelwriter/assets/icons/material_filled_bold.icons
new file mode 100644
index 00000000..b043b7c9
--- /dev/null
+++ b/novelwriter/assets/icons/material_filled_bold.icons
@@ -0,0 +1,89 @@
+alert_error =
+alert_info =
+alert_question =
+alert_warn =
+cls_archive =
+cls_character =
+cls_custom =
+cls_entity =
+cls_none =
+cls_novel =
+cls_object =
+cls_plot =
+cls_template =
+cls_timeline =
+cls_trash =
+cls_world =
+fmt_bold =
+fmt_italic =
+fmt_mark =
+fmt_strike =
+fmt_subscript =
+fmt_superscript =
+fmt_underline =
+fmt_toolbar =
+search_cancel =
+search_case =
+search_loop =
+search_preserve =
+search_project =
+search_regex =
+search_replace =
+search_word =
+search =
+bullet-off =
+bullet-on =
+unfold-hide =
+unfold-show =
+add =
+bookmarks =
+browse =
+cancel =
+checked =
+chevron_down =
+chevron_left =
+chevron_right =
+chevron_up =
+close =
+copy =
+document_add =
+document =
+edit =
+exclude =
+export =
+filter =
+fit_height =
+fit_width =
+folder =
+font =
+import =
+language =
+lines =
+list =
+manuscript =
+margin_bottom =
+margin_left =
+margin_right =
+margin_top =
+maximise =
+minimise =
+more_vertical =
+noncheckable =
+novel_view =
+open =
+outline =
+panel =
+pin =
+project_copy =
+project_view =
+quote =
+refresh =
+remove =
+revert =
+settings =
+star =
+stats =
+timer_off =
+timer =
+unchecked =
+view =
diff --git a/novelwriter/assets/icons/material_filled_normal.icons b/novelwriter/assets/icons/material_filled_normal.icons
new file mode 100644
index 00000000..e70f277f
--- /dev/null
+++ b/novelwriter/assets/icons/material_filled_normal.icons
@@ -0,0 +1,89 @@
+alert_error =
+alert_info =
+alert_question =
+alert_warn =
+cls_archive =
+cls_character =
+cls_custom =
+cls_entity =
+cls_none =
+cls_novel =
+cls_object =
+cls_plot =
+cls_template =
+cls_timeline =
+cls_trash =
+cls_world =
+fmt_bold =
+fmt_italic =
+fmt_mark =
+fmt_strike =
+fmt_subscript =
+fmt_superscript =
+fmt_underline =
+fmt_toolbar =
+search_cancel =
+search_case =
+search_loop =
+search_preserve =
+search_project =
+search_regex =
+search_replace =
+search_word =
+search =
+bullet-off =
+bullet-on =
+unfold-hide =
+unfold-show =
+add =
+bookmarks =
+browse =
+cancel =
+checked =
+chevron_down =
+chevron_left =
+chevron_right =
+chevron_up =
+close =
+copy =
+document_add =
+document =
+edit =
+exclude =
+export =
+filter =
+fit_height =
+fit_width =
+folder =
+font =
+import =
+language =
+lines =
+list =
+manuscript =
+margin_bottom =
+margin_left =
+margin_right =
+margin_top =
+maximise =
+minimise =
+more_vertical =
+noncheckable =
+novel_view =
+open =
+outline =
+panel =
+pin =
+project_copy =
+project_view =
+quote =
+refresh =
+remove =
+revert =
+settings =
+star =
+stats =
+timer_off =
+timer =
+unchecked =
+view =
diff --git a/novelwriter/assets/icons/material_outline_bold.icons b/novelwriter/assets/icons/material_outline_bold.icons
new file mode 100644
index 00000000..7225e7b1
--- /dev/null
+++ b/novelwriter/assets/icons/material_outline_bold.icons
@@ -0,0 +1,89 @@
+alert_error =
+alert_info =
+alert_question =
+alert_warn =
+cls_archive =
+cls_character =
+cls_custom =
+cls_entity =
+cls_none =
+cls_novel =
+cls_object =
+cls_plot =
+cls_template =
+cls_timeline =
+cls_trash =
+cls_world =
+fmt_bold =
+fmt_italic =
+fmt_mark =
+fmt_strike =
+fmt_subscript =
+fmt_superscript =
+fmt_underline =
+fmt_toolbar =
+search_cancel =
+search_case =
+search_loop =
+search_preserve =
+search_project =
+search_regex =
+search_replace =
+search_word =
+search =
+bullet-off =
+bullet-on =
+unfold-hide =
+unfold-show =
+add =
+bookmarks =
+browse =
+cancel =
+checked =
+chevron_down =
+chevron_left =
+chevron_right =
+chevron_up =
+close =
+copy =
+document_add =
+document =
+edit =
+exclude =
+export =
+filter =
+fit_height =
+fit_width =
+folder =
+font =
+import =
+language =
+lines =
+list =
+manuscript =
+margin_bottom =
+margin_left =
+margin_right =
+margin_top =
+maximise =
+minimise =
+more_vertical =
+noncheckable =
+novel_view =
+open =
+outline =
+panel =
+pin =
+project_copy =
+project_view =
+quote =
+refresh =
+remove =
+revert =
+settings =
+star =
+stats =
+timer_off =
+timer =
+unchecked =
+view =
diff --git a/novelwriter/assets/icons/material_outline_normal.icons b/novelwriter/assets/icons/material_outline_normal.icons
new file mode 100644
index 00000000..bf199798
--- /dev/null
+++ b/novelwriter/assets/icons/material_outline_normal.icons
@@ -0,0 +1,89 @@
+alert_error =
+alert_info =
+alert_question =
+alert_warn =
+cls_archive =
+cls_character =
+cls_custom =
+cls_entity =
+cls_none =
+cls_novel =
+cls_object =
+cls_plot =
+cls_template =
+cls_timeline =
+cls_trash =
+cls_world =
+fmt_bold =
+fmt_italic =
+fmt_mark =
+fmt_strike =
+fmt_subscript =
+fmt_superscript =
+fmt_underline =
+fmt_toolbar =
+search_cancel =
+search_case =
+search_loop =
+search_preserve =
+search_project =
+search_regex =
+search_replace =
+search_word =
+search =
+bullet-off =
+bullet-on =
+unfold-hide =
+unfold-show =
+add =
+bookmarks =
+browse =
+cancel =
+checked =
+chevron_down =
+chevron_left =
+chevron_right =
+chevron_up =
+close =
+copy =
+document_add =
+document =
+edit =
+exclude =
+export =
+filter =
+fit_height =
+fit_width =
+folder =
+font =
+import =
+language =
+lines =
+list =
+manuscript =
+margin_bottom =
+margin_left =
+margin_right =
+margin_top =
+maximise =
+minimise =
+more_vertical =
+noncheckable =
+novel_view =
+open =
+outline =
+panel =
+pin =
+project_copy =
+project_view =
+quote =
+refresh =
+remove =
+revert =
+settings =
+star =
+stats =
+timer_off =
+timer =
+unchecked =
+view =
From b97844512adce5c547566e6437e5a268b73b7859 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Tue, 7 Jan 2025 19:19:11 +0100
Subject: [PATCH 05/18] Update icons in the GUI
---
novelwriter/constants.py | 14 ++++
novelwriter/core/item.py | 5 +-
novelwriter/dialogs/projectsettings.py | 16 ++---
novelwriter/dialogs/wordlist.py | 8 +--
novelwriter/extensions/modified.py | 11 +--
novelwriter/extensions/novelselector.py | 4 +-
novelwriter/gui/doceditor.py | 26 +++----
novelwriter/gui/docviewer.py | 14 ++--
novelwriter/gui/docviewerpanel.py | 26 ++++---
novelwriter/gui/itemdetails.py | 10 +--
novelwriter/gui/noveltree.py | 4 +-
novelwriter/gui/outline.py | 6 +-
novelwriter/gui/projtree.py | 28 ++++----
novelwriter/gui/search.py | 4 +-
novelwriter/gui/sidebar.py | 14 ++--
novelwriter/gui/statusbar.py | 8 +--
novelwriter/gui/theme.py | 90 ++++++++-----------------
novelwriter/shared.py | 8 +--
novelwriter/tools/dictionaries.py | 2 +-
novelwriter/tools/lipsum.py | 2 +-
novelwriter/tools/manusbuild.py | 10 ++-
novelwriter/tools/manuscript.py | 12 ++--
novelwriter/tools/manussettings.py | 34 +++++-----
novelwriter/tools/welcome.py | 20 +++---
utils/material_icons.py | 38 ++++++++++-
25 files changed, 225 insertions(+), 189 deletions(-)
diff --git a/novelwriter/constants.py b/novelwriter/constants.py
index bdedab10..8213cc21 100644
--- a/novelwriter/constants.py
+++ b/novelwriter/constants.py
@@ -258,6 +258,20 @@ class nwLabels:
nwItemClass.TEMPLATE: "cls_template",
nwItemClass.TRASH: "cls_trash",
}
+ CLASS_COLOR = {
+ nwItemClass.NO_CLASS: "default",
+ nwItemClass.NOVEL: "red",
+ nwItemClass.PLOT: "blue",
+ nwItemClass.CHARACTER: "blue",
+ nwItemClass.WORLD: "blue",
+ nwItemClass.TIMELINE: "blue",
+ nwItemClass.OBJECT: "blue",
+ nwItemClass.ENTITY: "blue",
+ nwItemClass.CUSTOM: "blue",
+ nwItemClass.ARCHIVE: "red",
+ nwItemClass.TEMPLATE: "yellow",
+ nwItemClass.TRASH: "red",
+ }
LAYOUT_NAME = {
nwItemLayout.NO_LAYOUT: QT_TRANSLATE_NOOP("Constant", "None"),
nwItemLayout.DOCUMENT: QT_TRANSLATE_NOOP("Constant", "Novel Document"),
diff --git a/novelwriter/core/item.py b/novelwriter/core/item.py
index fb2b902f..cc253fe2 100644
--- a/novelwriter/core/item.py
+++ b/novelwriter/core/item.py
@@ -350,11 +350,12 @@ class NWItem:
"""
if self.isFileType():
key = "checked" if self._active else "unchecked"
+ color = "green" if self._active else "red"
text = trConst(nwLabels.ACTIVE_NAME[key])
- icon = SHARED.theme.getIcon(key)
+ icon = SHARED.theme.getIcon(key, color)
else:
text = ""
- icon = SHARED.theme.getIcon("noncheckable")
+ icon = SHARED.theme.getIcon("noncheckable", "orange")
return text, icon
##
diff --git a/novelwriter/dialogs/projectsettings.py b/novelwriter/dialogs/projectsettings.py
index a610373b..e9572157 100644
--- a/novelwriter/dialogs/projectsettings.py
+++ b/novelwriter/dialogs/projectsettings.py
@@ -363,27 +363,27 @@ class _StatusPage(NFixedPage):
self._addItem(key, StatusEntry.duplicate(entry))
# List Controls
- self.addButton = NIconToolButton(self, iSz, "add")
+ self.addButton = NIconToolButton(self, iSz, "add", "green")
self.addButton.setToolTip(self.tr("Add Label"))
self.addButton.clicked.connect(self._onItemCreate)
- self.delButton = NIconToolButton(self, iSz, "remove")
+ self.delButton = NIconToolButton(self, iSz, "remove", "red")
self.delButton.setToolTip(self.tr("Delete Label"))
self.delButton.clicked.connect(self._onItemDelete)
- self.upButton = NIconToolButton(self, iSz, "up")
+ self.upButton = NIconToolButton(self, iSz, "chevron_up", "blue")
self.upButton.setToolTip(self.tr("Move Up"))
self.upButton.clicked.connect(qtLambda(self._moveItem, -1))
- self.downButton = NIconToolButton(self, iSz, "down")
+ self.downButton = NIconToolButton(self, iSz, "chevron_down", "blue")
self.downButton.setToolTip(self.tr("Move Down"))
self.downButton.clicked.connect(qtLambda(self._moveItem, 1))
- self.importButton = NIconToolButton(self, iSz, "import")
+ self.importButton = NIconToolButton(self, iSz, "import", "green")
self.importButton.setToolTip(self.tr("Import Labels"))
self.importButton.clicked.connect(self._importLabels)
- self.exportButton = NIconToolButton(self, iSz, "export")
+ self.exportButton = NIconToolButton(self, iSz, "export", "blue")
self.exportButton.setToolTip(self.tr("Export Labels"))
self.exportButton.clicked.connect(self._exportLabels)
@@ -704,10 +704,10 @@ class _ReplacePage(NFixedPage):
self.listBox.setSortingEnabled(True)
# List Controls
- self.addButton = NIconToolButton(self, iSz, "add")
+ self.addButton = NIconToolButton(self, iSz, "add", "green")
self.addButton.clicked.connect(self._onEntryCreated)
- self.delButton = NIconToolButton(self, iSz, "remove")
+ self.delButton = NIconToolButton(self, iSz, "remove", "red")
self.delButton.clicked.connect(self._onEntryDeleted)
# Edit Form
diff --git a/novelwriter/dialogs/wordlist.py b/novelwriter/dialogs/wordlist.py
index 90e8a68a..5ecd8c1d 100644
--- a/novelwriter/dialogs/wordlist.py
+++ b/novelwriter/dialogs/wordlist.py
@@ -73,11 +73,11 @@ class GuiWordList(NDialog):
scale=NColourLabel.HEADER_SCALE
)
- self.importButton = NIconToolButton(self, iSz, "import")
+ self.importButton = NIconToolButton(self, iSz, "import", "green")
self.importButton.setToolTip(self.tr("Import words from text file"))
self.importButton.clicked.connect(self._importWords)
- self.exportButton = NIconToolButton(self, iSz, "export")
+ self.exportButton = NIconToolButton(self, iSz, "export", "blue")
self.exportButton.setToolTip(self.tr("Export words to text file"))
self.exportButton.clicked.connect(self._exportWords)
@@ -95,11 +95,11 @@ class GuiWordList(NDialog):
# Add/Remove Form
self.newEntry = QLineEdit(self)
- self.addButton = NIconToolButton(self, iSz, "add")
+ self.addButton = NIconToolButton(self, iSz, "add", "green")
self.addButton.setToolTip(self.tr("Add Word"))
self.addButton.clicked.connect(self._doAdd)
- self.delButton = NIconToolButton(self, iSz, "remove")
+ self.delButton = NIconToolButton(self, iSz, "remove", "red")
self.delButton.setToolTip(self.tr("Remove Word"))
self.delButton.clicked.connect(self._doDelete)
diff --git a/novelwriter/extensions/modified.py b/novelwriter/extensions/modified.py
index 548d771d..5471da29 100644
--- a/novelwriter/extensions/modified.py
+++ b/novelwriter/extensions/modified.py
@@ -164,18 +164,21 @@ class NDoubleSpinBox(QDoubleSpinBox):
class NIconToolButton(QToolButton):
- def __init__(self, parent: QWidget, iconSize: QSize, icon: str | None = None) -> None:
+ def __init__(
+ self, parent: QWidget, iconSize: QSize,
+ icon: str | None = None, color: str | None = None
+ ) -> None:
super().__init__(parent=parent)
self.setToolButtonStyle(Qt.ToolButtonStyle.ToolButtonIconOnly)
self.setIconSize(iconSize)
self.setPopupMode(QToolButton.ToolButtonPopupMode.InstantPopup)
if icon:
- self.setThemeIcon(icon)
+ self.setThemeIcon(icon, color)
return
- def setThemeIcon(self, iconKey: str) -> None:
+ def setThemeIcon(self, iconKey: str, color: str | None = None) -> None:
"""Set an icon from the current theme."""
- self.setIcon(SHARED.theme.getIcon(iconKey))
+ self.setIcon(SHARED.theme.getIcon(iconKey, color))
return
diff --git a/novelwriter/extensions/novelselector.py b/novelwriter/extensions/novelselector.py
index 3504896e..e57a3bce 100644
--- a/novelwriter/extensions/novelselector.py
+++ b/novelwriter/extensions/novelselector.py
@@ -94,7 +94,9 @@ class NovelSelector(QComboBox):
self._firstHandle = None
self.clear()
- icon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[nwItemClass.NOVEL])
+ icon = SHARED.theme.getIcon(
+ nwLabels.CLASS_ICON[nwItemClass.NOVEL], nwLabels.CLASS_COLOR[nwItemClass.NOVEL]
+ )
handle = self.currentData()
for tHandle, nwItem in SHARED.project.tree.iterRoots(nwItemClass.NOVEL):
if self._listFormat:
diff --git a/novelwriter/gui/doceditor.py b/novelwriter/gui/doceditor.py
index c95023d9..e7abcdb2 100644
--- a/novelwriter/gui/doceditor.py
+++ b/novelwriter/gui/doceditor.py
@@ -2438,9 +2438,9 @@ class GuiDocToolBar(QWidget):
palette.setColor(QPalette.ColorRole.Text, SHARED.theme.colText)
self.setPalette(palette)
- self.tbBoldMD.setThemeIcon("fmt_bold-md")
- self.tbItalicMD.setThemeIcon("fmt_italic-md")
- self.tbStrikeMD.setThemeIcon("fmt_strike-md")
+ self.tbBoldMD.setThemeIcon("fmt_bold", "orange")
+ self.tbItalicMD.setThemeIcon("fmt_italic", "orange")
+ self.tbStrikeMD.setThemeIcon("fmt_strike", "orange")
self.tbBold.setThemeIcon("fmt_bold")
self.tbItalic.setThemeIcon("fmt_italic")
self.tbStrike.setThemeIcon("fmt_strike")
@@ -2690,8 +2690,8 @@ class GuiDocEditSearch(QFrame):
self.toggleProject.setIcon(SHARED.theme.getIcon("search_project"))
self.toggleMatchCap.setIcon(SHARED.theme.getIcon("search_preserve"))
self.cancelSearch.setIcon(SHARED.theme.getIcon("search_cancel"))
- self.searchButton.setThemeIcon("search")
- self.replaceButton.setThemeIcon("search_replace")
+ self.searchButton.setThemeIcon("search", "green")
+ self.replaceButton.setThemeIcon("search_replace", "green")
# Set stylesheets
self.searchOpt.setStyleSheet("QToolBar {padding: 0;}")
@@ -2954,11 +2954,11 @@ class GuiDocEditHeader(QWidget):
def updateTheme(self) -> None:
"""Update theme elements."""
- self.tbButton.setThemeIcon("toolbar")
- self.outlineButton.setThemeIcon("list")
- self.searchButton.setThemeIcon("search")
- self.minmaxButton.setThemeIcon("maximise")
- self.closeButton.setThemeIcon("close")
+ self.tbButton.setThemeIcon("fmt_toolbar", "blue")
+ self.outlineButton.setThemeIcon("list", "blue")
+ self.searchButton.setThemeIcon("search", "blue")
+ self.minmaxButton.setThemeIcon("maximise", "blue")
+ self.closeButton.setThemeIcon("close", "red")
buttonStyle = SHARED.theme.getStyleSheet(STYLES_MIN_TOOLBUTTON)
self.tbButton.setStyleSheet(buttonStyle)
@@ -3031,7 +3031,7 @@ class GuiDocEditHeader(QWidget):
@pyqtSlot(bool)
def _focusModeChanged(self, focusMode: bool) -> None:
"""Update minimise/maximise icon of the Focus Mode button."""
- self.minmaxButton.setThemeIcon("minimise" if focusMode else "maximise")
+ self.minmaxButton.setThemeIcon("minimise" if focusMode else "maximise", "blue")
return
##
@@ -3165,8 +3165,8 @@ class GuiDocEditFooter(QWidget):
def updateTheme(self) -> None:
"""Update theme elements."""
iPx = round(0.9*SHARED.theme.baseIconHeight)
- self.linesIcon.setPixmap(SHARED.theme.getPixmap("status_lines", (iPx, iPx)))
- self.wordsIcon.setPixmap(SHARED.theme.getPixmap("status_stats", (iPx, iPx)))
+ self.linesIcon.setPixmap(SHARED.theme.getPixmap("lines", (iPx, iPx)))
+ self.wordsIcon.setPixmap(SHARED.theme.getPixmap("stats", (iPx, iPx)))
self.matchColours()
return
diff --git a/novelwriter/gui/docviewer.py b/novelwriter/gui/docviewer.py
index b43c7b7c..6bda315a 100644
--- a/novelwriter/gui/docviewer.py
+++ b/novelwriter/gui/docviewer.py
@@ -760,12 +760,12 @@ class GuiDocViewHeader(QWidget):
def updateTheme(self) -> None:
"""Update theme elements."""
- self.outlineButton.setThemeIcon("list")
- self.backButton.setThemeIcon("backward")
- self.forwardButton.setThemeIcon("forward")
- self.editButton.setThemeIcon("edit")
- self.refreshButton.setThemeIcon("refresh")
- self.closeButton.setThemeIcon("close")
+ self.outlineButton.setThemeIcon("list", "blue")
+ self.backButton.setThemeIcon("chevron_left", "blue")
+ self.forwardButton.setThemeIcon("chevron_right", "blue")
+ self.editButton.setThemeIcon("edit", "green")
+ self.refreshButton.setThemeIcon("refresh", "green")
+ self.closeButton.setThemeIcon("close", "red")
buttonStyle = SHARED.theme.getStyleSheet(STYLES_MIN_TOOLBUTTON)
self.outlineButton.setStyleSheet(buttonStyle)
@@ -951,7 +951,7 @@ class GuiDocViewFooter(QWidget):
"""Update theme elements."""
# Icons
fPx = int(0.9*SHARED.theme.fontPixelSize)
- bulletIcon = SHARED.theme.getToggleIcon("bullet", (fPx, fPx))
+ bulletIcon = SHARED.theme.getToggleIcon("bullet", (fPx, fPx), "blue")
self.showHide.setThemeIcon("panel")
self.showComments.setIcon(bulletIcon)
diff --git a/novelwriter/gui/docviewerpanel.py b/novelwriter/gui/docviewerpanel.py
index 093c1b84..262817a9 100644
--- a/novelwriter/gui/docviewerpanel.py
+++ b/novelwriter/gui/docviewerpanel.py
@@ -101,7 +101,7 @@ class GuiDocViewerPanel(QWidget):
def updateTheme(self, updateTabs: bool = True) -> None:
"""Update theme elements."""
- self.optsButton.setThemeIcon("menu")
+ self.optsButton.setThemeIcon("more_vertical")
self.optsButton.setStyleSheet(SHARED.theme.getStyleSheet(STYLES_MIN_TOOLBUTTON))
self.mainTabs.setStyleSheet(SHARED.theme.getStyleSheet(STYLES_FLAT_TABS))
self.updateHandle(self._lastHandle)
@@ -268,8 +268,8 @@ class _ViewPanelBackRefs(QTreeWidget):
treeHeader.setSectionsMovable(False)
# Cache Icons Locally
- self._editIcon = SHARED.theme.getIcon("edit")
- self._viewIcon = SHARED.theme.getIcon("view")
+ self._editIcon = SHARED.theme.getIcon("edit", "green")
+ self._viewIcon = SHARED.theme.getIcon("view", "blue")
# Signals
self.clicked.connect(self._treeItemClicked)
@@ -279,8 +279,8 @@ class _ViewPanelBackRefs(QTreeWidget):
def updateTheme(self) -> None:
"""Update theme elements."""
- self._editIcon = SHARED.theme.getIcon("edit")
- self._viewIcon = SHARED.theme.getIcon("view")
+ self._editIcon = SHARED.theme.getIcon("edit", "green")
+ self._viewIcon = SHARED.theme.getIcon("view", "blue")
for i in range(self.topLevelItemCount()):
if item := self.topLevelItem(i):
item.setIcon(self.C_EDIT, self._editIcon)
@@ -410,9 +410,11 @@ class _ViewPanelKeyWords(QTreeWidget):
treeHeader.setSectionsMovable(False)
# Cache Icons Locally
- self._classIcon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[itemClass])
- self._editIcon = SHARED.theme.getIcon("edit")
- self._viewIcon = SHARED.theme.getIcon("view")
+ self._classIcon = SHARED.theme.getIcon(
+ nwLabels.CLASS_ICON[itemClass], nwLabels.CLASS_COLOR[itemClass]
+ )
+ self._editIcon = SHARED.theme.getIcon("edit", "green")
+ self._viewIcon = SHARED.theme.getIcon("view", "blue")
# Signals
self.clicked.connect(self._treeItemClicked)
@@ -422,9 +424,11 @@ class _ViewPanelKeyWords(QTreeWidget):
def updateTheme(self) -> None:
"""Update theme elements."""
- self._classIcon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[self._class])
- self._editIcon = SHARED.theme.getIcon("edit")
- self._viewIcon = SHARED.theme.getIcon("view")
+ self._classIcon = SHARED.theme.getIcon(
+ nwLabels.CLASS_ICON[self._class], nwLabels.CLASS_COLOR[self._class]
+ )
+ self._editIcon = SHARED.theme.getIcon("edit", "green")
+ self._viewIcon = SHARED.theme.getIcon("view", "blue")
for i in range(self.topLevelItemCount()):
if item := self.topLevelItem(i):
item.setIcon(self.C_EDIT, self._editIcon)
diff --git a/novelwriter/gui/itemdetails.py b/novelwriter/gui/itemdetails.py
index b267a7ef..32fd926f 100644
--- a/novelwriter/gui/itemdetails.py
+++ b/novelwriter/gui/itemdetails.py
@@ -237,11 +237,11 @@ class GuiItemDetails(QWidget):
if nwItem.isFileType():
if nwItem.isActive:
- self.labelIcon.setPixmap(SHARED.theme.getPixmap("checked", (iPx, iPx)))
+ self.labelIcon.setPixmap(SHARED.theme.getPixmap("checked", (iPx, iPx), "green"))
else:
- self.labelIcon.setPixmap(SHARED.theme.getPixmap("unchecked", (iPx, iPx)))
+ self.labelIcon.setPixmap(SHARED.theme.getPixmap("unchecked", (iPx, iPx), "red"))
else:
- self.labelIcon.setPixmap(SHARED.theme.getPixmap("noncheckable", (iPx, iPx)))
+ self.labelIcon.setPixmap(SHARED.theme.getPixmap("noncheckable", (iPx, iPx), "orange"))
self.labelData.setText(elide(nwItem.itemName, 100))
@@ -255,7 +255,9 @@ class GuiItemDetails(QWidget):
# Class
# =====
- classIcon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[nwItem.itemClass])
+ classIcon = SHARED.theme.getIcon(
+ nwLabels.CLASS_ICON[nwItem.itemClass], nwLabels.CLASS_COLOR[nwItem.itemClass]
+ )
self.classIcon.setPixmap(classIcon.pixmap(iPx, iPx))
self.classData.setText(trConst(nwLabels.CLASS_NAME[nwItem.itemClass]))
diff --git a/novelwriter/gui/noveltree.py b/novelwriter/gui/noveltree.py
index 8c924be8..d33e3d2e 100644
--- a/novelwriter/gui/noveltree.py
+++ b/novelwriter/gui/noveltree.py
@@ -268,8 +268,8 @@ class GuiNovelToolBar(QWidget):
"""Update theme elements."""
# Icons
self.tbNovel.setThemeIcon("cls_novel")
- self.tbRefresh.setThemeIcon("refresh")
- self.tbMore.setThemeIcon("menu")
+ self.tbRefresh.setThemeIcon("refresh", "green")
+ self.tbMore.setThemeIcon("more_vertical")
qPalette = self.palette()
qPalette.setBrush(QPalette.ColorRole.Window, qPalette.base())
diff --git a/novelwriter/gui/outline.py b/novelwriter/gui/outline.py
index 89740fb2..932dcf07 100644
--- a/novelwriter/gui/outline.py
+++ b/novelwriter/gui/outline.py
@@ -268,9 +268,9 @@ class GuiOutlineToolBar(QToolBar):
"""Update theme elements."""
self.setStyleSheet("QToolBar {border: 0px;}")
self.novelValue.refreshNovelList()
- self.aRefresh.setIcon(SHARED.theme.getIcon("refresh"))
- self.aExport.setIcon(SHARED.theme.getIcon("export"))
- self.tbColumns.setIcon(SHARED.theme.getIcon("menu"))
+ self.aRefresh.setIcon(SHARED.theme.getIcon("refresh", "green"))
+ self.aExport.setIcon(SHARED.theme.getIcon("export", "blue"))
+ self.tbColumns.setIcon(SHARED.theme.getIcon("more_vertical"))
self.tbColumns.setStyleSheet("QToolButton::menu-indicator {image: none;}")
self.novelLabel.setTextColors(color=self.palette().windowText().color())
return
diff --git a/novelwriter/gui/projtree.py b/novelwriter/gui/projtree.py
index 564c4d66..61da1285 100644
--- a/novelwriter/gui/projtree.py
+++ b/novelwriter/gui/projtree.py
@@ -363,17 +363,17 @@ class GuiProjectToolBar(QWidget):
self.tbAdd.setStyleSheet(buttonStyle)
self.tbMore.setStyleSheet(buttonStyle)
- self.tbQuick.setThemeIcon("bookmark")
- self.tbMoveU.setThemeIcon("up")
- self.tbMoveD.setThemeIcon("down")
- self.tbAdd.setThemeIcon("add")
- self.tbMore.setThemeIcon("menu")
+ self.tbQuick.setThemeIcon("bookmarks", "blue")
+ self.tbMoveU.setThemeIcon("chevron_up", "blue")
+ self.tbMoveD.setThemeIcon("chevron_down", "blue")
+ self.tbAdd.setThemeIcon("add", "green")
+ self.tbMore.setThemeIcon("more_vertical")
- self.aAddEmpty.setIcon(SHARED.theme.getIcon("proj_document"))
- self.aAddChap.setIcon(SHARED.theme.getIcon("proj_chapter"))
- self.aAddScene.setIcon(SHARED.theme.getIcon("proj_scene"))
- self.aAddNote.setIcon(SHARED.theme.getIcon("proj_note"))
- self.aAddFolder.setIcon(SHARED.theme.getIcon("proj_folder"))
+ self.aAddEmpty.setIcon(SHARED.theme.getIcon("document"))
+ self.aAddChap.setIcon(SHARED.theme.getIcon("document", "red"))
+ self.aAddScene.setIcon(SHARED.theme.getIcon("document", "blue"))
+ self.aAddNote.setIcon(SHARED.theme.getIcon("document", "yellow"))
+ self.aAddFolder.setIcon(SHARED.theme.getIcon("folder"))
self.buildTemplatesMenu()
self.buildQuickLinksMenu()
@@ -394,7 +394,9 @@ class GuiProjectToolBar(QWidget):
for tHandle, nwItem in SHARED.project.tree.iterRoots(None):
action = self.mQuick.addAction(nwItem.itemName)
action.setData(tHandle)
- action.setIcon(SHARED.theme.getIcon(nwLabels.CLASS_ICON[nwItem.itemClass]))
+ action.setIcon(SHARED.theme.getIcon(
+ nwLabels.CLASS_ICON[nwItem.itemClass], nwLabels.CLASS_COLOR[nwItem.itemClass]
+ ))
action.triggered.connect(
qtLambda(self.projView.setSelectedHandle, tHandle, doScroll=True)
)
@@ -441,7 +443,9 @@ class GuiProjectToolBar(QWidget):
"""Build the rood folder menu."""
def addClass(itemClass: nwItemClass) -> None:
aNew = self.mAddRoot.addAction(trConst(nwLabels.CLASS_NAME[itemClass]))
- aNew.setIcon(SHARED.theme.getIcon(nwLabels.CLASS_ICON[itemClass]))
+ aNew.setIcon(SHARED.theme.getIcon(
+ nwLabels.CLASS_ICON[itemClass], nwLabels.CLASS_COLOR[itemClass]
+ ))
aNew.triggered.connect(
qtLambda(self.projTree.newTreeItem, nwItemType.ROOT, itemClass)
)
diff --git a/novelwriter/gui/search.py b/novelwriter/gui/search.py
index e6a51592..c3544750 100644
--- a/novelwriter/gui/search.py
+++ b/novelwriter/gui/search.py
@@ -105,7 +105,7 @@ class GuiProjectSearch(QWidget):
self.searchText.setClearButtonEnabled(True)
self.searchAction = self.searchText.addAction(
- SHARED.theme.getIcon("search"), QLineEdit.ActionPosition.TrailingPosition
+ SHARED.theme.getIcon("search", "blue"), QLineEdit.ActionPosition.TrailingPosition
)
self.searchAction.triggered.connect(self._processSearch)
@@ -173,7 +173,7 @@ class GuiProjectSearch(QWidget):
f"QLineEdit:focus {{border: {bPx}px solid {colFocus};}} "
)
- self.searchAction.setIcon(SHARED.theme.getIcon("search"))
+ self.searchAction.setIcon(SHARED.theme.getIcon("search", "blue"))
self.toggleCase.setIcon(SHARED.theme.getIcon("search_case"))
self.toggleWord.setIcon(SHARED.theme.getIcon("search_word"))
self.toggleRegEx.setIcon(SHARED.theme.getIcon("search_regex"))
diff --git a/novelwriter/gui/sidebar.py b/novelwriter/gui/sidebar.py
index 144695c9..d42e7a87 100644
--- a/novelwriter/gui/sidebar.py
+++ b/novelwriter/gui/sidebar.py
@@ -140,13 +140,13 @@ class GuiSideBar(QWidget):
self.tbStats.setStyleSheet(buttonStyle)
self.tbSettings.setStyleSheet(buttonStyle)
- self.tbProject.setThemeIcon("view_editor")
- self.tbNovel.setThemeIcon("view_novel")
- self.tbSearch.setThemeIcon("view_search")
- self.tbOutline.setThemeIcon("view_outline")
- self.tbBuild.setThemeIcon("view_build")
- self.tbDetails.setThemeIcon("proj_details")
- self.tbStats.setThemeIcon("proj_stats")
+ self.tbProject.setThemeIcon("project_view")
+ self.tbNovel.setThemeIcon("novel_view")
+ self.tbSearch.setThemeIcon("search")
+ self.tbOutline.setThemeIcon("outline")
+ self.tbBuild.setThemeIcon("manuscript")
+ self.tbDetails.setThemeIcon("list")
+ self.tbStats.setThemeIcon("stats")
self.tbSettings.setThemeIcon("settings")
return
diff --git a/novelwriter/gui/statusbar.py b/novelwriter/gui/statusbar.py
index 14e3f420..a2fe5b9f 100644
--- a/novelwriter/gui/statusbar.py
+++ b/novelwriter/gui/statusbar.py
@@ -129,10 +129,10 @@ class GuiMainStatus(QStatusBar):
def updateTheme(self) -> None:
"""Update theme elements."""
iPx = SHARED.theme.baseIconHeight
- self.langIcon.setPixmap(SHARED.theme.getPixmap("status_lang", (iPx, iPx)))
- self.statsIcon.setPixmap(SHARED.theme.getPixmap("status_stats", (iPx, iPx)))
- self.timePixmap = SHARED.theme.getPixmap("status_time", (iPx, iPx))
- self.idlePixmap = SHARED.theme.getPixmap("status_idle", (iPx, iPx))
+ self.langIcon.setPixmap(SHARED.theme.getPixmap("language", (iPx, iPx)))
+ self.statsIcon.setPixmap(SHARED.theme.getPixmap("stats", (iPx, iPx)))
+ self.timePixmap = SHARED.theme.getPixmap("timer", (iPx, iPx))
+ self.idlePixmap = SHARED.theme.getPixmap("timer_off", (iPx, iPx))
self.timeIcon.setPixmap(self.timePixmap)
colNone = SHARED.theme.statNone
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index 553786c2..18f4e543 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -501,36 +501,7 @@ class GuiIcons:
ICON_KEYS: set[str] = {
# Project and GUI Icons
- "novelwriter", "alert_error", "alert_info", "alert_question", "alert_warn",
- "build_excluded", "build_filtered", "build_included", "proj_chapter", "proj_details",
- "proj_document", "proj_folder", "proj_note", "proj_nwx", "proj_section", "proj_scene",
- "proj_stats", "proj_title", "status_idle", "status_lang", "status_lines", "status_stats",
- "status_time", "view_build", "view_editor", "view_novel", "view_outline", "view_search",
-
- # Class Icons
- "cls_archive", "cls_character", "cls_custom", "cls_entity", "cls_none", "cls_novel",
- "cls_object", "cls_plot", "cls_template", "cls_timeline", "cls_trash", "cls_world",
-
- # Search Icons
- "search_cancel", "search_case", "search_loop", "search_preserve", "search_project",
- "search_regex", "search_word",
-
- # Format Icons
- "fmt_bold", "fmt_bold-md", "fmt_italic", "fmt_italic-md", "fmt_mark", "fmt_strike",
- "fmt_strike-md", "fmt_subscript", "fmt_superscript", "fmt_underline", "margin_bottom",
- "margin_left", "margin_right", "margin_top", "size_height", "size_width",
-
- # General Button Icons
- "add", "add_document", "backward", "bookmark", "browse", "checked", "close", "copy",
- "cross", "document", "down", "edit", "export", "font", "forward", "import", "list",
- "maximise", "menu", "minimise", "more", "noncheckable", "open", "panel", "quote",
- "refresh", "remove", "revert", "search_replace", "search", "settings", "star", "toolbar",
- "unchecked", "up", "view",
-
- # Switches
- "sticky-on", "sticky-off",
- "bullet-on", "bullet-off",
- "unfold-show", "unfold-hide",
+ "novelwriter", "proj_nwx"
# Decorations
"deco_doc_h0", "deco_doc_h1", "deco_doc_h2", "deco_doc_h3", "deco_doc_h4", "deco_doc_more",
@@ -539,7 +510,6 @@ class GuiIcons:
}
TOGGLE_ICON_KEYS: dict[str, tuple[str, str]] = {
- "sticky": ("sticky-on", "sticky-off"),
"bullet": ("bullet-on", "bullet-off"),
"unfold": ("unfold-show", "unfold-hide"),
}
@@ -631,7 +601,7 @@ class GuiIcons:
iconPath = themePath / iconFile
if iconPath.is_file():
self._themeMap[iconName] = iconPath
- logger.debug("Icon slot '%s' using file '%s'", iconName, iconFile)
+ # logger.debug("Icon slot '%s' using file '%s'", iconName, iconFile)
else:
logger.error("Icon file '%s' not in theme folder", iconFile)
@@ -657,7 +627,7 @@ class GuiIcons:
def loadNewTheme(self, iconTheme: str) -> bool:
"""Load new style theme."""
- themePath = self._iconPath / "material_outline_normal.icons"
+ themePath = self._iconPath / "material_outline_bold.icons"
with open(themePath, mode="r", encoding="utf-8") as icons:
for icon in icons:
key, _, svg = icon.partition(" = ")
@@ -703,60 +673,62 @@ class GuiIcons:
return pixmap
- def getIcon(self, name: str, color: str | None = None) -> QIcon:
+ def getIcon(self, name: str, color: str | None = None, w: int = 24, h: int = 24) -> QIcon:
"""Return an icon from the icon buffer, or load it."""
- key = f"{name}_{color}" if color else name
- if key in self._qIcons:
- return self._qIcons[name]
+ variant = f"{name}-{color}" if color else name
+ if (key := f"{variant}-{w}x{h}") in self._qIcons:
+ return self._qIcons[key]
else:
- icon = self._loadIcon(name, color)
+ icon = self._loadIcon(name, color, w, h)
self._qIcons[key] = icon
+ logger.info("Icon: %s", key)
return icon
- def getToggleIcon(self, name: str, size: tuple[int, int]) -> QIcon:
+ def getToggleIcon(self, name: str, size: tuple[int, int], color: str | None = None) -> QIcon:
"""Return a toggle icon from the icon buffer. or load it."""
if name in self.TOGGLE_ICON_KEYS:
- pOne = self.getPixmap(self.TOGGLE_ICON_KEYS[name][0], size)
- pTwo = self.getPixmap(self.TOGGLE_ICON_KEYS[name][1], size)
+ pOne = self.getPixmap(self.TOGGLE_ICON_KEYS[name][0], size, color)
+ pTwo = self.getPixmap(self.TOGGLE_ICON_KEYS[name][1], size, color)
icon = QIcon()
icon.addPixmap(pOne, QIcon.Mode.Normal, QIcon.State.On)
icon.addPixmap(pTwo, QIcon.Mode.Normal, QIcon.State.Off)
return icon
return self._noIcon
- def getPixmap(self, name: str, size: tuple[int, int]) -> QPixmap:
+ def getPixmap(self, name: str, size: tuple[int, int], color: str | None = None) -> QPixmap:
"""Return an icon from the icon buffer as a QPixmap. If it
doesn't exist, return an empty QPixmap.
"""
- return self.getIcon(name).pixmap(size[0], size[1], QIcon.Mode.Normal)
+ w, h = size
+ return self.getIcon(name, color, w, h).pixmap(w, h, QIcon.Mode.Normal)
def getItemIcon(self, tType: nwItemType, tClass: nwItemClass,
tLayout: nwItemLayout, hLevel: str = "H0") -> QIcon:
"""Get the correct icon for a project item based on type, class
and heading level
"""
- iconName = None
+ name = None
+ color = "default"
if tType == nwItemType.ROOT:
- iconName = nwLabels.CLASS_ICON[tClass]
+ name = nwLabels.CLASS_ICON[tClass]
+ color = nwLabels.CLASS_COLOR[tClass]
elif tType == nwItemType.FOLDER:
- iconName = "proj_folder"
+ name = "folder"
elif tType == nwItemType.FILE:
- iconName = "proj_document"
+ name = "document"
if tLayout == nwItemLayout.DOCUMENT:
if hLevel == "H1":
- iconName = "proj_title"
+ color = "green"
elif hLevel == "H2":
- iconName = "proj_chapter"
+ color = "red"
elif hLevel == "H3":
- iconName = "proj_scene"
- elif hLevel == "H4":
- iconName = "proj_section"
+ color = "blue"
elif tLayout == nwItemLayout.NOTE:
- iconName = "proj_note"
- if iconName is None:
+ color = "yellow"
+ if name is None:
return self._noIcon
- return self.getIcon(iconName)
+ return self.getIcon(name, color)
def getHeaderDecoration(self, hLevel: int) -> QPixmap:
"""Get the decoration for a specific heading level."""
@@ -789,14 +761,10 @@ class GuiIcons:
# Internal Functions
##
- def _loadIcon(self, name: str, color: str | None = None) -> QIcon:
+ def _loadIcon(self, name: str, color: str | None = None, w: int = 24, h: int = 24) -> QIcon:
"""Load an icon from the assets themes folder. Is guaranteed to
return a QIcon.
"""
- # if name not in self.ICON_KEYS:
- # logger.error("Requested unknown icon name '%s'", name)
- # return self._noIcon
-
# If we just want the app icons, return right away
if name == "novelwriter":
return QIcon(str(self._iconPath / "novelwriter.svg"))
@@ -806,7 +774,7 @@ class GuiIcons:
if svg := self._svgData.get(name, b""):
if fill := self._svgColours.get(color or "default"):
svg = svg.replace(b"#000000", fill)
- pixmap = QPixmap(24, 24)
+ pixmap = QPixmap(w, h)
pixmap.fill(QtTransparent)
pixmap.loadFromData(svg, "svg")
return QIcon(pixmap)
diff --git a/novelwriter/shared.py b/novelwriter/shared.py
index b02395cb..86ef6eca 100644
--- a/novelwriter/shared.py
+++ b/novelwriter/shared.py
@@ -485,15 +485,15 @@ class _GuiAlert(QMessageBox):
self.setStandardButtons(QMessageBox.StandardButton.Ok)
pSz = 2*self._theme.baseIconHeight
if level == self.INFO:
- self.setIconPixmap(self._theme.getPixmap("alert_info", (pSz, pSz)))
+ self.setIconPixmap(self._theme.getPixmap("alert_info", (pSz, pSz), "blue"))
self.setWindowTitle(self.tr("Information"))
elif level == self.WARN:
- self.setIconPixmap(self._theme.getPixmap("alert_warn", (pSz, pSz)))
+ self.setIconPixmap(self._theme.getPixmap("alert_warn", (pSz, pSz), "orange"))
self.setWindowTitle(self.tr("Warning"))
elif level == self.ERROR:
- self.setIconPixmap(self._theme.getPixmap("alert_error", (pSz, pSz)))
+ self.setIconPixmap(self._theme.getPixmap("alert_error", (pSz, pSz), "red"))
self.setWindowTitle(self.tr("Error"))
elif level == self.ASK:
- self.setIconPixmap(self._theme.getPixmap("alert_question", (pSz, pSz)))
+ self.setIconPixmap(self._theme.getPixmap("alert_question", (pSz, pSz), "blue"))
self.setWindowTitle(self.tr("Question"))
return
diff --git a/novelwriter/tools/dictionaries.py b/novelwriter/tools/dictionaries.py
index eb22ff38..057637af 100644
--- a/novelwriter/tools/dictionaries.py
+++ b/novelwriter/tools/dictionaries.py
@@ -78,7 +78,7 @@ class GuiDictionaries(NNonBlockingDialog):
self.huBrowse = NIconToolButton(self, iSz, "browse")
self.huBrowse.clicked.connect(self._doBrowseHunspell)
self.huImport = QPushButton(self.tr("Add Dictionary"), self)
- self.huImport.setIcon(SHARED.theme.getIcon("add"))
+ self.huImport.setIcon(SHARED.theme.getIcon("add", "green"))
self.huImport.clicked.connect(self._doImportHunspell)
self.huPathBox = QHBoxLayout()
diff --git a/novelwriter/tools/lipsum.py b/novelwriter/tools/lipsum.py
index 590d12f8..1ca20005 100644
--- a/novelwriter/tools/lipsum.py
+++ b/novelwriter/tools/lipsum.py
@@ -60,7 +60,7 @@ class GuiLipsum(NDialog):
# Icon
self.docIcon = QLabel(self)
- self.docIcon.setPixmap(SHARED.theme.getPixmap("proj_document", (nPx, nPx)))
+ self.docIcon.setPixmap(SHARED.theme.getPixmap("document", (nPx, nPx), "blue"))
self.leftBox = QVBoxLayout()
self.leftBox.setSpacing(vSp)
diff --git a/novelwriter/tools/manusbuild.py b/novelwriter/tools/manusbuild.py
index 34f405a7..4c90aa73 100644
--- a/novelwriter/tools/manusbuild.py
+++ b/novelwriter/tools/manusbuild.py
@@ -154,7 +154,7 @@ class GuiManuscriptBuild(NDialog):
# Build Name
self.lblName = QLabel(self.tr("File Name"), self)
self.buildName = QLineEdit(self)
- self.btnReset = NIconToolButton(self, iSz, "revert")
+ self.btnReset = NIconToolButton(self, iSz, "revert", "green")
self.btnReset.setToolTip(self.tr("Reset file name to default"))
self.nameBox = QHBoxLayout()
@@ -181,12 +181,16 @@ class GuiManuscriptBuild(NDialog):
# Dialog Buttons
self.buttonBox = QDialogButtonBox(self)
- self.btnOpen = QPushButton(SHARED.theme.getIcon("browse"), self.tr("Open Folder"), self)
+ self.btnOpen = QPushButton(
+ SHARED.theme.getIcon("browse", "yellow"), self.tr("Open Folder"), self
+ )
self.btnOpen.setIconSize(bSz)
self.btnOpen.setAutoDefault(False)
self.buttonBox.addButton(self.btnOpen, QtRoleAction)
- self.btnBuild = QPushButton(SHARED.theme.getIcon("export"), self.tr("&Build"), self)
+ self.btnBuild = QPushButton(
+ SHARED.theme.getIcon("manuscript", "blue"), self.tr("&Build"), self
+ )
self.btnBuild.setIconSize(bSz)
self.btnBuild.setAutoDefault(True)
self.buttonBox.addButton(self.btnBuild, QtRoleAction)
diff --git a/novelwriter/tools/manuscript.py b/novelwriter/tools/manuscript.py
index 041132d8..a5952c3b 100644
--- a/novelwriter/tools/manuscript.py
+++ b/novelwriter/tools/manuscript.py
@@ -108,7 +108,7 @@ class GuiManuscript(NToolDialog):
buttonStyle = SHARED.theme.getStyleSheet(STYLES_MIN_TOOLBUTTON)
- self.tbAdd = NIconToolButton(self, iSz, "add")
+ self.tbAdd = NIconToolButton(self, iSz, "add", "green")
self.tbAdd.setToolTip(self.tr("Add New Build"))
self.tbAdd.setStyleSheet(buttonStyle)
self.tbAdd.clicked.connect(self._createNewBuild)
@@ -118,12 +118,12 @@ class GuiManuscript(NToolDialog):
self.tbDel.setStyleSheet(buttonStyle)
self.tbDel.clicked.connect(self._deleteSelectedBuild)
- self.tbCopy = NIconToolButton(self, iSz, "copy")
+ self.tbCopy = NIconToolButton(self, iSz, "copy", "blue")
self.tbCopy.setToolTip(self.tr("Duplicate Selected Build"))
self.tbCopy.setStyleSheet(buttonStyle)
self.tbCopy.clicked.connect(self._copySelectedBuild)
- self.tbEdit = NIconToolButton(self, iSz, "edit")
+ self.tbEdit = NIconToolButton(self, iSz, "edit", "green")
self.tbEdit.setToolTip(self.tr("Edit Selected Build"))
self.tbEdit.setStyleSheet(buttonStyle)
self.tbEdit.clicked.connect(self._editSelectedBuild)
@@ -490,7 +490,7 @@ class GuiManuscript(NToolDialog):
for key, name in self._builds.builds():
bItem = QListWidgetItem()
bItem.setText(name)
- bItem.setIcon(SHARED.theme.getIcon("export"))
+ bItem.setIcon(SHARED.theme.getIcon("manuscript", "blue"))
bItem.setData(self.D_KEY, key)
self.buildList.addItem(bItem)
self._buildMap[key] = bItem
@@ -585,8 +585,8 @@ class _DetailsWidget(QWidget):
self.listView.clear()
- on = SHARED.theme.getIcon("bullet-on")
- off = SHARED.theme.getIcon("bullet-off")
+ on = SHARED.theme.getIcon("bullet-on", "blue")
+ off = SHARED.theme.getIcon("bullet-off", "blue")
# Name
item = QTreeWidgetItem()
diff --git a/novelwriter/tools/manussettings.py b/novelwriter/tools/manussettings.py
index b0023c67..ab9cb041 100644
--- a/novelwriter/tools/manussettings.py
+++ b/novelwriter/tools/manussettings.py
@@ -287,9 +287,9 @@ class _FilterTab(NFixedPage):
self._statusFlags: dict[int, QIcon] = {
self.F_NONE: QIcon(),
- self.F_FILTERED: SHARED.theme.getIcon("build_filtered"),
- self.F_INCLUDED: SHARED.theme.getIcon("build_included"),
- self.F_EXCLUDED: SHARED.theme.getIcon("build_excluded"),
+ self.F_FILTERED: SHARED.theme.getIcon("filter", "orange"),
+ self.F_INCLUDED: SHARED.theme.getIcon("pin", "blue"),
+ self.F_EXCLUDED: SHARED.theme.getIcon("exclude", "red"),
}
self._trIncluded = self.tr("Included in manuscript")
@@ -337,7 +337,7 @@ class _FilterTab(NFixedPage):
self.excludedButton.setIcon(self._statusFlags[self.F_EXCLUDED])
self.excludedButton.clicked.connect(qtLambda(self._setSelectedMode, self.F_EXCLUDED))
- self.resetButton = NIconToolButton(self, iSz, "revert")
+ self.resetButton = NIconToolButton(self, iSz, "revert", "green")
self.resetButton.setToolTip(self.tr("Reset to default"))
self.resetButton.clicked.connect(qtLambda(self._setSelectedMode, self.F_FILTERED))
@@ -459,19 +459,19 @@ class _FilterTab(NFixedPage):
self.filterOpt.clear()
self.filterOpt.addLabel(self._build.getLabel("filter"))
self.filterOpt.addItem(
- SHARED.theme.getIcon("proj_scene"),
+ SHARED.theme.getIcon("document", "blue"),
self._build.getLabel("filter.includeNovel"),
"doc:filter.includeNovel",
default=self._build.getBool("filter.includeNovel")
)
self.filterOpt.addItem(
- SHARED.theme.getIcon("proj_note"),
+ SHARED.theme.getIcon("document", "yellow"),
self._build.getLabel("filter.includeNotes"),
"doc:filter.includeNotes",
default=self._build.getBool("filter.includeNotes")
)
self.filterOpt.addItem(
- SHARED.theme.getIcon("unchecked"),
+ SHARED.theme.getIcon("unchecked", "red"),
self._build.getLabel("filter.includeInactive"),
"doc:filter.includeInactive",
default=self._build.getBool("filter.includeInactive")
@@ -572,7 +572,7 @@ class _HeadingsTab(NScrollablePage):
self.lblPart = QLabel(self._build.getLabel("headings.fmtPart"), self)
self.fmtPart = QLineEdit("", self)
self.fmtPart.setReadOnly(True)
- self.btnPart = NIconToolButton(self, iSz, "edit")
+ self.btnPart = NIconToolButton(self, iSz, "edit", "green")
self.btnPart.clicked.connect(qtLambda(self._editHeading, self.EDIT_TITLE))
self.hdePart = QLabel(trHide, self)
self.hdePart.setIndent(bSp)
@@ -588,7 +588,7 @@ class _HeadingsTab(NScrollablePage):
self.lblChapter = QLabel(self._build.getLabel("headings.fmtChapter"), self)
self.fmtChapter = QLineEdit("", self)
self.fmtChapter.setReadOnly(True)
- self.btnChapter = NIconToolButton(self, iSz, "edit")
+ self.btnChapter = NIconToolButton(self, iSz, "edit", "green")
self.btnChapter.clicked.connect(qtLambda(self._editHeading, self.EDIT_CHAPTER))
self.hdeChapter = QLabel(trHide, self)
self.hdeChapter.setIndent(bSp)
@@ -604,7 +604,7 @@ class _HeadingsTab(NScrollablePage):
self.lblUnnumbered = QLabel(self._build.getLabel("headings.fmtUnnumbered"), self)
self.fmtUnnumbered = QLineEdit("", self)
self.fmtUnnumbered.setReadOnly(True)
- self.btnUnnumbered = NIconToolButton(self, iSz, "edit")
+ self.btnUnnumbered = NIconToolButton(self, iSz, "edit", "green")
self.btnUnnumbered.clicked.connect(qtLambda(self._editHeading, self.EDIT_UNNUM))
self.hdeUnnumbered = QLabel(trHide, self)
self.hdeUnnumbered.setIndent(bSp)
@@ -620,7 +620,7 @@ class _HeadingsTab(NScrollablePage):
self.lblScene = QLabel(self._build.getLabel("headings.fmtScene"), self)
self.fmtScene = QLineEdit("", self)
self.fmtScene.setReadOnly(True)
- self.btnScene = NIconToolButton(self, iSz, "edit")
+ self.btnScene = NIconToolButton(self, iSz, "edit", "green")
self.btnScene.clicked.connect(qtLambda(self._editHeading, self.EDIT_SCENE))
self.hdeScene = QLabel(trHide, self)
self.hdeScene.setIndent(bSp)
@@ -636,7 +636,7 @@ class _HeadingsTab(NScrollablePage):
self.lblAScene = QLabel(self._build.getLabel("headings.fmtAltScene"), self)
self.fmtAScene = QLineEdit("", self)
self.fmtAScene.setReadOnly(True)
- self.btnAScene = NIconToolButton(self, iSz, "edit")
+ self.btnAScene = NIconToolButton(self, iSz, "edit", "green")
self.btnAScene.clicked.connect(qtLambda(self._editHeading, self.EDIT_HSCENE))
self.hdeAScene = QLabel(trHide, self)
self.hdeAScene.setIndent(bSp)
@@ -652,7 +652,7 @@ class _HeadingsTab(NScrollablePage):
self.lblSection = QLabel(self._build.getLabel("headings.fmtSection"), self)
self.fmtSection = QLineEdit("", self)
self.fmtSection.setReadOnly(True)
- self.btnSection = NIconToolButton(self, iSz, "edit")
+ self.btnSection = NIconToolButton(self, iSz, "edit", "green")
self.btnSection.clicked.connect(qtLambda(self._editHeading, self.EDIT_SECTION))
self.hdeSection = QLabel(trHide, self)
self.hdeSection.setIndent(bSp)
@@ -977,7 +977,7 @@ class _FormattingTab(NScrollableForm):
lambda keyword=keyword: self._updateIgnoredKeywords(keyword)
)
- self.ignoredKeywordsButton = NIconToolButton(self, iSz, "add")
+ self.ignoredKeywordsButton = NIconToolButton(self, iSz, "add", "green")
self.ignoredKeywordsButton.setMenu(self.mnKeywords)
self.addRow(
self._build.getLabel("text.ignoredKeywords"), self.ignoredKeywords,
@@ -1063,8 +1063,8 @@ class _FormattingTab(NScrollableForm):
pixB = SHARED.theme.getPixmap("margin_bottom", (iPx, iPx))
pixL = SHARED.theme.getPixmap("margin_left", (iPx, iPx))
pixR = SHARED.theme.getPixmap("margin_right", (iPx, iPx))
- pixH = SHARED.theme.getPixmap("size_height", (iPx, iPx))
- pixW = SHARED.theme.getPixmap("size_width", (iPx, iPx))
+ pixH = SHARED.theme.getPixmap("fit_height", (iPx, iPx))
+ pixW = SHARED.theme.getPixmap("fit_width", (iPx, iPx))
# Title
self.titleMarginT = NDoubleSpinBox(self)
@@ -1223,7 +1223,7 @@ class _FormattingTab(NScrollableForm):
# Header
self.odtPageHeader = QLineEdit(self)
self.odtPageHeader.setMinimumWidth(CONFIG.pxInt(200))
- self.btnPageHeader = NIconToolButton(self, iSz, "revert")
+ self.btnPageHeader = NIconToolButton(self, iSz, "revert", "green")
self.btnPageHeader.clicked.connect(self._resetPageHeader)
self.addRow(
self._build.getLabel("doc.pageHeader"), self.odtPageHeader,
diff --git a/novelwriter/tools/welcome.py b/novelwriter/tools/welcome.py
index 74f57971..85482cfe 100644
--- a/novelwriter/tools/welcome.py
+++ b/novelwriter/tools/welcome.py
@@ -110,32 +110,32 @@ class GuiWelcome(NDialog):
# =======
self.btnList = QPushButton(self.tr("List"), self)
- self.btnList.setIcon(SHARED.theme.getIcon("list"))
+ self.btnList.setIcon(SHARED.theme.getIcon("list", "blue"))
self.btnList.setIconSize(btnIconSize)
self.btnList.clicked.connect(self._showOpenProjectPage)
self.btnNew = QPushButton(self.tr("New"), self)
- self.btnNew.setIcon(SHARED.theme.getIcon("add"))
+ self.btnNew.setIcon(SHARED.theme.getIcon("add", "green"))
self.btnNew.setIconSize(btnIconSize)
self.btnNew.clicked.connect(self._showNewProjectPage)
self.btnBrowse = QPushButton(self.tr("Browse"), self)
- self.btnBrowse.setIcon(SHARED.theme.getIcon("browse"))
+ self.btnBrowse.setIcon(SHARED.theme.getIcon("browse", "yellow"))
self.btnBrowse.setIconSize(btnIconSize)
self.btnBrowse.clicked.connect(self._browseForProject)
self.btnCancel = QPushButton(self.tr("Cancel"), self)
- self.btnCancel.setIcon(SHARED.theme.getIcon("cross"))
+ self.btnCancel.setIcon(SHARED.theme.getIcon("cancel", "red"))
self.btnCancel.setIconSize(btnIconSize)
self.btnCancel.clicked.connect(self.close)
self.btnCreate = QPushButton(self.tr("Create"), self)
- self.btnCreate.setIcon(SHARED.theme.getIcon("star"))
+ self.btnCreate.setIcon(SHARED.theme.getIcon("star", "yellow"))
self.btnCreate.setIconSize(btnIconSize)
self.btnCreate.clicked.connect(self.tabNew.createNewProject)
self.btnOpen = QPushButton(self.tr("Open"), self)
- self.btnOpen.setIcon(SHARED.theme.getIcon("open"))
+ self.btnOpen.setIcon(SHARED.theme.getIcon("open", "blue"))
self.btnOpen.setIconSize(btnIconSize)
self.btnOpen.clicked.connect(self._openSelectedItem)
@@ -289,7 +289,7 @@ class _OpenProjectPage(QWidget):
# Info / Tool
self.aMissing = QAction(self)
- self.aMissing.setIcon(SHARED.theme.getIcon("alert_warn"))
+ self.aMissing.setIcon(SHARED.theme.getIcon("alert_warn", "orange"))
self.aMissing.setToolTip(self.tr("The project path is not reachable."))
self.selectedPath = QLineEdit(self)
@@ -589,7 +589,7 @@ class _NewProjectForm(QWidget):
self.projFill = QLineEdit(self)
self.projFill.setReadOnly(True)
- self.browseFill = NIconToolButton(self, iSz, "add_document")
+ self.browseFill = NIconToolButton(self, iSz, "document_add", "blue")
self.fillMenu = _PopLeftDirectionMenu(self.browseFill)
@@ -598,11 +598,11 @@ class _NewProjectForm(QWidget):
self.fillBlank.triggered.connect(self._setFillBlank)
self.fillSample = self.fillMenu.addAction(self.tr("Create an example project"))
- self.fillSample.setIcon(SHARED.theme.getIcon("add_document"))
+ self.fillSample.setIcon(SHARED.theme.getIcon("document_add", "blue"))
self.fillSample.triggered.connect(self._setFillSample)
self.fillCopy = self.fillMenu.addAction(self.tr("Copy an existing project"))
- self.fillCopy.setIcon(SHARED.theme.getIcon("browse"))
+ self.fillCopy.setIcon(SHARED.theme.getIcon("project_copy", "green"))
self.fillCopy.triggered.connect(self._setFillCopy)
self.browseFill.setMenu(self.fillMenu)
diff --git a/utils/material_icons.py b/utils/material_icons.py
index 45292969..471284b6 100644
--- a/utils/material_icons.py
+++ b/utils/material_icons.py
@@ -69,27 +69,61 @@ ICON_MAP = {
"bullet-off": "radio_button_unchecked",
"bullet-on": "radio_button_checked",
+ "unfold-hide": "arrow_right",
+ "unfold-show": "arrow_drop_down",
+ "add": "add",
"bookmarks": "bookmarks",
+ "browse": "folder_open",
+ "cancel": "cancel",
"checked": "select_check_box",
"chevron_down": "keyboard_arrow_down",
"chevron_left": "arrow_back_ios",
"chevron_right": "arrow_forward_ios",
"chevron_up": "keyboard_arrow_up",
"close": "close",
+ "copy": "content_copy",
"document_add": "note_add",
"document": "description",
"edit": "edit",
+ "exclude": "do_not_disturb_on",
+ "export": "share_windows",
+ "filter": "filter_alt",
+ "fit_height": "fit_page_height",
+ "fit_width": "fit_page_width",
"folder": "folder",
- "item_add": "add",
+ "font": "font_download",
+ "import": "tab_move",
+ "language": "translate",
+ "lines": "reorder",
"list": "format_list_bulleted",
+ "manuscript": "export_notes",
+ "margin_bottom": "vertical_align_bottom",
+ "margin_left": "keyboard_tab_rtl",
+ "margin_right": "keyboard_tab",
+ "margin_top": "vertical_align_top",
"maximise": "fullscreen",
- "minimise": "close_fullscreen",
+ "minimise": "fullscreen_exit",
"more_vertical": "more_vert",
"noncheckable": "indeterminate_check_box",
+ "novel_view": "book_4_spark",
+ "open": "open_in_new",
+ "outline": "table",
+ "panel": "dock_to_bottom",
+ "pin": "keep",
"project_copy": "folder_copy",
+ "project_view": "bookmark_manager",
+ "quote": "format_quote",
"refresh": "refresh",
+ "remove": "remove",
+ "revert": "settings_backup_restore",
+ "settings": "settings",
+ "star": "star",
+ "stats": "bar_chart",
+ "timer_off": "timer_off",
+ "timer": "timer",
"unchecked": "disabled_by_default",
+ "view": "visibility",
}
From 5cc29a760593733354b6a236b829f313648148f1 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Wed, 8 Jan 2025 00:20:31 +0100
Subject: [PATCH 06/18] Update icons files
---
.../assets/icons/material_filled_bold.icons | 186 +++++++++---------
.../assets/icons/material_filled_normal.icons | 186 +++++++++---------
.../assets/icons/material_outline_bold.icons | 186 +++++++++---------
.../icons/material_outline_normal.icons | 186 +++++++++---------
.../assets/icons/material_rounded_bold.icons | 97 +++++++++
.../icons/material_rounded_normal.icons | 97 +++++++++
novelwriter/gui/theme.py | 27 ++-
pkgutils.py | 50 +++--
utils/material_icons.py | 52 +++--
9 files changed, 677 insertions(+), 390 deletions(-)
create mode 100644 novelwriter/assets/icons/material_rounded_bold.icons
create mode 100644 novelwriter/assets/icons/material_rounded_normal.icons
diff --git a/novelwriter/assets/icons/material_filled_bold.icons b/novelwriter/assets/icons/material_filled_bold.icons
index b043b7c9..9dc5a503 100644
--- a/novelwriter/assets/icons/material_filled_bold.icons
+++ b/novelwriter/assets/icons/material_filled_bold.icons
@@ -1,89 +1,97 @@
-alert_error =
-alert_info =
-alert_question =
-alert_warn =
-cls_archive =
-cls_character =
-cls_custom =
-cls_entity =
-cls_none =
-cls_novel =
-cls_object =
-cls_plot =
-cls_template =
-cls_timeline =
-cls_trash =
-cls_world =
-fmt_bold =
-fmt_italic =
-fmt_mark =
-fmt_strike =
-fmt_subscript =
-fmt_superscript =
-fmt_underline =
-fmt_toolbar =
-search_cancel =
-search_case =
-search_loop =
-search_preserve =
-search_project =
-search_regex =
-search_replace =
-search_word =
-search =
-bullet-off =
-bullet-on =
-unfold-hide =
-unfold-show =
-add =
-bookmarks =
-browse =
-cancel =
-checked =
-chevron_down =
-chevron_left =
-chevron_right =
-chevron_up =
-close =
-copy =
-document_add =
-document =
-edit =
-exclude =
-export =
-filter =
-fit_height =
-fit_width =
-folder =
-font =
-import =
-language =
-lines =
-list =
-manuscript =
-margin_bottom =
-margin_left =
-margin_right =
-margin_top =
-maximise =
-minimise =
-more_vertical =
-noncheckable =
-novel_view =
-open =
-outline =
-panel =
-pin =
-project_copy =
-project_view =
-quote =
-refresh =
-remove =
-revert =
-settings =
-star =
-stats =
-timer_off =
-timer =
-unchecked =
-view =
+# This file is automatically generated. Do not edit.
+
+# Meta
+meta:name = Material Symbols - Filled Bold
+meta:author = Google
+meta:licence = Apache License Version 2.0
+
+# Icons
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/novelwriter/assets/icons/material_filled_normal.icons b/novelwriter/assets/icons/material_filled_normal.icons
index e70f277f..c729da16 100644
--- a/novelwriter/assets/icons/material_filled_normal.icons
+++ b/novelwriter/assets/icons/material_filled_normal.icons
@@ -1,89 +1,97 @@
-alert_error =
-alert_info =
-alert_question =
-alert_warn =
-cls_archive =
-cls_character =
-cls_custom =
-cls_entity =
-cls_none =
-cls_novel =
-cls_object =
-cls_plot =
-cls_template =
-cls_timeline =
-cls_trash =
-cls_world =
-fmt_bold =
-fmt_italic =
-fmt_mark =
-fmt_strike =
-fmt_subscript =
-fmt_superscript =
-fmt_underline =
-fmt_toolbar =
-search_cancel =
-search_case =
-search_loop =
-search_preserve =
-search_project =
-search_regex =
-search_replace =
-search_word =
-search =
-bullet-off =
-bullet-on =
-unfold-hide =
-unfold-show =
-add =
-bookmarks =
-browse =
-cancel =
-checked =
-chevron_down =
-chevron_left =
-chevron_right =
-chevron_up =
-close =
-copy =
-document_add =
-document =
-edit =
-exclude =
-export =
-filter =
-fit_height =
-fit_width =
-folder =
-font =
-import =
-language =
-lines =
-list =
-manuscript =
-margin_bottom =
-margin_left =
-margin_right =
-margin_top =
-maximise =
-minimise =
-more_vertical =
-noncheckable =
-novel_view =
-open =
-outline =
-panel =
-pin =
-project_copy =
-project_view =
-quote =
-refresh =
-remove =
-revert =
-settings =
-star =
-stats =
-timer_off =
-timer =
-unchecked =
-view =
+# This file is automatically generated. Do not edit.
+
+# Meta
+meta:name = Material Symbols - Filled
+meta:author = Google
+meta:licence = Apache License Version 2.0
+
+# Icons
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/novelwriter/assets/icons/material_outline_bold.icons b/novelwriter/assets/icons/material_outline_bold.icons
index 7225e7b1..a1ae5ea5 100644
--- a/novelwriter/assets/icons/material_outline_bold.icons
+++ b/novelwriter/assets/icons/material_outline_bold.icons
@@ -1,89 +1,97 @@
-alert_error =
-alert_info =
-alert_question =
-alert_warn =
-cls_archive =
-cls_character =
-cls_custom =
-cls_entity =
-cls_none =
-cls_novel =
-cls_object =
-cls_plot =
-cls_template =
-cls_timeline =
-cls_trash =
-cls_world =
-fmt_bold =
-fmt_italic =
-fmt_mark =
-fmt_strike =
-fmt_subscript =
-fmt_superscript =
-fmt_underline =
-fmt_toolbar =
-search_cancel =
-search_case =
-search_loop =
-search_preserve =
-search_project =
-search_regex =
-search_replace =
-search_word =
-search =
-bullet-off =
-bullet-on =
-unfold-hide =
-unfold-show =
-add =
-bookmarks =
-browse =
-cancel =
-checked =
-chevron_down =
-chevron_left =
-chevron_right =
-chevron_up =
-close =
-copy =
-document_add =
-document =
-edit =
-exclude =
-export =
-filter =
-fit_height =
-fit_width =
-folder =
-font =
-import =
-language =
-lines =
-list =
-manuscript =
-margin_bottom =
-margin_left =
-margin_right =
-margin_top =
-maximise =
-minimise =
-more_vertical =
-noncheckable =
-novel_view =
-open =
-outline =
-panel =
-pin =
-project_copy =
-project_view =
-quote =
-refresh =
-remove =
-revert =
-settings =
-star =
-stats =
-timer_off =
-timer =
-unchecked =
-view =
+# This file is automatically generated. Do not edit.
+
+# Meta
+meta:name = Material Symbols - Outlined Bold
+meta:author = Google
+meta:licence = Apache License Version 2.0
+
+# Icons
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/novelwriter/assets/icons/material_outline_normal.icons b/novelwriter/assets/icons/material_outline_normal.icons
index bf199798..14d66542 100644
--- a/novelwriter/assets/icons/material_outline_normal.icons
+++ b/novelwriter/assets/icons/material_outline_normal.icons
@@ -1,89 +1,97 @@
-alert_error =
-alert_info =
-alert_question =
-alert_warn =
-cls_archive =
-cls_character =
-cls_custom =
-cls_entity =
-cls_none =
-cls_novel =
-cls_object =
-cls_plot =
-cls_template =
-cls_timeline =
-cls_trash =
-cls_world =
-fmt_bold =
-fmt_italic =
-fmt_mark =
-fmt_strike =
-fmt_subscript =
-fmt_superscript =
-fmt_underline =
-fmt_toolbar =
-search_cancel =
-search_case =
-search_loop =
-search_preserve =
-search_project =
-search_regex =
-search_replace =
-search_word =
-search =
-bullet-off =
-bullet-on =
-unfold-hide =
-unfold-show =
-add =
-bookmarks =
-browse =
-cancel =
-checked =
-chevron_down =
-chevron_left =
-chevron_right =
-chevron_up =
-close =
-copy =
-document_add =
-document =
-edit =
-exclude =
-export =
-filter =
-fit_height =
-fit_width =
-folder =
-font =
-import =
-language =
-lines =
-list =
-manuscript =
-margin_bottom =
-margin_left =
-margin_right =
-margin_top =
-maximise =
-minimise =
-more_vertical =
-noncheckable =
-novel_view =
-open =
-outline =
-panel =
-pin =
-project_copy =
-project_view =
-quote =
-refresh =
-remove =
-revert =
-settings =
-star =
-stats =
-timer_off =
-timer =
-unchecked =
-view =
+# This file is automatically generated. Do not edit.
+
+# Meta
+meta:name = Material Symbols - Outlined
+meta:author = Google
+meta:licence = Apache License Version 2.0
+
+# Icons
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/novelwriter/assets/icons/material_rounded_bold.icons b/novelwriter/assets/icons/material_rounded_bold.icons
new file mode 100644
index 00000000..7d28ed46
--- /dev/null
+++ b/novelwriter/assets/icons/material_rounded_bold.icons
@@ -0,0 +1,97 @@
+# This file is automatically generated. Do not edit.
+
+# Meta
+meta:name = Material Symbols - Rounded Bold
+meta:author = Google
+meta:licence = Apache License Version 2.0
+
+# Icons
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/novelwriter/assets/icons/material_rounded_normal.icons b/novelwriter/assets/icons/material_rounded_normal.icons
new file mode 100644
index 00000000..c4022290
--- /dev/null
+++ b/novelwriter/assets/icons/material_rounded_normal.icons
@@ -0,0 +1,97 @@
+# This file is automatically generated. Do not edit.
+
+# Meta
+meta:name = Material Symbols - Rounded
+meta:author = Google
+meta:licence = Apache License Version 2.0
+
+# Icons
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index 18f4e543..5dfc079b 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -627,12 +627,15 @@ class GuiIcons:
def loadNewTheme(self, iconTheme: str) -> bool:
"""Load new style theme."""
- themePath = self._iconPath / "material_outline_bold.icons"
+ themePath = self._iconPath / "material_rounded_normal.icons"
with open(themePath, mode="r", encoding="utf-8") as icons:
for icon in icons:
- key, _, svg = icon.partition(" = ")
- if key and svg:
- self._svgData[key.strip()] = svg.strip().encode("utf-8")
+ bits = icon.partition("=")
+ key = bits[0].strip()
+ value = bits[2].strip()
+ if key and value:
+ if key.startswith("icon:"):
+ self._svgData[key[5:]] = value.encode("utf-8")
return True
@@ -811,3 +814,19 @@ def _loadInternalName(confParser: NWConfigParser, confFile: str | Path) -> str:
return ""
return confParser.rdStr("Main", "name", "")
+
+
+def _loadIconName(path: Path) -> str:
+ """Open an icons file and read the 'name' setting."""
+ try:
+ with open(path, mode="r", encoding="utf-8") as icons:
+ for icon in icons:
+ key, _, value = icon.partition("=")
+ if key.strip() == "meta:name":
+ return value.strip()
+ except Exception:
+ logger.error("Could not load file: %s", path)
+ logException()
+ return ""
+
+ return ""
diff --git a/pkgutils.py b/pkgutils.py
index be32d51f..2e874153 100755
--- a/pkgutils.py
+++ b/pkgutils.py
@@ -345,18 +345,44 @@ def buildIconTheme(args: argparse.Namespace) -> None:
style = args.style
if style == "material":
- processMaterialIcons(
- workDir, iconsDir / "material_outline_normal.icons", "outlined", False, 400
- )
- processMaterialIcons(
- workDir, iconsDir / "material_filled_normal.icons", "outlined", True, 400
- )
- processMaterialIcons(
- workDir, iconsDir / "material_outline_bold.icons", "outlined", False, 700
- )
- processMaterialIcons(
- workDir, iconsDir / "material_filled_bold.icons", "outlined", True, 700
- )
+ processMaterialIcons(workDir, iconsDir, {
+ "material_outline_normal": {
+ "name": "Material Symbols - Outlined",
+ "style": "outlined",
+ "filled": False,
+ "weight": 400,
+ },
+ "material_outline_bold": {
+ "name": "Material Symbols - Outlined Bold",
+ "style": "outlined",
+ "filled": False,
+ "weight": 700,
+ },
+ "material_rounded_normal": {
+ "name": "Material Symbols - Rounded",
+ "style": "rounded",
+ "filled": False,
+ "weight": 400,
+ },
+ "material_rounded_bold": {
+ "name": "Material Symbols - Rounded Bold",
+ "style": "rounded",
+ "filled": False,
+ "weight": 700,
+ },
+ "material_filled_normal": {
+ "name": "Material Symbols - Filled",
+ "style": "rounded",
+ "filled": True,
+ "weight": 400,
+ },
+ "material_filled_bold": {
+ "name": "Material Symbols - Filled Bold",
+ "style": "rounded",
+ "filled": True,
+ "weight": 700,
+ },
+ })
print("")
diff --git a/utils/material_icons.py b/utils/material_icons.py
index 471284b6..49a62579 100644
--- a/utils/material_icons.py
+++ b/utils/material_icons.py
@@ -57,6 +57,7 @@ ICON_MAP = {
"fmt_underline": "format_underlined",
"fmt_toolbar": "text_format",
+ "search": "search",
"search_cancel": "close",
"search_case": "match_case",
"search_loop": "laps",
@@ -65,7 +66,6 @@ ICON_MAP = {
"search_regex": "regular_expression",
"search_replace": "find_replace",
"search_word": "match_word",
- "search": "search",
"bullet-off": "radio_button_unchecked",
"bullet-on": "radio_button_checked",
@@ -136,7 +136,7 @@ def _fixXml(svg: str) -> str:
return etree.tostring(xSvg).decode()
-def processMaterialIcons(workDir: Path, output: Path, style: str, fill: bool, weight: int) -> None:
+def processMaterialIcons(workDir: Path, iconsDir: Path, jobs: dict) -> None:
"""Process material icons of a given spec and write output file."""
srcRepo = workDir / "material-design-icons"
if not srcRepo.is_dir():
@@ -144,20 +144,36 @@ def processMaterialIcons(workDir: Path, output: Path, style: str, fill: bool, we
else:
subprocess.call(["git", "pull"], cwd=srcRepo)
- kind = f"wght{weight}" if weight != 400 else ""
- kind += "fill1" if fill else ""
+ for file, job in jobs.items():
+ name: str = job["name"]
+ style: str = job["style"]
+ filled: bool = job["filled"]
+ weight: int = job["weight"]
- with open(output, mode="w", encoding="utf-8") as icons:
- iconSrc = srcRepo / "symbols" / "web"
- for key, name in ICON_MAP.items():
- if kind:
- fileNmae = f"{name}_{kind}_24px.svg"
- else:
- fileNmae = f"{name}_24px.svg"
- iconFile = iconSrc / name / f"materialsymbols{style}" / fileNmae
- if iconFile.is_file():
- svg = iconFile.read_text(encoding="utf-8")
- icons.write(f"{key:<15s} = {_fixXml(svg)}\n")
- print(f"Wrote: {iconFile.stem}")
- else:
- print(f"Not Found: {iconFile}")
+ kind = f"wght{weight}" if weight != 400 else ""
+ kind += "fill1" if filled else ""
+
+ print("")
+ print(f"Processing: {name}")
+ print("")
+ with open(iconsDir / f"{file}.icons", mode="w", encoding="utf-8") as icons:
+ icons.write("# This file is automatically generated. Do not edit.\n\n")
+ icons.write("# Meta\n")
+ icons.write(f"meta:name = {name}\n")
+ icons.write("meta:author = Google\n")
+ icons.write("meta:licence = Apache License Version 2.0\n")
+ icons.write("\n")
+ icons.write("# Icons\n")
+ iconSrc = srcRepo / "symbols" / "web"
+ for key, icon in ICON_MAP.items():
+ if kind:
+ fileNmae = f"{icon}_{kind}_24px.svg"
+ else:
+ fileNmae = f"{icon}_24px.svg"
+ iconFile = iconSrc / icon / f"materialsymbols{style}" / fileNmae
+ if iconFile.is_file():
+ svg = iconFile.read_text(encoding="utf-8")
+ icons.write(f"icon:{key:<15s} = {_fixXml(svg)}\n")
+ print(f"Wrote: {iconFile.stem}")
+ else:
+ print(f"Not Found: {iconFile}")
From fa046897dc7597e53890fe8fdd09f13e94e74cc8 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Wed, 8 Jan 2025 00:21:08 +0100
Subject: [PATCH 07/18] Fix a few icons and add icon theme setting
---
novelwriter/config.py | 3 +++
novelwriter/gui/noveltree.py | 2 +-
novelwriter/gui/theme.py | 25 +++++++++++++++----------
novelwriter/tools/manuscript.py | 2 +-
4 files changed, 20 insertions(+), 12 deletions(-)
diff --git a/novelwriter/config.py b/novelwriter/config.py
index 5c7bf0a0..697dd711 100644
--- a/novelwriter/config.py
+++ b/novelwriter/config.py
@@ -114,6 +114,7 @@ class Config:
self.guiLocale = self._qLocale.name()
self.guiTheme = "default" # GUI theme
self.guiSyntax = "default_light" # Syntax theme
+ self.guiIcons = "material_rounded_normal" # Icons theme
self.guiFont = QFont() # Main GUI font
self.guiScale = 1.0 # Set automatically by Theme class
self.hideVScroll = False # Hide vertical scroll bars on main widgets
@@ -605,6 +606,7 @@ class Config:
self.setGuiFont(conf.rdStr(sec, "font", ""))
self.guiTheme = conf.rdStr(sec, "theme", self.guiTheme)
self.guiSyntax = conf.rdStr(sec, "syntax", self.guiSyntax)
+ self.guiIcons = conf.rdStr(sec, "icons", self.guiIcons)
self.guiLocale = conf.rdStr(sec, "localisation", self.guiLocale)
self.hideVScroll = conf.rdBool(sec, "hidevscroll", self.hideVScroll)
self.hideHScroll = conf.rdBool(sec, "hidehscroll", self.hideHScroll)
@@ -716,6 +718,7 @@ class Config:
"font": self.guiFont.toString(),
"theme": str(self.guiTheme),
"syntax": str(self.guiSyntax),
+ "icons": str(self.guiIcons),
"localisation": str(self.guiLocale),
"hidevscroll": str(self.hideVScroll),
"hidehscroll": str(self.hideHScroll),
diff --git a/novelwriter/gui/noveltree.py b/novelwriter/gui/noveltree.py
index d33e3d2e..96617d71 100644
--- a/novelwriter/gui/noveltree.py
+++ b/novelwriter/gui/noveltree.py
@@ -267,7 +267,7 @@ class GuiNovelToolBar(QWidget):
def updateTheme(self) -> None:
"""Update theme elements."""
# Icons
- self.tbNovel.setThemeIcon("cls_novel")
+ self.tbNovel.setThemeIcon("cls_novel", "red")
self.tbRefresh.setThemeIcon("refresh", "green")
self.tbMore.setThemeIcon("more_vertical")
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index 5dfc079b..f78dde59 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -307,7 +307,7 @@ class GuiTheme:
# Icons
defaultIcons = "typicons_light" if backLNess >= 0.5 else "typicons_dark"
self.iconCache.loadTheme(self.themeIcons or defaultIcons)
- self.iconCache.loadNewTheme("")
+ self.iconCache.loadNewTheme(CONFIG.guiIcons)
# Apply Styles
QApplication.setPalette(self._guiPalette)
@@ -627,15 +627,20 @@ class GuiIcons:
def loadNewTheme(self, iconTheme: str) -> bool:
"""Load new style theme."""
- themePath = self._iconPath / "material_rounded_normal.icons"
- with open(themePath, mode="r", encoding="utf-8") as icons:
- for icon in icons:
- bits = icon.partition("=")
- key = bits[0].strip()
- value = bits[2].strip()
- if key and value:
- if key.startswith("icon:"):
- self._svgData[key[5:]] = value.encode("utf-8")
+ themePath = self._iconPath / f"{iconTheme}.icons"
+ try:
+ with open(themePath, mode="r", encoding="utf-8") as icons:
+ for icon in icons:
+ bits = icon.partition("=")
+ key = bits[0].strip()
+ value = bits[2].strip()
+ if key and value:
+ if key.startswith("icon:"):
+ self._svgData[key[5:]] = value.encode("utf-8")
+ except Exception:
+ logger.error("Could not load icon theme settings from: %s", themePath)
+ logException()
+ return False
return True
diff --git a/novelwriter/tools/manuscript.py b/novelwriter/tools/manuscript.py
index a5952c3b..7eccec55 100644
--- a/novelwriter/tools/manuscript.py
+++ b/novelwriter/tools/manuscript.py
@@ -113,7 +113,7 @@ class GuiManuscript(NToolDialog):
self.tbAdd.setStyleSheet(buttonStyle)
self.tbAdd.clicked.connect(self._createNewBuild)
- self.tbDel = NIconToolButton(self, iSz, "remove")
+ self.tbDel = NIconToolButton(self, iSz, "remove", "red")
self.tbDel.setToolTip(self.tr("Delete Selected Build"))
self.tbDel.setStyleSheet(buttonStyle)
self.tbDel.clicked.connect(self._deleteSelectedBuild)
From 553958b952b8864e0ab67ac317a8b239b4eeb97b Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Wed, 8 Jan 2025 00:57:01 +0100
Subject: [PATCH 08/18] Fix decoration loading
---
.../assets/icons/material_filled_bold.icons | 3 +-
.../assets/icons/material_filled_normal.icons | 3 +-
.../assets/icons/material_outline_bold.icons | 3 +-
.../icons/material_outline_normal.icons | 3 +-
.../assets/icons/material_rounded_bold.icons | 3 +-
.../icons/material_rounded_normal.icons | 3 +-
novelwriter/core/status.py | 4 +-
novelwriter/extensions/pagedsidebar.py | 6 +-
novelwriter/extensions/progressbars.py | 6 +-
novelwriter/extensions/statusled.py | 4 +-
novelwriter/extensions/switch.py | 4 +-
novelwriter/gui/noveltree.py | 2 +-
novelwriter/gui/theme.py | 160 ++++++------------
novelwriter/types.py | 2 +-
utils/material_icons.py | 3 +-
15 files changed, 83 insertions(+), 126 deletions(-)
diff --git a/novelwriter/assets/icons/material_filled_bold.icons b/novelwriter/assets/icons/material_filled_bold.icons
index 9dc5a503..71152699 100644
--- a/novelwriter/assets/icons/material_filled_bold.icons
+++ b/novelwriter/assets/icons/material_filled_bold.icons
@@ -3,7 +3,7 @@
# Meta
meta:name = Material Symbols - Filled Bold
meta:author = Google
-meta:licence = Apache License Version 2.0
+meta:license = Apache License Version 2.0
# Icons
icon:alert_error =
@@ -75,6 +75,7 @@ icon:margin_right =
icon:maximise =
icon:minimise =
+icon:more_arrow =
icon:more_vertical =
icon:noncheckable =
icon:novel_view =
diff --git a/novelwriter/assets/icons/material_filled_normal.icons b/novelwriter/assets/icons/material_filled_normal.icons
index c729da16..601a2c1e 100644
--- a/novelwriter/assets/icons/material_filled_normal.icons
+++ b/novelwriter/assets/icons/material_filled_normal.icons
@@ -3,7 +3,7 @@
# Meta
meta:name = Material Symbols - Filled
meta:author = Google
-meta:licence = Apache License Version 2.0
+meta:license = Apache License Version 2.0
# Icons
icon:alert_error =
@@ -75,6 +75,7 @@ icon:margin_right =
icon:maximise =
icon:minimise =
+icon:more_arrow =
icon:more_vertical =
icon:noncheckable =
icon:novel_view =
diff --git a/novelwriter/assets/icons/material_outline_bold.icons b/novelwriter/assets/icons/material_outline_bold.icons
index a1ae5ea5..18f89bc2 100644
--- a/novelwriter/assets/icons/material_outline_bold.icons
+++ b/novelwriter/assets/icons/material_outline_bold.icons
@@ -3,7 +3,7 @@
# Meta
meta:name = Material Symbols - Outlined Bold
meta:author = Google
-meta:licence = Apache License Version 2.0
+meta:license = Apache License Version 2.0
# Icons
icon:alert_error =
@@ -75,6 +75,7 @@ icon:margin_right =
icon:maximise =
icon:minimise =
+icon:more_arrow =
icon:more_vertical =
icon:noncheckable =
icon:novel_view =
diff --git a/novelwriter/assets/icons/material_outline_normal.icons b/novelwriter/assets/icons/material_outline_normal.icons
index 14d66542..590e6ee6 100644
--- a/novelwriter/assets/icons/material_outline_normal.icons
+++ b/novelwriter/assets/icons/material_outline_normal.icons
@@ -3,7 +3,7 @@
# Meta
meta:name = Material Symbols - Outlined
meta:author = Google
-meta:licence = Apache License Version 2.0
+meta:license = Apache License Version 2.0
# Icons
icon:alert_error =
@@ -75,6 +75,7 @@ icon:margin_right =
icon:maximise =
icon:minimise =
+icon:more_arrow =
icon:more_vertical =
icon:noncheckable =
icon:novel_view =
diff --git a/novelwriter/assets/icons/material_rounded_bold.icons b/novelwriter/assets/icons/material_rounded_bold.icons
index 7d28ed46..7f1a4b3b 100644
--- a/novelwriter/assets/icons/material_rounded_bold.icons
+++ b/novelwriter/assets/icons/material_rounded_bold.icons
@@ -3,7 +3,7 @@
# Meta
meta:name = Material Symbols - Rounded Bold
meta:author = Google
-meta:licence = Apache License Version 2.0
+meta:license = Apache License Version 2.0
# Icons
icon:alert_error =
@@ -75,6 +75,7 @@ icon:margin_right =
icon:maximise =
icon:minimise =
+icon:more_arrow =
icon:more_vertical =
icon:noncheckable =
icon:novel_view =
diff --git a/novelwriter/assets/icons/material_rounded_normal.icons b/novelwriter/assets/icons/material_rounded_normal.icons
index c4022290..ff312875 100644
--- a/novelwriter/assets/icons/material_rounded_normal.icons
+++ b/novelwriter/assets/icons/material_rounded_normal.icons
@@ -3,7 +3,7 @@
# Meta
meta:name = Material Symbols - Rounded
meta:author = Google
-meta:licence = Apache License Version 2.0
+meta:license = Apache License Version 2.0
# Icons
icon:alert_error =
@@ -75,6 +75,7 @@ icon:margin_right =
icon:maximise =
icon:minimise =
+icon:more_arrow =
icon:more_vertical =
icon:noncheckable =
icon:novel_view =
diff --git a/novelwriter/core/status.py b/novelwriter/core/status.py
index 4e5a0edf..f8569532 100644
--- a/novelwriter/core/status.py
+++ b/novelwriter/core/status.py
@@ -37,7 +37,7 @@ from PyQt5.QtGui import QColor, QIcon, QPainter, QPainterPath, QPixmap, QPolygon
from novelwriter import SHARED
from novelwriter.common import simplified
from novelwriter.enum import nwStatusShape
-from novelwriter.types import QtPaintAnitAlias, QtTransparent
+from novelwriter.types import QtPaintAntiAlias, QtTransparent
if TYPE_CHECKING: # pragma: no cover
from typing import TypeGuard # Requires Python 3.10
@@ -195,7 +195,7 @@ class NWStatus:
pixmap.fill(QtTransparent)
painter = QPainter(pixmap)
- painter.setRenderHint(QtPaintAnitAlias)
+ painter.setRenderHint(QtPaintAntiAlias)
painter.fillPath(_SHAPES.getShape(shape), color)
painter.end()
diff --git a/novelwriter/extensions/pagedsidebar.py b/novelwriter/extensions/pagedsidebar.py
index 8f3063e7..319cfaaf 100644
--- a/novelwriter/extensions/pagedsidebar.py
+++ b/novelwriter/extensions/pagedsidebar.py
@@ -33,7 +33,7 @@ from PyQt5.QtWidgets import (
)
from novelwriter.types import (
- QtAlignLeft, QtMouseOver, QtNoBrush, QtNoPen, QtPaintAnitAlias,
+ QtAlignLeft, QtMouseOver, QtNoBrush, QtNoPen, QtPaintAntiAlias,
QtSizeExpanding, QtSizeFixed
)
@@ -146,7 +146,7 @@ class _PagedToolButton(QToolButton):
opt.initFrom(self)
paint = QPainter(self)
- paint.setRenderHint(QtPaintAnitAlias, True)
+ paint.setRenderHint(QtPaintAntiAlias, True)
paint.setPen(QtNoPen)
paint.setBrush(QtNoBrush)
@@ -213,7 +213,7 @@ class _NPagedToolLabel(QLabel):
label that matches the button style.
"""
paint = QPainter(self)
- paint.setRenderHint(QtPaintAnitAlias, True)
+ paint.setRenderHint(QtPaintAntiAlias, True)
paint.setPen(QtNoPen)
width = self.width()
diff --git a/novelwriter/extensions/progressbars.py b/novelwriter/extensions/progressbars.py
index b08d4808..1c7684fb 100644
--- a/novelwriter/extensions/progressbars.py
+++ b/novelwriter/extensions/progressbars.py
@@ -31,7 +31,7 @@ from PyQt5.QtGui import QBrush, QColor, QPainter, QPaintEvent, QPen
from PyQt5.QtWidgets import QProgressBar, QWidget
from novelwriter.types import (
- QtAlignCenter, QtPaintAnitAlias, QtRoundCap, QtSizeFixed, QtSolidLine,
+ QtAlignCenter, QtPaintAntiAlias, QtRoundCap, QtSizeFixed, QtSolidLine,
QtTransparent
)
@@ -91,7 +91,7 @@ class NProgressCircle(QProgressBar):
progress = 100.0*self.value()/self.maximum()
angle = ceil(16*3.6*progress)
painter = QPainter(self)
- painter.setRenderHint(QtPaintAnitAlias, True)
+ painter.setRenderHint(QtPaintAntiAlias, True)
painter.setPen(self._dPen)
painter.setBrush(self._dBrush)
painter.drawEllipse(self._dRect)
@@ -119,7 +119,7 @@ class NProgressSimple(QProgressBar):
if (value := self.value()) > 0:
progress = ceil(self.width()*float(value)/self.maximum())
painter = QPainter(self)
- painter.setRenderHint(QtPaintAnitAlias, True)
+ painter.setRenderHint(QtPaintAntiAlias, True)
painter.setPen(self.palette().highlight().color())
painter.setBrush(self.palette().highlight())
painter.drawRect(0, 0, progress, self.height())
diff --git a/novelwriter/extensions/statusled.py b/novelwriter/extensions/statusled.py
index 1aeb2065..e9a88104 100644
--- a/novelwriter/extensions/statusled.py
+++ b/novelwriter/extensions/statusled.py
@@ -30,7 +30,7 @@ from PyQt5.QtWidgets import QAbstractButton, QWidget
from novelwriter import CONFIG
from novelwriter.enum import nwTrinary
-from novelwriter.types import QtBlack, QtPaintAnitAlias
+from novelwriter.types import QtBlack, QtPaintAntiAlias
logger = logging.getLogger(__name__)
@@ -81,7 +81,7 @@ class StatusLED(QAbstractButton):
def paintEvent(self, event: QPaintEvent) -> None:
"""Draw the LED."""
painter = QPainter(self)
- painter.setRenderHint(QtPaintAnitAlias, True)
+ painter.setRenderHint(QtPaintAntiAlias, True)
painter.setPen(self.palette().windowText().color())
painter.setBrush(self._color)
painter.setOpacity(1.0)
diff --git a/novelwriter/extensions/switch.py b/novelwriter/extensions/switch.py
index 20a2b2f1..43d60fc6 100644
--- a/novelwriter/extensions/switch.py
+++ b/novelwriter/extensions/switch.py
@@ -28,7 +28,7 @@ from PyQt5.QtGui import QMouseEvent, QPainter, QPaintEvent, QResizeEvent
from PyQt5.QtWidgets import QAbstractButton, QWidget
from novelwriter import CONFIG, SHARED
-from novelwriter.types import QtMouseLeft, QtNoPen, QtPaintAnitAlias, QtSizeFixed
+from novelwriter.types import QtMouseLeft, QtNoPen, QtPaintAntiAlias, QtSizeFixed
class NSwitch(QAbstractButton):
@@ -90,7 +90,7 @@ class NSwitch(QAbstractButton):
def paintEvent(self, event: QPaintEvent) -> None:
"""Drawing the switch itself."""
painter = QPainter(self)
- painter.setRenderHint(QtPaintAnitAlias, True)
+ painter.setRenderHint(QtPaintAntiAlias, True)
painter.setPen(QtNoPen)
palette = self.palette()
diff --git a/novelwriter/gui/noveltree.py b/novelwriter/gui/noveltree.py
index 96617d71..190bcafd 100644
--- a/novelwriter/gui/noveltree.py
+++ b/novelwriter/gui/noveltree.py
@@ -452,7 +452,7 @@ class GuiNovelTree(QTreeWidget):
def updateTheme(self) -> None:
"""Update theme elements."""
iPx = SHARED.theme.baseIconHeight
- self._pMore = SHARED.theme.loadDecoration("deco_doc_more", h=iPx)
+ self._pMore = SHARED.theme.getPixmap("more_arrow", (iPx, iPx))
return
##
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index f78dde59..2ef76954 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -30,7 +30,10 @@ from math import ceil
from pathlib import Path
from PyQt5.QtCore import QSize, Qt
-from PyQt5.QtGui import QColor, QFont, QFontDatabase, QFontMetrics, QIcon, QPalette, QPixmap
+from PyQt5.QtGui import (
+ QColor, QFont, QFontDatabase, QFontMetrics, QIcon, QPainter, QPainterPath,
+ QPalette, QPixmap
+)
from PyQt5.QtWidgets import QApplication
from novelwriter import CONFIG
@@ -38,7 +41,7 @@ from novelwriter.common import NWConfigParser, cssCol, minmax
from novelwriter.constants import nwLabels
from novelwriter.enum import nwItemClass, nwItemLayout, nwItemType
from novelwriter.error import logException
-from novelwriter.types import QtTransparent
+from novelwriter.types import QtPaintAntiAlias, QtTransparent
logger = logging.getLogger(__name__)
@@ -68,7 +71,6 @@ class GuiTheme:
self.themeUrl = ""
self.themeLicense = ""
self.themeLicenseUrl = ""
- self.themeIcons = ""
self.isLightTheme = True
# GUI
@@ -244,7 +246,6 @@ class GuiTheme:
self.themeUrl = parser.rdStr(sec, "url", "")
self.themeLicense = parser.rdStr(sec, "license", "N/A")
self.themeLicenseUrl = parser.rdStr(sec, "licenseurl", "")
- self.themeIcons = parser.rdStr(sec, "icontheme", "")
# Icons
sec = "Icons"
@@ -304,12 +305,10 @@ class GuiTheme:
self.helpText.red(), self.helpText.green(), self.helpText.blue()
)
- # Icons
- defaultIcons = "typicons_light" if backLNess >= 0.5 else "typicons_dark"
- self.iconCache.loadTheme(self.themeIcons or defaultIcons)
- self.iconCache.loadNewTheme(CONFIG.guiIcons)
+ # Load icons after theme is parsed
+ self.iconCache.loadTheme(CONFIG.guiIcons)
- # Apply Styles
+ # Apply styles
QApplication.setPalette(self._guiPalette)
# Reset stylesheets so that they are regenerated
@@ -526,27 +525,20 @@ class GuiIcons:
# Storage
self._svgData: dict[str, bytes] = {}
self._svgColours: dict[str, bytes] = {}
-
self._qIcons: dict[str, QIcon] = {}
- self._themeMap: dict[str, Path] = {}
self._headerDec: list[QPixmap] = []
self._headerDecNarrow: list[QPixmap] = []
# Icon Theme Path
- self._confName = "icons.conf"
self._iconPath = CONFIG.assetPath("icons")
# None Icon
self._noIcon = QIcon(str(self._iconPath / "none.svg"))
# Icon Theme Meta
- self.themeName = ""
- self.themeDescription = ""
- self.themeAuthor = ""
- self.themeCredit = ""
- self.themeUrl = ""
- self.themeLicense = ""
- self.themeLicenseUrl = ""
+ self.themeName = ""
+ self.themeAuthor = ""
+ self.themeLicense = ""
return
@@ -559,74 +551,7 @@ class GuiIcons:
the GUI icons cannot really be replaced without writing specific
update functions for the classes where they're used.
"""
- self._themeMap = {}
- themePath = self._iconPath / iconTheme
- if not themePath.is_dir():
- themePath = CONFIG.dataPath("icons") / iconTheme
- if not themePath.is_dir():
- logger.warning("No icons loaded for '%s'", iconTheme)
- return False
-
- themeConf = themePath / self._confName
logger.info("Loading icon theme '%s'", iconTheme)
-
- # Config File
- confParser = NWConfigParser()
- try:
- with open(themeConf, mode="r", encoding="utf-8") as inFile:
- confParser.read_file(inFile)
- except Exception:
- logger.error("Could not load icon theme settings from: %s", themeConf)
- logException()
- return False
-
- # Main
- cnfSec = "Main"
- if confParser.has_section(cnfSec):
- self.themeName = confParser.rdStr(cnfSec, "name", "")
- self.themeDescription = confParser.rdStr(cnfSec, "description", "")
- self.themeAuthor = confParser.rdStr(cnfSec, "author", "N/A")
- self.themeCredit = confParser.rdStr(cnfSec, "credit", "N/A")
- self.themeUrl = confParser.rdStr(cnfSec, "url", "")
- self.themeLicense = confParser.rdStr(cnfSec, "license", "N/A")
- self.themeLicenseUrl = confParser.rdStr(cnfSec, "licenseurl", "")
-
- # Populate Icon Map
- cnfSec = "Map"
- if confParser.has_section(cnfSec):
- for iconName, iconFile in confParser.items(cnfSec):
- if iconName not in self.ICON_KEYS:
- logger.error("Unknown icon name '%s' in config file", iconName)
- else:
- iconPath = themePath / iconFile
- if iconPath.is_file():
- self._themeMap[iconName] = iconPath
- # logger.debug("Icon slot '%s' using file '%s'", iconName, iconFile)
- else:
- logger.error("Icon file '%s' not in theme folder", iconFile)
-
- # Check that icons have been defined
- logger.debug("Scanning theme icons")
- for iconKey in self.ICON_KEYS:
- if iconKey in ("novelwriter", "proj_nwx"):
- # These are not part of the theme itself
- continue
- if iconKey not in self._themeMap:
- logger.error("No icon file specified for '%s'", iconKey)
-
- # Refresh icons
- for iconKey in self._qIcons:
- logger.debug("Reloading icon: '%s'", iconKey)
- qIcon = self._loadIcon(iconKey)
- self._qIcons[iconKey] = qIcon
-
- self._headerDec = []
- self._headerDecNarrow = []
-
- return True
-
- def loadNewTheme(self, iconTheme: str) -> bool:
- """Load new style theme."""
themePath = self._iconPath / f"{iconTheme}.icons"
try:
with open(themePath, mode="r", encoding="utf-8") as icons:
@@ -637,11 +562,26 @@ class GuiIcons:
if key and value:
if key.startswith("icon:"):
self._svgData[key[5:]] = value.encode("utf-8")
+ elif key == "meta:name":
+ self.themeName = value
+ elif key == "meta:author":
+ self.themeAuthor = value
+ elif key == "meta:license":
+ self.themeLicense = value
except Exception:
logger.error("Could not load icon theme settings from: %s", themePath)
logException()
return False
+ # Refresh icons
+ for iconKey in self._qIcons:
+ logger.debug("Reloading icon: '%s'", iconKey)
+ qIcon = self._loadIcon(iconKey)
+ self._qIcons[iconKey] = qIcon
+
+ self._headerDec = []
+ self._headerDecNarrow = []
+
return True
def setIconColor(self, key: str, color: QColor) -> None:
@@ -657,9 +597,7 @@ class GuiIcons:
"""Load graphical decoration element based on the decoration
map or the icon map. This function always returns a QPixmap.
"""
- if name in self._themeMap:
- imgPath = self._themeMap[name]
- elif name in self.IMAGE_MAP:
+ if name in self.IMAGE_MAP:
idx = 0 if self.mainTheme.isLightTheme else 1
imgPath = CONFIG.assetPath("images") / self.IMAGE_MAP[name][idx]
else:
@@ -743,11 +681,11 @@ class GuiIcons:
if not self._headerDec:
iPx = self.mainTheme.baseIconHeight
self._headerDec = [
- self.loadDecoration("deco_doc_h0", h=iPx),
- self.loadDecoration("deco_doc_h1", h=iPx),
- self.loadDecoration("deco_doc_h2", h=iPx),
- self.loadDecoration("deco_doc_h3", h=iPx),
- self.loadDecoration("deco_doc_h4", h=iPx),
+ self._generateDecoration("default", iPx, 0),
+ self._generateDecoration("green", iPx, 0),
+ self._generateDecoration("red", iPx, 1),
+ self._generateDecoration("blue", iPx, 2),
+ self._generateDecoration("default", iPx, 3),
]
return self._headerDec[minmax(hLevel, 0, 4)]
@@ -756,12 +694,12 @@ class GuiIcons:
if not self._headerDecNarrow:
iPx = self.mainTheme.baseIconHeight
self._headerDecNarrow = [
- self.loadDecoration("deco_doc_h0_n", h=iPx),
- self.loadDecoration("deco_doc_h1_n", h=iPx),
- self.loadDecoration("deco_doc_h2_n", h=iPx),
- self.loadDecoration("deco_doc_h3_n", h=iPx),
- self.loadDecoration("deco_doc_h4_n", h=iPx),
- self.loadDecoration("deco_doc_nt_n", h=iPx),
+ self._generateDecoration("default", iPx, 0),
+ self._generateDecoration("green", iPx, 0),
+ self._generateDecoration("red", iPx, 0),
+ self._generateDecoration("blue", iPx, 0),
+ self._generateDecoration("default", iPx, 0),
+ self._generateDecoration("yellow", iPx, 0),
]
return self._headerDecNarrow[minmax(hLevel, 0, 5)]
@@ -787,16 +725,28 @@ class GuiIcons:
pixmap.loadFromData(svg, "svg")
return QIcon(pixmap)
- # Otherwise, we load from the theme folder
- if name in self._themeMap:
- logger.debug("Loading: %s", self._themeMap[name].name)
- return QIcon(str(self._themeMap[name]))
-
# If we didn't find one, give up and return an empty icon
logger.warning("Did not load an icon for '%s'", name)
return self._noIcon
+ def _generateDecoration(self, color: str, height: int, indent: int = 0) -> QPixmap:
+ """Generate a decoration pixmap for novel headers."""
+ pixmap = QPixmap(48*indent + 12, 48)
+ pixmap.fill(QtTransparent)
+
+ path = QPainterPath()
+ path.addRoundedRect(48.0*indent, 2.0, 12.0, 44.0, 4.0, 4.0)
+
+ painter = QPainter(pixmap)
+ painter.setRenderHint(QtPaintAntiAlias)
+ if fill := self._svgColours.get(color or "default"):
+ painter.fillPath(path, QColor(fill.decode(encoding="utf-8")))
+ painter.end()
+
+ tMode = Qt.TransformationMode.SmoothTransformation
+ return pixmap.scaledToHeight(height, tMode)
+
# Module Functions
# ================
diff --git a/novelwriter/types.py b/novelwriter/types.py
index a692a8c6..0732f5a8 100644
--- a/novelwriter/types.py
+++ b/novelwriter/types.py
@@ -66,7 +66,7 @@ QtNoBrush = Qt.BrushStyle.NoBrush
QtNoPen = Qt.PenStyle.NoPen
QtRoundCap = Qt.PenCapStyle.RoundCap
QtSolidLine = Qt.PenStyle.SolidLine
-QtPaintAnitAlias = QPainter.RenderHint.Antialiasing
+QtPaintAntiAlias = QPainter.RenderHint.Antialiasing
QtMouseOver = QStyle.StateFlag.State_MouseOver
QtSelected = QStyle.StateFlag.State_Selected
diff --git a/utils/material_icons.py b/utils/material_icons.py
index 49a62579..7758759c 100644
--- a/utils/material_icons.py
+++ b/utils/material_icons.py
@@ -104,6 +104,7 @@ ICON_MAP = {
"margin_top": "vertical_align_top",
"maximise": "fullscreen",
"minimise": "fullscreen_exit",
+ "more_arrow": "arrow_right",
"more_vertical": "more_vert",
"noncheckable": "indeterminate_check_box",
"novel_view": "book_4_spark",
@@ -161,7 +162,7 @@ def processMaterialIcons(workDir: Path, iconsDir: Path, jobs: dict) -> None:
icons.write("# Meta\n")
icons.write(f"meta:name = {name}\n")
icons.write("meta:author = Google\n")
- icons.write("meta:licence = Apache License Version 2.0\n")
+ icons.write("meta:license = Apache License Version 2.0\n")
icons.write("\n")
icons.write("# Icons\n")
iconSrc = srcRepo / "symbols" / "web"
From f4bdf3be711d0872eccd2228412e933bb4729f28 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Wed, 8 Jan 2025 01:16:31 +0100
Subject: [PATCH 09/18] Fix a few remaining issues with icon refresh
---
novelwriter/gui/theme.py | 57 ++++++++++++++++------------------------
novelwriter/guimain.py | 1 +
2 files changed, 24 insertions(+), 34 deletions(-)
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index 2ef76954..2abb4aa4 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -235,6 +235,7 @@ class GuiTheme:
# Reset Palette
self._guiPalette = QApplication.style().standardPalette()
self._resetGuiColors()
+ self.iconCache.clear()
# Main
sec = "Main"
@@ -486,33 +487,17 @@ class GuiTheme:
class GuiIcons:
"""The icon class manages the content of the assets/icons folder,
- and provides a simple interface for requesting icons. Only icons
- listed in the ICON_KEYS are handled.
+ and provides a simple interface for requesting icons.
- Icons are loaded on first request, and then cached for further
- requests. Each icon key in the ICON_KEYS set has standard icon set
- in the icon theme conf file. The existence of the file, and the
- definition of all keys are checked when the theme is loaded.
-
- When an icon is requested, the icon is loaded and cached. If it is
- missing, a blank icon is returned and a warning issued.
+ Icons are generated from SVG on first request, and then cached for
+ further requests. If the icon is not defined, a placeholder icon is
+ returned instead.
"""
- ICON_KEYS: set[str] = {
- # Project and GUI Icons
- "novelwriter", "proj_nwx"
-
- # Decorations
- "deco_doc_h0", "deco_doc_h1", "deco_doc_h2", "deco_doc_h3", "deco_doc_h4", "deco_doc_more",
- "deco_doc_h0_n", "deco_doc_h1_n", "deco_doc_h2_n", "deco_doc_h3_n", "deco_doc_h4_n",
- "deco_doc_nt_n",
- }
-
TOGGLE_ICON_KEYS: dict[str, tuple[str, str]] = {
"bullet": ("bullet-on", "bullet-off"),
"unfold": ("unfold-show", "unfold-hide"),
}
-
IMAGE_MAP: dict[str, tuple[str, str]] = {
"welcome": ("welcome-light.jpg", "welcome-dark.jpg"),
"nw-text": ("novelwriter-text-light.svg", "novelwriter-text-dark.svg"),
@@ -542,6 +527,18 @@ class GuiIcons:
return
+ def clear(self) -> None:
+ """Clear the icon cache."""
+ self._svgData = {}
+ self._svgColours = {}
+ self._qIcons = {}
+ self._headerDec = []
+ self._headerDecNarrow = []
+ self.themeName = ""
+ self.themeAuthor = ""
+ self.themeLicense = ""
+ return
+
##
# Actions
##
@@ -569,19 +566,10 @@ class GuiIcons:
elif key == "meta:license":
self.themeLicense = value
except Exception:
- logger.error("Could not load icon theme settings from: %s", themePath)
+ logger.error("Could not load icon theme from: %s", themePath)
logException()
return False
- # Refresh icons
- for iconKey in self._qIcons:
- logger.debug("Reloading icon: '%s'", iconKey)
- qIcon = self._loadIcon(iconKey)
- self._qIcons[iconKey] = qIcon
-
- self._headerDec = []
- self._headerDecNarrow = []
-
return True
def setIconColor(self, key: str, color: QColor) -> None:
@@ -631,7 +619,7 @@ class GuiIcons:
return icon
def getToggleIcon(self, name: str, size: tuple[int, int], color: str | None = None) -> QIcon:
- """Return a toggle icon from the icon buffer. or load it."""
+ """Return a toggle icon from the icon buffer, or load it."""
if name in self.TOGGLE_ICON_KEYS:
pOne = self.getPixmap(self.TOGGLE_ICON_KEYS[name][0], size, color)
pTwo = self.getPixmap(self.TOGGLE_ICON_KEYS[name][1], size, color)
@@ -648,8 +636,9 @@ class GuiIcons:
w, h = size
return self.getIcon(name, color, w, h).pixmap(w, h, QIcon.Mode.Normal)
- def getItemIcon(self, tType: nwItemType, tClass: nwItemClass,
- tLayout: nwItemLayout, hLevel: str = "H0") -> QIcon:
+ def getItemIcon(
+ self, tType: nwItemType, tClass: nwItemClass, tLayout: nwItemLayout, hLevel: str = "H0"
+ ) -> QIcon:
"""Get the correct icon for a project item based on type, class
and heading level
"""
@@ -772,7 +761,7 @@ def _loadInternalName(confParser: NWConfigParser, confFile: str | Path) -> str:
def _loadIconName(path: Path) -> str:
- """Open an icons file and read the 'name' setting."""
+ """Open an icons file and read the name setting."""
try:
with open(path, mode="r", encoding="utf-8") as icons:
for icon in icons:
diff --git a/novelwriter/guimain.py b/novelwriter/guimain.py
index eabcc185..f7aef529 100644
--- a/novelwriter/guimain.py
+++ b/novelwriter/guimain.py
@@ -1064,6 +1064,7 @@ class GuiMain(QMainWindow):
self.outlineView.updateTheme()
self.itemDetails.updateTheme()
self.mainStatus.updateTheme()
+ SHARED.project.tree.refreshAllItems()
if syntax:
SHARED.theme.loadSyntax()
From c571d701acd0d0717e4a12e194e0938c1892796a Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Wed, 8 Jan 2025 01:17:47 +0100
Subject: [PATCH 10/18] Remove old icon themes
---
.../assets/icons/typicons_dark/README.md | 29 ----
.../assets/icons/typicons_dark/icons.conf | 134 ------------------
.../assets/icons/typicons_dark/mixed_copy.svg | 4 -
.../typicons_dark/mixed_document-chapter.svg | 12 --
.../typicons_dark/mixed_document-new.svg | 6 -
.../typicons_dark/mixed_document-note.svg | 12 --
.../typicons_dark/mixed_document-scene.svg | 12 --
.../typicons_dark/mixed_document-section.svg | 12 --
.../typicons_dark/mixed_document-title.svg | 12 --
.../assets/icons/typicons_dark/mixed_edit.svg | 4 -
.../icons/typicons_dark/mixed_import.svg | 5 -
.../typicons_dark/mixed_input-checked.svg | 5 -
.../icons/typicons_dark/mixed_input-none.svg | 5 -
.../typicons_dark/mixed_input-unchecked.svg | 5 -
.../typicons_dark/mixed_margin-bottom.svg | 6 -
.../icons/typicons_dark/mixed_margin-left.svg | 6 -
.../typicons_dark/mixed_margin-right.svg | 6 -
.../icons/typicons_dark/mixed_margin-top.svg | 6 -
.../typicons_dark/mixed_search-replace.svg | 6 -
.../icons/typicons_dark/mixed_size-height.svg | 6 -
.../icons/typicons_dark/mixed_size-width.svg | 6 -
.../assets/icons/typicons_dark/nw_deco-h0.svg | 4 -
.../assets/icons/typicons_dark/nw_deco-h1.svg | 4 -
.../icons/typicons_dark/nw_deco-h2-narrow.svg | 4 -
.../assets/icons/typicons_dark/nw_deco-h2.svg | 4 -
.../icons/typicons_dark/nw_deco-h3-narrow.svg | 4 -
.../assets/icons/typicons_dark/nw_deco-h3.svg | 4 -
.../icons/typicons_dark/nw_deco-h4-narrow.svg | 4 -
.../assets/icons/typicons_dark/nw_deco-h4.svg | 4 -
.../icons/typicons_dark/nw_deco-note.svg | 4 -
.../typicons_dark/nw_deco-noveltree-more.svg | 4 -
.../assets/icons/typicons_dark/nw_font.svg | 4 -
.../assets/icons/typicons_dark/nw_panel.svg | 4 -
.../assets/icons/typicons_dark/nw_quote.svg | 4 -
.../icons/typicons_dark/nw_search-case.svg | 4 -
.../typicons_dark/nw_search-preserve.svg | 4 -
.../icons/typicons_dark/nw_search-regex.svg | 4 -
.../icons/typicons_dark/nw_search-word.svg | 4 -
.../icons/typicons_dark/nw_tb-bold-md.svg | 4 -
.../assets/icons/typicons_dark/nw_tb-bold.svg | 6 -
.../icons/typicons_dark/nw_tb-italic-md.svg | 4 -
.../icons/typicons_dark/nw_tb-italic.svg | 6 -
.../assets/icons/typicons_dark/nw_tb-mark.svg | 7 -
.../icons/typicons_dark/nw_tb-strike-md.svg | 4 -
.../icons/typicons_dark/nw_tb-strike.svg | 6 -
.../icons/typicons_dark/nw_tb-subscript.svg | 7 -
.../icons/typicons_dark/nw_tb-superscript.svg | 7 -
.../icons/typicons_dark/nw_tb-underline.svg | 7 -
.../assets/icons/typicons_dark/nw_toolbar.svg | 5 -
.../typ_arrow-down-thick-grey.svg | 4 -
.../icons/typicons_dark/typ_arrow-forward.svg | 4 -
.../typicons_dark/typ_arrow-maximise.svg | 4 -
.../typicons_dark/typ_arrow-minimise.svg | 4 -
.../typicons_dark/typ_arrow-repeat-grey.svg | 4 -
.../icons/typicons_dark/typ_book-grey.svg | 4 -
.../assets/icons/typicons_dark/typ_book.svg | 6 -
.../icons/typicons_dark/typ_bookmark.svg | 4 -
.../icons/typicons_dark/typ_calendar.svg | 4 -
.../icons/typicons_dark/typ_cancel-grey.svg | 4 -
.../assets/icons/typicons_dark/typ_cancel.svg | 4 -
.../typicons_dark/typ_chart-bar-grey.svg | 4 -
.../icons/typicons_dark/typ_chevron-down.svg | 4 -
.../icons/typicons_dark/typ_chevron-left.svg | 4 -
.../icons/typicons_dark/typ_chevron-right.svg | 4 -
.../icons/typicons_dark/typ_chevron-up.svg | 4 -
.../assets/icons/typicons_dark/typ_cog.svg | 4 -
.../icons/typicons_dark/typ_delete-full.svg | 4 -
.../assets/icons/typicons_dark/typ_delete.svg | 4 -
.../typicons_dark/typ_directions-full.svg | 4 -
.../icons/typicons_dark/typ_document-add.svg | 4 -
.../icons/typicons_dark/typ_document-text.svg | 8 --
.../icons/typicons_dark/typ_document.svg | 4 -
.../icons/typicons_dark/typ_export-grey.svg | 4 -
.../assets/icons/typicons_dark/typ_export.svg | 4 -
.../assets/icons/typicons_dark/typ_eye.svg | 4 -
.../assets/icons/typicons_dark/typ_flag.svg | 4 -
.../icons/typicons_dark/typ_folder-open.svg | 4 -
.../assets/icons/typicons_dark/typ_folder.svg | 5 -
.../icons/typicons_dark/typ_globe-grey.svg | 4 -
.../assets/icons/typicons_dark/typ_key.svg | 4 -
.../typicons_dark/typ_lightbulb-full.svg | 4 -
.../icons/typicons_dark/typ_location.svg | 4 -
.../typicons_dark/typ_media-pause-grey.svg | 4 -
.../typ_media-record-outline.svg | 4 -
.../icons/typicons_dark/typ_media-record.svg | 4 -
.../assets/icons/typicons_dark/typ_minus.svg | 4 -
.../assets/icons/typicons_dark/typ_pencil.svg | 5 -
.../icons/typicons_dark/typ_pin-outline.svg | 4 -
.../assets/icons/typicons_dark/typ_pin.svg | 4 -
.../assets/icons/typicons_dark/typ_plus.svg | 4 -
.../typicons_dark/typ_puzzle-outline.svg | 4 -
.../assets/icons/typicons_dark/typ_puzzle.svg | 4 -
.../typicons_dark/typ_refresh-flipped.svg | 4 -
.../icons/typicons_dark/typ_refresh.svg | 4 -
.../icons/typicons_dark/typ_search-grey.svg | 4 -
.../assets/icons/typicons_dark/typ_search.svg | 4 -
.../assets/icons/typicons_dark/typ_star.svg | 4 -
.../typicons_dark/typ_stopwatch-grey.svg | 4 -
.../icons/typicons_dark/typ_th-dot-menu.svg | 4 -
.../icons/typicons_dark/typ_th-dot-more.svg | 4 -
.../icons/typicons_dark/typ_th-list-grey.svg | 4 -
.../icons/typicons_dark/typ_th-list.svg | 9 --
.../assets/icons/typicons_dark/typ_times.svg | 4 -
.../assets/icons/typicons_dark/typ_trash.svg | 5 -
.../icons/typicons_dark/typ_unfold-hidden.svg | 4 -
.../typicons_dark/typ_unfold-visible.svg | 4 -
.../assets/icons/typicons_dark/typ_user.svg | 5 -
.../icons/typicons_dark/typ_warning-full.svg | 4 -
.../assets/icons/typicons_light/README.md | 29 ----
.../assets/icons/typicons_light/icons.conf | 134 ------------------
.../icons/typicons_light/mixed_copy.svg | 4 -
.../typicons_light/mixed_document-chapter.svg | 12 --
.../typicons_light/mixed_document-new.svg | 6 -
.../typicons_light/mixed_document-note.svg | 12 --
.../typicons_light/mixed_document-scene.svg | 12 --
.../typicons_light/mixed_document-section.svg | 12 --
.../typicons_light/mixed_document-title.svg | 12 --
.../icons/typicons_light/mixed_edit.svg | 4 -
.../icons/typicons_light/mixed_import.svg | 5 -
.../typicons_light/mixed_input-checked.svg | 5 -
.../icons/typicons_light/mixed_input-none.svg | 5 -
.../typicons_light/mixed_input-unchecked.svg | 5 -
.../typicons_light/mixed_margin-bottom.svg | 6 -
.../typicons_light/mixed_margin-left.svg | 6 -
.../typicons_light/mixed_margin-right.svg | 6 -
.../icons/typicons_light/mixed_margin-top.svg | 6 -
.../typicons_light/mixed_search-replace.svg | 6 -
.../typicons_light/mixed_size-height.svg | 6 -
.../icons/typicons_light/mixed_size-width.svg | 6 -
.../icons/typicons_light/nw_deco-h0.svg | 4 -
.../icons/typicons_light/nw_deco-h1.svg | 4 -
.../typicons_light/nw_deco-h2-narrow.svg | 4 -
.../icons/typicons_light/nw_deco-h2.svg | 4 -
.../typicons_light/nw_deco-h3-narrow.svg | 4 -
.../icons/typicons_light/nw_deco-h3.svg | 4 -
.../typicons_light/nw_deco-h4-narrow.svg | 4 -
.../icons/typicons_light/nw_deco-h4.svg | 4 -
.../icons/typicons_light/nw_deco-note.svg | 4 -
.../typicons_light/nw_deco-noveltree-more.svg | 4 -
.../assets/icons/typicons_light/nw_font.svg | 4 -
.../assets/icons/typicons_light/nw_panel.svg | 4 -
.../assets/icons/typicons_light/nw_quote.svg | 4 -
.../icons/typicons_light/nw_search-case.svg | 4 -
.../typicons_light/nw_search-preserve.svg | 4 -
.../icons/typicons_light/nw_search-regex.svg | 4 -
.../icons/typicons_light/nw_search-word.svg | 4 -
.../icons/typicons_light/nw_tb-bold-md.svg | 4 -
.../icons/typicons_light/nw_tb-bold.svg | 6 -
.../icons/typicons_light/nw_tb-italic-md.svg | 4 -
.../icons/typicons_light/nw_tb-italic.svg | 6 -
.../icons/typicons_light/nw_tb-mark.svg | 7 -
.../icons/typicons_light/nw_tb-strike-md.svg | 4 -
.../icons/typicons_light/nw_tb-strike.svg | 6 -
.../icons/typicons_light/nw_tb-subscript.svg | 7 -
.../typicons_light/nw_tb-superscript.svg | 7 -
.../icons/typicons_light/nw_tb-underline.svg | 7 -
.../icons/typicons_light/nw_toolbar.svg | 5 -
.../typ_arrow-down-thick-grey.svg | 4 -
.../typicons_light/typ_arrow-forward.svg | 4 -
.../typicons_light/typ_arrow-maximise.svg | 4 -
.../typicons_light/typ_arrow-minimise.svg | 4 -
.../typicons_light/typ_arrow-repeat-grey.svg | 4 -
.../icons/typicons_light/typ_book-grey.svg | 4 -
.../assets/icons/typicons_light/typ_book.svg | 6 -
.../icons/typicons_light/typ_bookmark.svg | 4 -
.../icons/typicons_light/typ_calendar.svg | 4 -
.../icons/typicons_light/typ_cancel-grey.svg | 4 -
.../icons/typicons_light/typ_cancel.svg | 4 -
.../typicons_light/typ_chart-bar-grey.svg | 4 -
.../icons/typicons_light/typ_chevron-down.svg | 4 -
.../icons/typicons_light/typ_chevron-left.svg | 4 -
.../typicons_light/typ_chevron-right.svg | 4 -
.../icons/typicons_light/typ_chevron-up.svg | 4 -
.../assets/icons/typicons_light/typ_cog.svg | 4 -
.../icons/typicons_light/typ_delete-full.svg | 4 -
.../icons/typicons_light/typ_delete.svg | 4 -
.../typicons_light/typ_directions-full.svg | 4 -
.../icons/typicons_light/typ_document-add.svg | 4 -
.../typicons_light/typ_document-text.svg | 5 -
.../icons/typicons_light/typ_document.svg | 4 -
.../icons/typicons_light/typ_export-grey.svg | 4 -
.../icons/typicons_light/typ_export.svg | 4 -
.../assets/icons/typicons_light/typ_eye.svg | 4 -
.../assets/icons/typicons_light/typ_flag.svg | 4 -
.../icons/typicons_light/typ_folder-open.svg | 4 -
.../icons/typicons_light/typ_folder.svg | 5 -
.../icons/typicons_light/typ_globe-grey.svg | 4 -
.../assets/icons/typicons_light/typ_key.svg | 4 -
.../typicons_light/typ_lightbulb-full.svg | 4 -
.../icons/typicons_light/typ_location.svg | 4 -
.../typicons_light/typ_media-pause-grey.svg | 4 -
.../typ_media-record-outline.svg | 4 -
.../icons/typicons_light/typ_media-record.svg | 4 -
.../assets/icons/typicons_light/typ_minus.svg | 4 -
.../icons/typicons_light/typ_pencil.svg | 5 -
.../icons/typicons_light/typ_pin-outline.svg | 4 -
.../assets/icons/typicons_light/typ_pin.svg | 4 -
.../assets/icons/typicons_light/typ_plus.svg | 4 -
.../typicons_light/typ_puzzle-outline.svg | 4 -
.../icons/typicons_light/typ_puzzle.svg | 4 -
.../typicons_light/typ_refresh-flipped.svg | 4 -
.../icons/typicons_light/typ_refresh.svg | 4 -
.../icons/typicons_light/typ_search-grey.svg | 4 -
.../icons/typicons_light/typ_search.svg | 4 -
.../assets/icons/typicons_light/typ_star.svg | 4 -
.../typicons_light/typ_stopwatch-grey.svg | 4 -
.../icons/typicons_light/typ_th-dot-menu.svg | 4 -
.../icons/typicons_light/typ_th-dot-more.svg | 4 -
.../icons/typicons_light/typ_th-list-grey.svg | 4 -
.../icons/typicons_light/typ_th-list.svg | 9 --
.../assets/icons/typicons_light/typ_times.svg | 4 -
.../assets/icons/typicons_light/typ_trash.svg | 5 -
.../typicons_light/typ_unfold-hidden.svg | 4 -
.../typicons_light/typ_unfold-visible.svg | 4 -
.../assets/icons/typicons_light/typ_user.svg | 5 -
.../icons/typicons_light/typ_warning-full.svg | 4 -
.../assets/themes/cyberpunk_night.conf | 1 -
novelwriter/assets/themes/default_dark.conf | 1 -
novelwriter/assets/themes/default_light.conf | 1 -
novelwriter/assets/themes/dracula.conf | 1 -
novelwriter/assets/themes/solarized_dark.conf | 1 -
.../assets/themes/solarized_light.conf | 1 -
sample/nwProject.nwx | 6 +-
223 files changed, 3 insertions(+), 1368 deletions(-)
delete mode 100644 novelwriter/assets/icons/typicons_dark/README.md
delete mode 100644 novelwriter/assets/icons/typicons_dark/icons.conf
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_copy.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_document-chapter.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_document-new.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_document-note.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_document-scene.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_document-section.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_document-title.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_edit.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_import.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_input-checked.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_input-none.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_input-unchecked.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_margin-bottom.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_margin-left.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_margin-right.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_margin-top.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_search-replace.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_size-height.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/mixed_size-width.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-h0.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-h1.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-h2-narrow.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-h2.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-h3-narrow.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-h3.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-h4-narrow.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-h4.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-note.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_deco-noveltree-more.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_font.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_panel.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_quote.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_search-case.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_search-preserve.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_search-regex.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_search-word.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-bold-md.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-bold.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-italic-md.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-italic.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-mark.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-strike-md.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-strike.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-subscript.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-superscript.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_tb-underline.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/nw_toolbar.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_arrow-down-thick-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_arrow-forward.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_arrow-maximise.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_arrow-minimise.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_arrow-repeat-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_book-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_book.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_bookmark.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_calendar.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_cancel-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_cancel.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_chart-bar-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_chevron-down.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_chevron-left.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_chevron-right.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_chevron-up.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_cog.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_delete-full.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_delete.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_directions-full.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_document-add.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_document-text.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_document.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_export-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_export.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_eye.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_flag.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_folder-open.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_folder.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_globe-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_key.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_lightbulb-full.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_location.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_media-pause-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_media-record-outline.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_media-record.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_minus.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_pencil.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_pin-outline.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_pin.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_plus.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_puzzle-outline.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_puzzle.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_refresh-flipped.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_refresh.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_search-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_search.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_star.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_stopwatch-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_th-dot-menu.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_th-dot-more.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_th-list-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_th-list.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_times.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_trash.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_unfold-hidden.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_unfold-visible.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_user.svg
delete mode 100644 novelwriter/assets/icons/typicons_dark/typ_warning-full.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/README.md
delete mode 100644 novelwriter/assets/icons/typicons_light/icons.conf
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_copy.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_document-chapter.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_document-new.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_document-note.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_document-scene.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_document-section.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_document-title.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_edit.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_import.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_input-checked.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_input-none.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_input-unchecked.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_margin-bottom.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_margin-left.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_margin-right.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_margin-top.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_search-replace.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_size-height.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/mixed_size-width.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-h0.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-h1.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-h2-narrow.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-h2.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-h3-narrow.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-h3.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-h4-narrow.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-h4.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-note.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_deco-noveltree-more.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_font.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_panel.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_quote.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_search-case.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_search-preserve.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_search-regex.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_search-word.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-bold-md.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-bold.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-italic-md.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-italic.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-mark.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-strike-md.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-strike.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-subscript.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-superscript.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_tb-underline.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/nw_toolbar.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_arrow-down-thick-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_arrow-forward.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_arrow-maximise.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_arrow-minimise.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_arrow-repeat-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_book-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_book.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_bookmark.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_calendar.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_cancel-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_cancel.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_chart-bar-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_chevron-down.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_chevron-left.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_chevron-right.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_chevron-up.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_cog.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_delete-full.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_delete.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_directions-full.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_document-add.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_document-text.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_document.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_export-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_export.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_eye.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_flag.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_folder-open.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_folder.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_globe-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_key.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_lightbulb-full.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_location.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_media-pause-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_media-record-outline.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_media-record.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_minus.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_pencil.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_pin-outline.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_pin.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_plus.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_puzzle-outline.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_puzzle.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_refresh-flipped.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_refresh.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_search-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_search.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_star.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_stopwatch-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_th-dot-menu.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_th-dot-more.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_th-list-grey.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_th-list.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_times.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_trash.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_unfold-hidden.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_unfold-visible.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_user.svg
delete mode 100644 novelwriter/assets/icons/typicons_light/typ_warning-full.svg
diff --git a/novelwriter/assets/icons/typicons_dark/README.md b/novelwriter/assets/icons/typicons_dark/README.md
deleted file mode 100644
index 48c3f4ef..00000000
--- a/novelwriter/assets/icons/typicons_dark/README.md
+++ /dev/null
@@ -1,29 +0,0 @@
-# Typicons for Dark Backgrounds
-
-This theme is based on Typicons. All files are prefixed, depending on whether they are based
-directly on original Typicons, redesigned, or designed from scratch.
-
-## Typicons Icons
-
-The files have a `typ_` prefix. These are colourised and rescaled Typicons, but with no other
-modifications.
-
-Copyright: Stephen Hutchings
-Source: https://github.com/stephenhutchings/typicons.font
-License: [CC BY-SA 4.0](https://creativecommons.org/licenses/by-sa/4.0/)
-
-## Original Icons
-
-The files have a `nw_` prefix. These are made completely from scratch for novelWriter and are not
-using any design elements from Typicons.
-
-Copyright: Veronica Berglyd Olsen
-License: [CC BY-SA 4.0](https://creativecommons.org/licenses/by-sa/4.0/)
-
-## Mixed Icons
-
-The files have a `mixed_` prefix. These are redesigned from Typicons components, modified from
-Typicons, or consist of a mix of Typicons and new elements.
-
-Copyright: Stephen Hutchings, Veronica Berglyd Olsen
-License: [CC BY-SA 4.0](https://creativecommons.org/licenses/by-sa/4.0/)
diff --git a/novelwriter/assets/icons/typicons_dark/icons.conf b/novelwriter/assets/icons/typicons_dark/icons.conf
deleted file mode 100644
index 22adb00a..00000000
--- a/novelwriter/assets/icons/typicons_dark/icons.conf
+++ /dev/null
@@ -1,134 +0,0 @@
-##
-# Icons: Typicons Dark
-# Source: https://github.com/stephenhutchings/typicons.font
-# Credit: Stephen Hutchings
-# Modified: Veronica Berglyd Olsen
-# Additions: hash.svg
-##
-
-[Main]
-name = Typicons Dark
-description = Colourised icons for dark GUI theme based on Typicons.
-author = Veronica Berglyd Olsen (adaptation)
-credit = Stephen Hutchings (icon design)
-url = https://github.com/stephenhutchings/typicons.font
-license = CC BY-SA 4.0
-licenseurl = https://creativecommons.org/licenses/by-sa/4.0/
-
-[Map]
-add = typ_plus.svg
-add_document = typ_document-add.svg
-alert_error = typ_delete-full.svg
-alert_info = typ_lightbulb-full.svg
-alert_question = typ_directions-full.svg
-alert_warn = typ_warning-full.svg
-backward = typ_chevron-left.svg
-bookmark = typ_bookmark.svg
-browse = typ_folder-open.svg
-build_excluded = typ_cancel.svg
-build_filtered = typ_arrow-forward.svg
-build_included = typ_pin.svg
-bullet-off = typ_media-record-outline.svg
-bullet-on = typ_media-record.svg
-checked = mixed_input-checked.svg
-close = typ_times.svg
-cls_archive = typ_delete.svg
-cls_character = typ_user.svg
-cls_custom = typ_star.svg
-cls_entity = typ_flag.svg
-cls_none = typ_cancel.svg
-cls_novel = typ_book.svg
-cls_object = typ_key.svg
-cls_plot = typ_puzzle.svg
-cls_template = mixed_document-new.svg
-cls_timeline = typ_calendar.svg
-cls_trash = typ_trash.svg
-cls_world = typ_location.svg
-copy = mixed_copy.svg
-cross = typ_times.svg
-document = typ_document.svg
-down = typ_chevron-down.svg
-edit = typ_pencil.svg
-export = typ_export.svg
-fmt_bold = nw_tb-bold.svg
-fmt_bold-md = nw_tb-bold-md.svg
-fmt_italic = nw_tb-italic.svg
-fmt_italic-md = nw_tb-italic-md.svg
-fmt_mark = nw_tb-mark.svg
-fmt_strike = nw_tb-strike.svg
-fmt_strike-md = nw_tb-strike-md.svg
-fmt_subscript = nw_tb-subscript.svg
-fmt_superscript = nw_tb-superscript.svg
-fmt_underline = nw_tb-underline.svg
-font = nw_font.svg
-forward = typ_chevron-right.svg
-import = mixed_import.svg
-list = typ_th-list.svg
-margin_bottom = mixed_margin-bottom.svg
-margin_left = mixed_margin-left.svg
-margin_right = mixed_margin-right.svg
-margin_top = mixed_margin-top.svg
-maximise = typ_arrow-maximise.svg
-menu = typ_th-dot-menu.svg
-minimise = typ_arrow-minimise.svg
-more = typ_th-dot-more.svg
-noncheckable = mixed_input-none.svg
-open = typ_folder.svg
-panel = nw_panel.svg
-proj_chapter = mixed_document-chapter.svg
-proj_details = typ_th-list-grey.svg
-proj_document = typ_document-text.svg
-proj_folder = typ_folder.svg
-proj_note = mixed_document-note.svg
-proj_scene = mixed_document-scene.svg
-proj_section = mixed_document-section.svg
-proj_stats = typ_chart-bar-grey.svg
-proj_title = mixed_document-title.svg
-quote = nw_quote.svg
-refresh = typ_refresh.svg
-remove = typ_minus.svg
-revert = typ_refresh-flipped.svg
-search = typ_search.svg
-search_cancel = typ_cancel-grey.svg
-search_case = nw_search-case.svg
-search_loop = typ_arrow-repeat-grey.svg
-search_preserve = nw_search-preserve.svg
-search_project = typ_arrow-down-thick-grey.svg
-search_regex = nw_search-regex.svg
-search_replace = mixed_search-replace.svg
-search_word = nw_search-word.svg
-settings = typ_cog.svg
-size_height = mixed_size-height.svg
-size_width = mixed_size-width.svg
-star = typ_star.svg
-status_idle = typ_media-pause-grey.svg
-status_lang = typ_globe-grey.svg
-status_lines = typ_th-list-grey.svg
-status_stats = typ_chart-bar-grey.svg
-status_time = typ_stopwatch-grey.svg
-sticky-off = typ_pin-outline.svg
-sticky-on = typ_pin.svg
-toolbar = nw_toolbar.svg
-unchecked = mixed_input-unchecked.svg
-unfold-hide = typ_unfold-hidden.svg
-unfold-show = typ_unfold-visible.svg
-up = typ_chevron-up.svg
-view = typ_eye.svg
-view_build = typ_export-grey.svg
-view_editor = mixed_edit.svg
-view_novel = typ_book-grey.svg
-view_outline = typ_puzzle-outline.svg
-view_search = typ_search-grey.svg
-
-deco_doc_h0 = nw_deco-h0.svg
-deco_doc_h0_n = nw_deco-h0.svg
-deco_doc_h1 = nw_deco-h1.svg
-deco_doc_h1_n = nw_deco-h1.svg
-deco_doc_h2 = nw_deco-h2.svg
-deco_doc_h2_n = nw_deco-h2-narrow.svg
-deco_doc_h3 = nw_deco-h3.svg
-deco_doc_h3_n = nw_deco-h3-narrow.svg
-deco_doc_h4 = nw_deco-h4.svg
-deco_doc_h4_n = nw_deco-h4-narrow.svg
-deco_doc_more = nw_deco-noveltree-more.svg
-deco_doc_nt_n = nw_deco-note.svg
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_copy.svg b/novelwriter/assets/icons/typicons_dark/mixed_copy.svg
deleted file mode 100644
index ff43bce5..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_copy.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_document-chapter.svg b/novelwriter/assets/icons/typicons_dark/mixed_document-chapter.svg
deleted file mode 100644
index ab586a75..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_document-chapter.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_document-new.svg b/novelwriter/assets/icons/typicons_dark/mixed_document-new.svg
deleted file mode 100644
index 6752917f..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_document-new.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_document-note.svg b/novelwriter/assets/icons/typicons_dark/mixed_document-note.svg
deleted file mode 100644
index 7778aefc..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_document-note.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_document-scene.svg b/novelwriter/assets/icons/typicons_dark/mixed_document-scene.svg
deleted file mode 100644
index 89878f30..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_document-scene.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_document-section.svg b/novelwriter/assets/icons/typicons_dark/mixed_document-section.svg
deleted file mode 100644
index 111b074f..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_document-section.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_document-title.svg b/novelwriter/assets/icons/typicons_dark/mixed_document-title.svg
deleted file mode 100644
index 07fae46a..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_document-title.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_edit.svg b/novelwriter/assets/icons/typicons_dark/mixed_edit.svg
deleted file mode 100644
index 910a1582..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_edit.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_import.svg b/novelwriter/assets/icons/typicons_dark/mixed_import.svg
deleted file mode 100644
index 262e2e5a..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_import.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_input-checked.svg b/novelwriter/assets/icons/typicons_dark/mixed_input-checked.svg
deleted file mode 100644
index 24307843..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_input-checked.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_input-none.svg b/novelwriter/assets/icons/typicons_dark/mixed_input-none.svg
deleted file mode 100644
index e0b0f08f..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_input-none.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_input-unchecked.svg b/novelwriter/assets/icons/typicons_dark/mixed_input-unchecked.svg
deleted file mode 100644
index 91a45b7a..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_input-unchecked.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_margin-bottom.svg b/novelwriter/assets/icons/typicons_dark/mixed_margin-bottom.svg
deleted file mode 100644
index 986b19e2..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_margin-bottom.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_margin-left.svg b/novelwriter/assets/icons/typicons_dark/mixed_margin-left.svg
deleted file mode 100644
index 84358b19..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_margin-left.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_margin-right.svg b/novelwriter/assets/icons/typicons_dark/mixed_margin-right.svg
deleted file mode 100644
index a828f7c2..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_margin-right.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_margin-top.svg b/novelwriter/assets/icons/typicons_dark/mixed_margin-top.svg
deleted file mode 100644
index a7e3933c..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_margin-top.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_search-replace.svg b/novelwriter/assets/icons/typicons_dark/mixed_search-replace.svg
deleted file mode 100644
index 817adfca..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_search-replace.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_size-height.svg b/novelwriter/assets/icons/typicons_dark/mixed_size-height.svg
deleted file mode 100644
index 0c05bcff..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_size-height.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/mixed_size-width.svg b/novelwriter/assets/icons/typicons_dark/mixed_size-width.svg
deleted file mode 100644
index 6c8c7622..00000000
--- a/novelwriter/assets/icons/typicons_dark/mixed_size-width.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-h0.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-h0.svg
deleted file mode 100644
index 9b9cf15e..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-h0.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-h1.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-h1.svg
deleted file mode 100644
index 2b5398d0..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-h1.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-h2-narrow.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-h2-narrow.svg
deleted file mode 100644
index ced9f866..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-h2-narrow.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-h2.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-h2.svg
deleted file mode 100644
index 7b71c946..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-h2.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-h3-narrow.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-h3-narrow.svg
deleted file mode 100644
index e5a9fad9..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-h3-narrow.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-h3.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-h3.svg
deleted file mode 100644
index a65690d2..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-h3.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-h4-narrow.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-h4-narrow.svg
deleted file mode 100644
index 3394646e..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-h4-narrow.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-h4.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-h4.svg
deleted file mode 100644
index d32578ed..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-h4.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-note.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-note.svg
deleted file mode 100644
index 85944eb6..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-note.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_deco-noveltree-more.svg b/novelwriter/assets/icons/typicons_dark/nw_deco-noveltree-more.svg
deleted file mode 100644
index 845b6883..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_deco-noveltree-more.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_font.svg b/novelwriter/assets/icons/typicons_dark/nw_font.svg
deleted file mode 100644
index 588dd615..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_font.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_panel.svg b/novelwriter/assets/icons/typicons_dark/nw_panel.svg
deleted file mode 100644
index 2863918f..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_panel.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_quote.svg b/novelwriter/assets/icons/typicons_dark/nw_quote.svg
deleted file mode 100644
index db50fcb4..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_quote.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_search-case.svg b/novelwriter/assets/icons/typicons_dark/nw_search-case.svg
deleted file mode 100644
index 903d2182..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_search-case.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_search-preserve.svg b/novelwriter/assets/icons/typicons_dark/nw_search-preserve.svg
deleted file mode 100644
index 35fb425e..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_search-preserve.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_search-regex.svg b/novelwriter/assets/icons/typicons_dark/nw_search-regex.svg
deleted file mode 100644
index 95e8a29e..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_search-regex.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_search-word.svg b/novelwriter/assets/icons/typicons_dark/nw_search-word.svg
deleted file mode 100644
index e59c7704..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_search-word.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-bold-md.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-bold-md.svg
deleted file mode 100644
index e59edb08..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-bold-md.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-bold.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-bold.svg
deleted file mode 100644
index 92e3df02..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-bold.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-italic-md.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-italic-md.svg
deleted file mode 100644
index 0ec5fb2a..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-italic-md.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-italic.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-italic.svg
deleted file mode 100644
index 4ef620d2..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-italic.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-mark.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-mark.svg
deleted file mode 100644
index 5539581a..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-mark.svg
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-strike-md.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-strike-md.svg
deleted file mode 100644
index 2858b4d1..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-strike-md.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-strike.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-strike.svg
deleted file mode 100644
index 5c87b666..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-strike.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-subscript.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-subscript.svg
deleted file mode 100644
index 7fcd5715..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-subscript.svg
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-superscript.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-superscript.svg
deleted file mode 100644
index d867fb36..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-superscript.svg
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_tb-underline.svg b/novelwriter/assets/icons/typicons_dark/nw_tb-underline.svg
deleted file mode 100644
index 65190358..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_tb-underline.svg
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/nw_toolbar.svg b/novelwriter/assets/icons/typicons_dark/nw_toolbar.svg
deleted file mode 100644
index ea6e9ab9..00000000
--- a/novelwriter/assets/icons/typicons_dark/nw_toolbar.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_arrow-down-thick-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_arrow-down-thick-grey.svg
deleted file mode 100644
index 57c65d93..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_arrow-down-thick-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_arrow-forward.svg b/novelwriter/assets/icons/typicons_dark/typ_arrow-forward.svg
deleted file mode 100644
index e235e9c2..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_arrow-forward.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_arrow-maximise.svg b/novelwriter/assets/icons/typicons_dark/typ_arrow-maximise.svg
deleted file mode 100644
index 47f05387..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_arrow-maximise.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_arrow-minimise.svg b/novelwriter/assets/icons/typicons_dark/typ_arrow-minimise.svg
deleted file mode 100644
index b965395d..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_arrow-minimise.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_arrow-repeat-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_arrow-repeat-grey.svg
deleted file mode 100644
index e6675e02..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_arrow-repeat-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_book-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_book-grey.svg
deleted file mode 100644
index 1100eb3a..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_book-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_book.svg b/novelwriter/assets/icons/typicons_dark/typ_book.svg
deleted file mode 100644
index f3ebfa6b..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_book.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_bookmark.svg b/novelwriter/assets/icons/typicons_dark/typ_bookmark.svg
deleted file mode 100644
index 172fdf92..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_bookmark.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_calendar.svg b/novelwriter/assets/icons/typicons_dark/typ_calendar.svg
deleted file mode 100644
index 999f2bf2..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_calendar.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_cancel-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_cancel-grey.svg
deleted file mode 100644
index cda5d15c..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_cancel-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_cancel.svg b/novelwriter/assets/icons/typicons_dark/typ_cancel.svg
deleted file mode 100644
index 718d0ef5..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_cancel.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_chart-bar-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_chart-bar-grey.svg
deleted file mode 100644
index 956830bc..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_chart-bar-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_chevron-down.svg b/novelwriter/assets/icons/typicons_dark/typ_chevron-down.svg
deleted file mode 100644
index 4d08c906..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_chevron-down.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_chevron-left.svg b/novelwriter/assets/icons/typicons_dark/typ_chevron-left.svg
deleted file mode 100644
index bc8ea192..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_chevron-left.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_chevron-right.svg b/novelwriter/assets/icons/typicons_dark/typ_chevron-right.svg
deleted file mode 100644
index c96f63bb..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_chevron-right.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_chevron-up.svg b/novelwriter/assets/icons/typicons_dark/typ_chevron-up.svg
deleted file mode 100644
index 765dd6de..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_chevron-up.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_cog.svg b/novelwriter/assets/icons/typicons_dark/typ_cog.svg
deleted file mode 100644
index d8b8fcc9..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_cog.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_delete-full.svg b/novelwriter/assets/icons/typicons_dark/typ_delete-full.svg
deleted file mode 100644
index 2dbe7364..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_delete-full.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_delete.svg b/novelwriter/assets/icons/typicons_dark/typ_delete.svg
deleted file mode 100644
index bcd9dcc9..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_delete.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_directions-full.svg b/novelwriter/assets/icons/typicons_dark/typ_directions-full.svg
deleted file mode 100644
index 0075285d..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_directions-full.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_document-add.svg b/novelwriter/assets/icons/typicons_dark/typ_document-add.svg
deleted file mode 100644
index 68f6b53d..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_document-add.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_document-text.svg b/novelwriter/assets/icons/typicons_dark/typ_document-text.svg
deleted file mode 100644
index 016a8202..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_document-text.svg
+++ /dev/null
@@ -1,8 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_document.svg b/novelwriter/assets/icons/typicons_dark/typ_document.svg
deleted file mode 100644
index 20121f32..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_document.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_export-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_export-grey.svg
deleted file mode 100644
index aa6de8d4..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_export-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_export.svg b/novelwriter/assets/icons/typicons_dark/typ_export.svg
deleted file mode 100644
index 06452fcb..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_export.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_eye.svg b/novelwriter/assets/icons/typicons_dark/typ_eye.svg
deleted file mode 100644
index 34d22862..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_eye.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_flag.svg b/novelwriter/assets/icons/typicons_dark/typ_flag.svg
deleted file mode 100644
index 3899d75a..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_flag.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_folder-open.svg b/novelwriter/assets/icons/typicons_dark/typ_folder-open.svg
deleted file mode 100644
index 072bff87..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_folder-open.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_folder.svg b/novelwriter/assets/icons/typicons_dark/typ_folder.svg
deleted file mode 100644
index 097534be..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_folder.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_globe-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_globe-grey.svg
deleted file mode 100644
index 46adc157..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_globe-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_key.svg b/novelwriter/assets/icons/typicons_dark/typ_key.svg
deleted file mode 100644
index 1b8de73f..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_key.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_lightbulb-full.svg b/novelwriter/assets/icons/typicons_dark/typ_lightbulb-full.svg
deleted file mode 100644
index 569fc5e2..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_lightbulb-full.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_location.svg b/novelwriter/assets/icons/typicons_dark/typ_location.svg
deleted file mode 100644
index bf461226..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_location.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_media-pause-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_media-pause-grey.svg
deleted file mode 100644
index 37362722..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_media-pause-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_media-record-outline.svg b/novelwriter/assets/icons/typicons_dark/typ_media-record-outline.svg
deleted file mode 100644
index 20cbf14b..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_media-record-outline.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_media-record.svg b/novelwriter/assets/icons/typicons_dark/typ_media-record.svg
deleted file mode 100644
index b3b3c510..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_media-record.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_minus.svg b/novelwriter/assets/icons/typicons_dark/typ_minus.svg
deleted file mode 100644
index 2bba31a3..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_minus.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_pencil.svg b/novelwriter/assets/icons/typicons_dark/typ_pencil.svg
deleted file mode 100644
index a0b0bf09..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_pencil.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_pin-outline.svg b/novelwriter/assets/icons/typicons_dark/typ_pin-outline.svg
deleted file mode 100644
index 51a04860..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_pin-outline.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_pin.svg b/novelwriter/assets/icons/typicons_dark/typ_pin.svg
deleted file mode 100644
index 0ee523f8..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_pin.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_plus.svg b/novelwriter/assets/icons/typicons_dark/typ_plus.svg
deleted file mode 100644
index c19c2fc5..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_plus.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_puzzle-outline.svg b/novelwriter/assets/icons/typicons_dark/typ_puzzle-outline.svg
deleted file mode 100644
index dcb2180e..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_puzzle-outline.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_puzzle.svg b/novelwriter/assets/icons/typicons_dark/typ_puzzle.svg
deleted file mode 100644
index f4f215bd..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_puzzle.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_refresh-flipped.svg b/novelwriter/assets/icons/typicons_dark/typ_refresh-flipped.svg
deleted file mode 100644
index 09b422a8..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_refresh-flipped.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_refresh.svg b/novelwriter/assets/icons/typicons_dark/typ_refresh.svg
deleted file mode 100644
index 6a2c5548..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_refresh.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_search-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_search-grey.svg
deleted file mode 100644
index 5a8a7330..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_search-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_search.svg b/novelwriter/assets/icons/typicons_dark/typ_search.svg
deleted file mode 100644
index 81453af0..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_search.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_star.svg b/novelwriter/assets/icons/typicons_dark/typ_star.svg
deleted file mode 100644
index 2d1e2428..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_star.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_stopwatch-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_stopwatch-grey.svg
deleted file mode 100644
index 719defae..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_stopwatch-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_th-dot-menu.svg b/novelwriter/assets/icons/typicons_dark/typ_th-dot-menu.svg
deleted file mode 100644
index 19ec3bde..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_th-dot-menu.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_th-dot-more.svg b/novelwriter/assets/icons/typicons_dark/typ_th-dot-more.svg
deleted file mode 100644
index 782996dc..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_th-dot-more.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_th-list-grey.svg b/novelwriter/assets/icons/typicons_dark/typ_th-list-grey.svg
deleted file mode 100644
index 8d98a411..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_th-list-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_th-list.svg b/novelwriter/assets/icons/typicons_dark/typ_th-list.svg
deleted file mode 100644
index 85a79c58..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_th-list.svg
+++ /dev/null
@@ -1,9 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_times.svg b/novelwriter/assets/icons/typicons_dark/typ_times.svg
deleted file mode 100644
index 4d086668..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_times.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_trash.svg b/novelwriter/assets/icons/typicons_dark/typ_trash.svg
deleted file mode 100644
index 6521acff..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_trash.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_unfold-hidden.svg b/novelwriter/assets/icons/typicons_dark/typ_unfold-hidden.svg
deleted file mode 100644
index a44038ee..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_unfold-hidden.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_unfold-visible.svg b/novelwriter/assets/icons/typicons_dark/typ_unfold-visible.svg
deleted file mode 100644
index 9062561c..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_unfold-visible.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_user.svg b/novelwriter/assets/icons/typicons_dark/typ_user.svg
deleted file mode 100644
index f8e8f0e6..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_user.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_dark/typ_warning-full.svg b/novelwriter/assets/icons/typicons_dark/typ_warning-full.svg
deleted file mode 100644
index cdb68b1e..00000000
--- a/novelwriter/assets/icons/typicons_dark/typ_warning-full.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/README.md b/novelwriter/assets/icons/typicons_light/README.md
deleted file mode 100644
index eb6f78a5..00000000
--- a/novelwriter/assets/icons/typicons_light/README.md
+++ /dev/null
@@ -1,29 +0,0 @@
-# Typicons for Light Backgrounds
-
-This theme is based on Typicons. All files are prefixed, depending on whether they are based
-directly on original Typicons, redesigned, or designed from scratch.
-
-## Typicons Icons
-
-The files have a `typ_` prefix. These are colourised and rescaled Typicons, but with no other
-modifications.
-
-Copyright: Stephen Hutchings
-Source: https://github.com/stephenhutchings/typicons.font
-License: [CC BY-SA 4.0](https://creativecommons.org/licenses/by-sa/4.0/)
-
-## Original Icons
-
-The files have a `nw_` prefix. These are made completely from scratch for novelWriter and are not
-using any design elements from Typicons.
-
-Copyright: Veronica Berglyd Olsen
-License: [CC BY-SA 4.0](https://creativecommons.org/licenses/by-sa/4.0/)
-
-## Mixed Icons
-
-The files have a `mixed_` prefix. These are redesigned from Typicons components, modified from
-Typicons, or consist of a mix of Typicons and new elements.
-
-Copyright: Stephen Hutchings, Veronica Berglyd Olsen
-License: [CC BY-SA 4.0](https://creativecommons.org/licenses/by-sa/4.0/)
diff --git a/novelwriter/assets/icons/typicons_light/icons.conf b/novelwriter/assets/icons/typicons_light/icons.conf
deleted file mode 100644
index 90e88b88..00000000
--- a/novelwriter/assets/icons/typicons_light/icons.conf
+++ /dev/null
@@ -1,134 +0,0 @@
-##
-# Icons: Typicons Light
-# Source: https://github.com/stephenhutchings/typicons.font
-# Credit: Stephen Hutchings
-# Modified: Veronica Berglyd Olsen
-# Additions: hash.svg
-##
-
-[Main]
-name = Typicons Light
-description = Colourised icons for light GUI theme based on Typicons.
-author = Veronica Berglyd Olsen (adaptation)
-credit = Stephen Hutchings (icon design)
-url = https://github.com/stephenhutchings/typicons.font
-license = CC BY-SA 4.0
-licenseurl = https://creativecommons.org/licenses/by-sa/4.0/
-
-[Map]
-add = typ_plus.svg
-add_document = typ_document-add.svg
-alert_error = typ_delete-full.svg
-alert_info = typ_lightbulb-full.svg
-alert_question = typ_directions-full.svg
-alert_warn = typ_warning-full.svg
-backward = typ_chevron-left.svg
-bookmark = typ_bookmark.svg
-browse = typ_folder-open.svg
-build_excluded = typ_cancel.svg
-build_filtered = typ_arrow-forward.svg
-build_included = typ_pin.svg
-bullet-off = typ_media-record-outline.svg
-bullet-on = typ_media-record.svg
-checked = mixed_input-checked.svg
-close = typ_times.svg
-cls_archive = typ_delete.svg
-cls_character = typ_user.svg
-cls_custom = typ_star.svg
-cls_entity = typ_flag.svg
-cls_none = typ_cancel.svg
-cls_novel = typ_book.svg
-cls_object = typ_key.svg
-cls_plot = typ_puzzle.svg
-cls_template = mixed_document-new.svg
-cls_timeline = typ_calendar.svg
-cls_trash = typ_trash.svg
-cls_world = typ_location.svg
-copy = mixed_copy.svg
-cross = typ_times.svg
-document = typ_document.svg
-down = typ_chevron-down.svg
-edit = typ_pencil.svg
-export = typ_export.svg
-fmt_bold = nw_tb-bold.svg
-fmt_bold-md = nw_tb-bold-md.svg
-fmt_italic = nw_tb-italic.svg
-fmt_italic-md = nw_tb-italic-md.svg
-fmt_mark = nw_tb-mark.svg
-fmt_strike = nw_tb-strike.svg
-fmt_strike-md = nw_tb-strike-md.svg
-fmt_subscript = nw_tb-subscript.svg
-fmt_superscript = nw_tb-superscript.svg
-fmt_underline = nw_tb-underline.svg
-font = nw_font.svg
-forward = typ_chevron-right.svg
-import = mixed_import.svg
-list = typ_th-list.svg
-margin_bottom = mixed_margin-bottom.svg
-margin_left = mixed_margin-left.svg
-margin_right = mixed_margin-right.svg
-margin_top = mixed_margin-top.svg
-maximise = typ_arrow-maximise.svg
-menu = typ_th-dot-menu.svg
-minimise = typ_arrow-minimise.svg
-more = typ_th-dot-more.svg
-noncheckable = mixed_input-none.svg
-open = typ_folder.svg
-panel = nw_panel.svg
-proj_chapter = mixed_document-chapter.svg
-proj_details = typ_th-list-grey.svg
-proj_document = typ_document-text.svg
-proj_folder = typ_folder.svg
-proj_note = mixed_document-note.svg
-proj_scene = mixed_document-scene.svg
-proj_section = mixed_document-section.svg
-proj_stats = typ_chart-bar-grey.svg
-proj_title = mixed_document-title.svg
-quote = nw_quote.svg
-refresh = typ_refresh.svg
-remove = typ_minus.svg
-revert = typ_refresh-flipped.svg
-search = typ_search.svg
-search_cancel = typ_cancel-grey.svg
-search_case = nw_search-case.svg
-search_loop = typ_arrow-repeat-grey.svg
-search_preserve = nw_search-preserve.svg
-search_project = typ_arrow-down-thick-grey.svg
-search_regex = nw_search-regex.svg
-search_replace = mixed_search-replace.svg
-search_word = nw_search-word.svg
-settings = typ_cog.svg
-size_height = mixed_size-height.svg
-size_width = mixed_size-width.svg
-star = typ_star.svg
-status_idle = typ_media-pause-grey.svg
-status_lang = typ_globe-grey.svg
-status_lines = typ_th-list-grey.svg
-status_stats = typ_chart-bar-grey.svg
-status_time = typ_stopwatch-grey.svg
-sticky-off = typ_pin-outline.svg
-sticky-on = typ_pin.svg
-toolbar = nw_toolbar.svg
-unchecked = mixed_input-unchecked.svg
-unfold-hide = typ_unfold-hidden.svg
-unfold-show = typ_unfold-visible.svg
-up = typ_chevron-up.svg
-view = typ_eye.svg
-view_build = typ_export-grey.svg
-view_editor = mixed_edit.svg
-view_novel = typ_book-grey.svg
-view_outline = typ_puzzle-outline.svg
-view_search = typ_search-grey.svg
-
-deco_doc_h0 = nw_deco-h0.svg
-deco_doc_h0_n = nw_deco-h0.svg
-deco_doc_h1 = nw_deco-h1.svg
-deco_doc_h1_n = nw_deco-h1.svg
-deco_doc_h2 = nw_deco-h2.svg
-deco_doc_h2_n = nw_deco-h2-narrow.svg
-deco_doc_h3 = nw_deco-h3.svg
-deco_doc_h3_n = nw_deco-h3-narrow.svg
-deco_doc_h4 = nw_deco-h4.svg
-deco_doc_h4_n = nw_deco-h4-narrow.svg
-deco_doc_more = nw_deco-noveltree-more.svg
-deco_doc_nt_n = nw_deco-note.svg
diff --git a/novelwriter/assets/icons/typicons_light/mixed_copy.svg b/novelwriter/assets/icons/typicons_light/mixed_copy.svg
deleted file mode 100644
index 17b6efc7..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_copy.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_document-chapter.svg b/novelwriter/assets/icons/typicons_light/mixed_document-chapter.svg
deleted file mode 100644
index 292f9650..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_document-chapter.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_document-new.svg b/novelwriter/assets/icons/typicons_light/mixed_document-new.svg
deleted file mode 100644
index 6d905312..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_document-new.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_document-note.svg b/novelwriter/assets/icons/typicons_light/mixed_document-note.svg
deleted file mode 100644
index b190e7ea..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_document-note.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_document-scene.svg b/novelwriter/assets/icons/typicons_light/mixed_document-scene.svg
deleted file mode 100644
index bf923192..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_document-scene.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_document-section.svg b/novelwriter/assets/icons/typicons_light/mixed_document-section.svg
deleted file mode 100644
index 89856762..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_document-section.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_document-title.svg b/novelwriter/assets/icons/typicons_light/mixed_document-title.svg
deleted file mode 100644
index 07ec932e..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_document-title.svg
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_edit.svg b/novelwriter/assets/icons/typicons_light/mixed_edit.svg
deleted file mode 100644
index 5f643b15..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_edit.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_import.svg b/novelwriter/assets/icons/typicons_light/mixed_import.svg
deleted file mode 100644
index c06c6cd8..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_import.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_input-checked.svg b/novelwriter/assets/icons/typicons_light/mixed_input-checked.svg
deleted file mode 100644
index 05ce62f8..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_input-checked.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_input-none.svg b/novelwriter/assets/icons/typicons_light/mixed_input-none.svg
deleted file mode 100644
index 59912739..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_input-none.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_input-unchecked.svg b/novelwriter/assets/icons/typicons_light/mixed_input-unchecked.svg
deleted file mode 100644
index c2c314b8..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_input-unchecked.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_margin-bottom.svg b/novelwriter/assets/icons/typicons_light/mixed_margin-bottom.svg
deleted file mode 100644
index 86347296..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_margin-bottom.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_margin-left.svg b/novelwriter/assets/icons/typicons_light/mixed_margin-left.svg
deleted file mode 100644
index 436f8f8d..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_margin-left.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_margin-right.svg b/novelwriter/assets/icons/typicons_light/mixed_margin-right.svg
deleted file mode 100644
index 4462801c..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_margin-right.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_margin-top.svg b/novelwriter/assets/icons/typicons_light/mixed_margin-top.svg
deleted file mode 100644
index 4eb684f9..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_margin-top.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_search-replace.svg b/novelwriter/assets/icons/typicons_light/mixed_search-replace.svg
deleted file mode 100644
index 8031c745..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_search-replace.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_size-height.svg b/novelwriter/assets/icons/typicons_light/mixed_size-height.svg
deleted file mode 100644
index 4deb1a4c..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_size-height.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/mixed_size-width.svg b/novelwriter/assets/icons/typicons_light/mixed_size-width.svg
deleted file mode 100644
index b63fe98d..00000000
--- a/novelwriter/assets/icons/typicons_light/mixed_size-width.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-h0.svg b/novelwriter/assets/icons/typicons_light/nw_deco-h0.svg
deleted file mode 100644
index 9b9cf15e..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-h0.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-h1.svg b/novelwriter/assets/icons/typicons_light/nw_deco-h1.svg
deleted file mode 100644
index 5dd9cb21..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-h1.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-h2-narrow.svg b/novelwriter/assets/icons/typicons_light/nw_deco-h2-narrow.svg
deleted file mode 100644
index fe43924d..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-h2-narrow.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-h2.svg b/novelwriter/assets/icons/typicons_light/nw_deco-h2.svg
deleted file mode 100644
index e3ab3835..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-h2.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-h3-narrow.svg b/novelwriter/assets/icons/typicons_light/nw_deco-h3-narrow.svg
deleted file mode 100644
index 79a75ac4..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-h3-narrow.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-h3.svg b/novelwriter/assets/icons/typicons_light/nw_deco-h3.svg
deleted file mode 100644
index f3e40a82..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-h3.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-h4-narrow.svg b/novelwriter/assets/icons/typicons_light/nw_deco-h4-narrow.svg
deleted file mode 100644
index 7a7279bc..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-h4-narrow.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-h4.svg b/novelwriter/assets/icons/typicons_light/nw_deco-h4.svg
deleted file mode 100644
index 1b187073..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-h4.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-note.svg b/novelwriter/assets/icons/typicons_light/nw_deco-note.svg
deleted file mode 100644
index 972d71c7..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-note.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_deco-noveltree-more.svg b/novelwriter/assets/icons/typicons_light/nw_deco-noveltree-more.svg
deleted file mode 100644
index 845b6883..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_deco-noveltree-more.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_font.svg b/novelwriter/assets/icons/typicons_light/nw_font.svg
deleted file mode 100644
index 987f2fc6..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_font.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_panel.svg b/novelwriter/assets/icons/typicons_light/nw_panel.svg
deleted file mode 100644
index c78ab50b..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_panel.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_quote.svg b/novelwriter/assets/icons/typicons_light/nw_quote.svg
deleted file mode 100644
index bdf76e81..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_quote.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_search-case.svg b/novelwriter/assets/icons/typicons_light/nw_search-case.svg
deleted file mode 100644
index c5271d80..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_search-case.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_search-preserve.svg b/novelwriter/assets/icons/typicons_light/nw_search-preserve.svg
deleted file mode 100644
index 69926638..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_search-preserve.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_search-regex.svg b/novelwriter/assets/icons/typicons_light/nw_search-regex.svg
deleted file mode 100644
index 87d127e9..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_search-regex.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_search-word.svg b/novelwriter/assets/icons/typicons_light/nw_search-word.svg
deleted file mode 100644
index 90742084..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_search-word.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-bold-md.svg b/novelwriter/assets/icons/typicons_light/nw_tb-bold-md.svg
deleted file mode 100644
index 69614a4b..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-bold-md.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-bold.svg b/novelwriter/assets/icons/typicons_light/nw_tb-bold.svg
deleted file mode 100644
index 45b25e7c..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-bold.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-italic-md.svg b/novelwriter/assets/icons/typicons_light/nw_tb-italic-md.svg
deleted file mode 100644
index 893d8930..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-italic-md.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-italic.svg b/novelwriter/assets/icons/typicons_light/nw_tb-italic.svg
deleted file mode 100644
index b09e11cc..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-italic.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-mark.svg b/novelwriter/assets/icons/typicons_light/nw_tb-mark.svg
deleted file mode 100644
index dcf138de..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-mark.svg
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-strike-md.svg b/novelwriter/assets/icons/typicons_light/nw_tb-strike-md.svg
deleted file mode 100644
index c915d218..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-strike-md.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-strike.svg b/novelwriter/assets/icons/typicons_light/nw_tb-strike.svg
deleted file mode 100644
index 2d73ab90..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-strike.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-subscript.svg b/novelwriter/assets/icons/typicons_light/nw_tb-subscript.svg
deleted file mode 100644
index 573d6802..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-subscript.svg
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-superscript.svg b/novelwriter/assets/icons/typicons_light/nw_tb-superscript.svg
deleted file mode 100644
index f650df47..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-superscript.svg
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_tb-underline.svg b/novelwriter/assets/icons/typicons_light/nw_tb-underline.svg
deleted file mode 100644
index 2c7eb51d..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_tb-underline.svg
+++ /dev/null
@@ -1,7 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/nw_toolbar.svg b/novelwriter/assets/icons/typicons_light/nw_toolbar.svg
deleted file mode 100644
index c68f444d..00000000
--- a/novelwriter/assets/icons/typicons_light/nw_toolbar.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_arrow-down-thick-grey.svg b/novelwriter/assets/icons/typicons_light/typ_arrow-down-thick-grey.svg
deleted file mode 100644
index cc4178db..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_arrow-down-thick-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_arrow-forward.svg b/novelwriter/assets/icons/typicons_light/typ_arrow-forward.svg
deleted file mode 100644
index 9d488e06..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_arrow-forward.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_arrow-maximise.svg b/novelwriter/assets/icons/typicons_light/typ_arrow-maximise.svg
deleted file mode 100644
index 5e855826..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_arrow-maximise.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_arrow-minimise.svg b/novelwriter/assets/icons/typicons_light/typ_arrow-minimise.svg
deleted file mode 100644
index 903257ed..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_arrow-minimise.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_arrow-repeat-grey.svg b/novelwriter/assets/icons/typicons_light/typ_arrow-repeat-grey.svg
deleted file mode 100644
index a45827e0..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_arrow-repeat-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_book-grey.svg b/novelwriter/assets/icons/typicons_light/typ_book-grey.svg
deleted file mode 100644
index 5bc4509c..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_book-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_book.svg b/novelwriter/assets/icons/typicons_light/typ_book.svg
deleted file mode 100644
index c3e3b698..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_book.svg
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_bookmark.svg b/novelwriter/assets/icons/typicons_light/typ_bookmark.svg
deleted file mode 100644
index 62bcb1e7..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_bookmark.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_calendar.svg b/novelwriter/assets/icons/typicons_light/typ_calendar.svg
deleted file mode 100644
index 0dc1b1b0..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_calendar.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_cancel-grey.svg b/novelwriter/assets/icons/typicons_light/typ_cancel-grey.svg
deleted file mode 100644
index 008be70c..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_cancel-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_cancel.svg b/novelwriter/assets/icons/typicons_light/typ_cancel.svg
deleted file mode 100644
index 5c2e2ba9..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_cancel.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_chart-bar-grey.svg b/novelwriter/assets/icons/typicons_light/typ_chart-bar-grey.svg
deleted file mode 100644
index 1d02c6bd..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_chart-bar-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_chevron-down.svg b/novelwriter/assets/icons/typicons_light/typ_chevron-down.svg
deleted file mode 100644
index d05627bd..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_chevron-down.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_chevron-left.svg b/novelwriter/assets/icons/typicons_light/typ_chevron-left.svg
deleted file mode 100644
index 803fb034..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_chevron-left.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_chevron-right.svg b/novelwriter/assets/icons/typicons_light/typ_chevron-right.svg
deleted file mode 100644
index e5041577..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_chevron-right.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_chevron-up.svg b/novelwriter/assets/icons/typicons_light/typ_chevron-up.svg
deleted file mode 100644
index 3eec317b..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_chevron-up.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_cog.svg b/novelwriter/assets/icons/typicons_light/typ_cog.svg
deleted file mode 100644
index e456de42..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_cog.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_delete-full.svg b/novelwriter/assets/icons/typicons_light/typ_delete-full.svg
deleted file mode 100644
index 5a4dd8cd..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_delete-full.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_delete.svg b/novelwriter/assets/icons/typicons_light/typ_delete.svg
deleted file mode 100644
index 93f62972..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_delete.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_directions-full.svg b/novelwriter/assets/icons/typicons_light/typ_directions-full.svg
deleted file mode 100644
index 230a2774..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_directions-full.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_document-add.svg b/novelwriter/assets/icons/typicons_light/typ_document-add.svg
deleted file mode 100644
index 4e181685..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_document-add.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_document-text.svg b/novelwriter/assets/icons/typicons_light/typ_document-text.svg
deleted file mode 100644
index 77e4e270..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_document-text.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_document.svg b/novelwriter/assets/icons/typicons_light/typ_document.svg
deleted file mode 100644
index 3d42b98b..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_document.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_export-grey.svg b/novelwriter/assets/icons/typicons_light/typ_export-grey.svg
deleted file mode 100644
index eed8ef4b..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_export-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_export.svg b/novelwriter/assets/icons/typicons_light/typ_export.svg
deleted file mode 100644
index 7d43e7a1..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_export.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_eye.svg b/novelwriter/assets/icons/typicons_light/typ_eye.svg
deleted file mode 100644
index 9cae4229..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_eye.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_flag.svg b/novelwriter/assets/icons/typicons_light/typ_flag.svg
deleted file mode 100644
index 66bb3739..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_flag.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_folder-open.svg b/novelwriter/assets/icons/typicons_light/typ_folder-open.svg
deleted file mode 100644
index 69c4ab24..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_folder-open.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_folder.svg b/novelwriter/assets/icons/typicons_light/typ_folder.svg
deleted file mode 100644
index 6d951ad2..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_folder.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_globe-grey.svg b/novelwriter/assets/icons/typicons_light/typ_globe-grey.svg
deleted file mode 100644
index 4cb3c5ea..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_globe-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_key.svg b/novelwriter/assets/icons/typicons_light/typ_key.svg
deleted file mode 100644
index 4aa23e01..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_key.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_lightbulb-full.svg b/novelwriter/assets/icons/typicons_light/typ_lightbulb-full.svg
deleted file mode 100644
index 46b3d88a..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_lightbulb-full.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_location.svg b/novelwriter/assets/icons/typicons_light/typ_location.svg
deleted file mode 100644
index 1afc813c..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_location.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_media-pause-grey.svg b/novelwriter/assets/icons/typicons_light/typ_media-pause-grey.svg
deleted file mode 100644
index 633ba70d..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_media-pause-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_media-record-outline.svg b/novelwriter/assets/icons/typicons_light/typ_media-record-outline.svg
deleted file mode 100644
index fa665fa4..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_media-record-outline.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_media-record.svg b/novelwriter/assets/icons/typicons_light/typ_media-record.svg
deleted file mode 100644
index 8ccc5fb5..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_media-record.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_minus.svg b/novelwriter/assets/icons/typicons_light/typ_minus.svg
deleted file mode 100644
index 05c9198a..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_minus.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_pencil.svg b/novelwriter/assets/icons/typicons_light/typ_pencil.svg
deleted file mode 100644
index 5307c1ce..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_pencil.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_pin-outline.svg b/novelwriter/assets/icons/typicons_light/typ_pin-outline.svg
deleted file mode 100644
index ee88a535..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_pin-outline.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_pin.svg b/novelwriter/assets/icons/typicons_light/typ_pin.svg
deleted file mode 100644
index 685a986c..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_pin.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_plus.svg b/novelwriter/assets/icons/typicons_light/typ_plus.svg
deleted file mode 100644
index 2a9491bd..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_plus.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_puzzle-outline.svg b/novelwriter/assets/icons/typicons_light/typ_puzzle-outline.svg
deleted file mode 100644
index 362eb304..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_puzzle-outline.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_puzzle.svg b/novelwriter/assets/icons/typicons_light/typ_puzzle.svg
deleted file mode 100644
index 7958538a..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_puzzle.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_refresh-flipped.svg b/novelwriter/assets/icons/typicons_light/typ_refresh-flipped.svg
deleted file mode 100644
index f59e7a83..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_refresh-flipped.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_refresh.svg b/novelwriter/assets/icons/typicons_light/typ_refresh.svg
deleted file mode 100644
index 78eb2622..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_refresh.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_search-grey.svg b/novelwriter/assets/icons/typicons_light/typ_search-grey.svg
deleted file mode 100644
index e6249537..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_search-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_search.svg b/novelwriter/assets/icons/typicons_light/typ_search.svg
deleted file mode 100644
index 5d1c701d..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_search.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_star.svg b/novelwriter/assets/icons/typicons_light/typ_star.svg
deleted file mode 100644
index 234444c3..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_star.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_stopwatch-grey.svg b/novelwriter/assets/icons/typicons_light/typ_stopwatch-grey.svg
deleted file mode 100644
index dcf3f49e..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_stopwatch-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_th-dot-menu.svg b/novelwriter/assets/icons/typicons_light/typ_th-dot-menu.svg
deleted file mode 100644
index 3b5d6383..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_th-dot-menu.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_th-dot-more.svg b/novelwriter/assets/icons/typicons_light/typ_th-dot-more.svg
deleted file mode 100644
index 779bc23f..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_th-dot-more.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_th-list-grey.svg b/novelwriter/assets/icons/typicons_light/typ_th-list-grey.svg
deleted file mode 100644
index 234af0ec..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_th-list-grey.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_th-list.svg b/novelwriter/assets/icons/typicons_light/typ_th-list.svg
deleted file mode 100644
index d569d85f..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_th-list.svg
+++ /dev/null
@@ -1,9 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_times.svg b/novelwriter/assets/icons/typicons_light/typ_times.svg
deleted file mode 100644
index dc905456..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_times.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_trash.svg b/novelwriter/assets/icons/typicons_light/typ_trash.svg
deleted file mode 100644
index 6073aaef..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_trash.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_unfold-hidden.svg b/novelwriter/assets/icons/typicons_light/typ_unfold-hidden.svg
deleted file mode 100644
index f187a8ad..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_unfold-hidden.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_unfold-visible.svg b/novelwriter/assets/icons/typicons_light/typ_unfold-visible.svg
deleted file mode 100644
index 8fad21e3..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_unfold-visible.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_user.svg b/novelwriter/assets/icons/typicons_light/typ_user.svg
deleted file mode 100644
index c85b1e1c..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_user.svg
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
diff --git a/novelwriter/assets/icons/typicons_light/typ_warning-full.svg b/novelwriter/assets/icons/typicons_light/typ_warning-full.svg
deleted file mode 100644
index 3310b350..00000000
--- a/novelwriter/assets/icons/typicons_light/typ_warning-full.svg
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
diff --git a/novelwriter/assets/themes/cyberpunk_night.conf b/novelwriter/assets/themes/cyberpunk_night.conf
index ba3e8898..54c68b6c 100644
--- a/novelwriter/assets/themes/cyberpunk_night.conf
+++ b/novelwriter/assets/themes/cyberpunk_night.conf
@@ -5,7 +5,6 @@ author = Anders Lemvigh
url = https://github.com/alemvigh
license = CC BY-SA 4.0
licenseurl = https://creativecommons.org/licenses/by-sa/4.0/
-icontheme = typicons_dark
[Icons]
default = 150, 150, 150
diff --git a/novelwriter/assets/themes/default_dark.conf b/novelwriter/assets/themes/default_dark.conf
index d123ec9d..17fbe2cd 100644
--- a/novelwriter/assets/themes/default_dark.conf
+++ b/novelwriter/assets/themes/default_dark.conf
@@ -6,7 +6,6 @@ credit = Veronica Berglyd Olsen
url = https://github.com/vkbo/novelWriter
license = CC BY-SA 4.0
licenseurl = https://creativecommons.org/licenses/by-sa/4.0/
-icontheme = typicons_dark
[Icons]
default = 204, 204, 204
diff --git a/novelwriter/assets/themes/default_light.conf b/novelwriter/assets/themes/default_light.conf
index 99a66b37..f3374a24 100644
--- a/novelwriter/assets/themes/default_light.conf
+++ b/novelwriter/assets/themes/default_light.conf
@@ -6,7 +6,6 @@ credit = Veronica Berglyd Olsen
url = https://github.com/vkbo/novelWriter
license = CC BY-SA 4.0
licenseurl = https://creativecommons.org/licenses/by-sa/4.0/
-icontheme = typicons_light
[Icons]
default = 77, 77, 76
diff --git a/novelwriter/assets/themes/dracula.conf b/novelwriter/assets/themes/dracula.conf
index 7e637fce..f9e5a41e 100644
--- a/novelwriter/assets/themes/dracula.conf
+++ b/novelwriter/assets/themes/dracula.conf
@@ -6,7 +6,6 @@ credit = Zeno Rocha
url = https://draculatheme.com
license = MIT
licenseurl = https://github.com/dracula/dracula-theme/blob/main/LICENSE
-icontheme = typicons_dark
##
# Colours:
diff --git a/novelwriter/assets/themes/solarized_dark.conf b/novelwriter/assets/themes/solarized_dark.conf
index 8adf91b8..904dc734 100644
--- a/novelwriter/assets/themes/solarized_dark.conf
+++ b/novelwriter/assets/themes/solarized_dark.conf
@@ -5,7 +5,6 @@ credit = Ethan Schoonover
url = https://ethanschoonover.com/solarized/
license = MIT
licenseurl = https://github.com/altercation/solarized/blob/master/LICENSE
-icontheme = typicons_dark
[Icons]
default = 253, 246, 227
diff --git a/novelwriter/assets/themes/solarized_light.conf b/novelwriter/assets/themes/solarized_light.conf
index 6b5cec3f..2cea39a9 100644
--- a/novelwriter/assets/themes/solarized_light.conf
+++ b/novelwriter/assets/themes/solarized_light.conf
@@ -5,7 +5,6 @@ credit = Ethan Schoonover
url = https://ethanschoonover.com/solarized/
license = MIT
licenseurl = https://github.com/altercation/solarized/blob/master/LICENSE
-icontheme = typicons_light
[Icons]
default = 0, 43, 54
diff --git a/sample/nwProject.nwx b/sample/nwProject.nwx
index a3c73560..78ab501b 100644
--- a/sample/nwProject.nwx
+++ b/sample/nwProject.nwx
@@ -1,6 +1,6 @@
-
-
+
+
Sample Project
Jane Smith
@@ -58,7 +58,7 @@
Chapter One
-
-
+
Making a Scene
-
From 24eb99cdaa92aa73a0cbfaecfc830902f375a9ba Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Wed, 8 Jan 2025 02:09:04 +0100
Subject: [PATCH 11/18] Change the material icons a little
---
.../assets/icons/material_filled_bold.icons | 180 +++++++++---------
.../assets/icons/material_filled_normal.icons | 2 +-
.../assets/icons/material_filled_thin.icons | 98 ++++++++++
.../assets/icons/material_outline_bold.icons | 98 ----------
.../icons/material_outline_normal.icons | 98 ----------
.../assets/icons/material_rounded_bold.icons | 180 +++++++++---------
.../icons/material_rounded_normal.icons | 2 +-
.../assets/icons/material_rounded_thin.icons | 98 ++++++++++
pkgutils.py | 28 +--
utils/material_icons.py | 2 +-
10 files changed, 393 insertions(+), 393 deletions(-)
create mode 100644 novelwriter/assets/icons/material_filled_thin.icons
delete mode 100644 novelwriter/assets/icons/material_outline_bold.icons
delete mode 100644 novelwriter/assets/icons/material_outline_normal.icons
create mode 100644 novelwriter/assets/icons/material_rounded_thin.icons
diff --git a/novelwriter/assets/icons/material_filled_bold.icons b/novelwriter/assets/icons/material_filled_bold.icons
index 71152699..92889201 100644
--- a/novelwriter/assets/icons/material_filled_bold.icons
+++ b/novelwriter/assets/icons/material_filled_bold.icons
@@ -6,93 +6,93 @@ meta:author = Google
meta:license = Apache License Version 2.0
# Icons
-icon:alert_error =
-icon:alert_info =
-icon:alert_question =
-icon:alert_warn =
-icon:cls_archive =
-icon:cls_character =
-icon:cls_custom =
-icon:cls_entity =
-icon:cls_none =
-icon:cls_novel =
-icon:cls_object =
-icon:cls_plot =
-icon:cls_template =
-icon:cls_timeline =
-icon:cls_trash =
-icon:cls_world =
-icon:fmt_bold =
-icon:fmt_italic =
-icon:fmt_mark =
-icon:fmt_strike =
-icon:fmt_subscript =
-icon:fmt_superscript =
-icon:fmt_underline =
-icon:fmt_toolbar =
-icon:search =
-icon:search_cancel =
-icon:search_case =
-icon:search_loop =
-icon:search_preserve =
-icon:search_project =
-icon:search_regex =
-icon:search_replace =
-icon:search_word =
-icon:bullet-off =
-icon:bullet-on =
-icon:unfold-hide =
-icon:unfold-show =
-icon:add =
-icon:bookmarks =
-icon:browse =
-icon:cancel =
-icon:checked =
-icon:chevron_down =
-icon:chevron_left =
-icon:chevron_right =
-icon:chevron_up =
-icon:close =
-icon:copy =
-icon:document_add =
-icon:document =
-icon:edit =
-icon:exclude =
-icon:export =
-icon:filter =
-icon:fit_height =
-icon:fit_width =
-icon:folder =
-icon:font =
-icon:import =
-icon:language =
-icon:lines =
-icon:list =
-icon:manuscript =
-icon:margin_bottom =
-icon:margin_left =
-icon:margin_right =
-icon:margin_top =
-icon:maximise =
-icon:minimise =
-icon:more_arrow =
-icon:more_vertical =
-icon:noncheckable =
-icon:novel_view =
-icon:open =
-icon:outline =
-icon:panel =
-icon:pin =
-icon:project_copy =
-icon:project_view =
-icon:quote =
-icon:refresh =
-icon:remove =
-icon:revert =
-icon:settings =
-icon:star =
-icon:stats =
-icon:timer_off =
-icon:timer =
-icon:unchecked =
-icon:view =
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_arrow =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/novelwriter/assets/icons/material_filled_normal.icons b/novelwriter/assets/icons/material_filled_normal.icons
index 601a2c1e..2f3d1b84 100644
--- a/novelwriter/assets/icons/material_filled_normal.icons
+++ b/novelwriter/assets/icons/material_filled_normal.icons
@@ -1,7 +1,7 @@
# This file is automatically generated. Do not edit.
# Meta
-meta:name = Material Symbols - Filled
+meta:name = Material Symbols - Filled Medium
meta:author = Google
meta:license = Apache License Version 2.0
diff --git a/novelwriter/assets/icons/material_filled_thin.icons b/novelwriter/assets/icons/material_filled_thin.icons
new file mode 100644
index 00000000..70206ae1
--- /dev/null
+++ b/novelwriter/assets/icons/material_filled_thin.icons
@@ -0,0 +1,98 @@
+# This file is automatically generated. Do not edit.
+
+# Meta
+meta:name = Material Symbols - Filled Thin
+meta:author = Google
+meta:license = Apache License Version 2.0
+
+# Icons
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_arrow =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/novelwriter/assets/icons/material_outline_bold.icons b/novelwriter/assets/icons/material_outline_bold.icons
deleted file mode 100644
index 18f89bc2..00000000
--- a/novelwriter/assets/icons/material_outline_bold.icons
+++ /dev/null
@@ -1,98 +0,0 @@
-# This file is automatically generated. Do not edit.
-
-# Meta
-meta:name = Material Symbols - Outlined Bold
-meta:author = Google
-meta:license = Apache License Version 2.0
-
-# Icons
-icon:alert_error =
-icon:alert_info =
-icon:alert_question =
-icon:alert_warn =
-icon:cls_archive =
-icon:cls_character =
-icon:cls_custom =
-icon:cls_entity =
-icon:cls_none =
-icon:cls_novel =
-icon:cls_object =
-icon:cls_plot =
-icon:cls_template =
-icon:cls_timeline =
-icon:cls_trash =
-icon:cls_world =
-icon:fmt_bold =
-icon:fmt_italic =
-icon:fmt_mark =
-icon:fmt_strike =
-icon:fmt_subscript =
-icon:fmt_superscript =
-icon:fmt_underline =
-icon:fmt_toolbar =
-icon:search =
-icon:search_cancel =
-icon:search_case =
-icon:search_loop =
-icon:search_preserve =
-icon:search_project =
-icon:search_regex =
-icon:search_replace =
-icon:search_word =
-icon:bullet-off =
-icon:bullet-on =
-icon:unfold-hide =
-icon:unfold-show =
-icon:add =
-icon:bookmarks =
-icon:browse =
-icon:cancel =
-icon:checked =
-icon:chevron_down =
-icon:chevron_left =
-icon:chevron_right =
-icon:chevron_up =
-icon:close =
-icon:copy =
-icon:document_add =
-icon:document =
-icon:edit =
-icon:exclude =
-icon:export =
-icon:filter =
-icon:fit_height =
-icon:fit_width =
-icon:folder =
-icon:font =
-icon:import =
-icon:language =
-icon:lines =
-icon:list =
-icon:manuscript =
-icon:margin_bottom =
-icon:margin_left =
-icon:margin_right =
-icon:margin_top =
-icon:maximise =
-icon:minimise =
-icon:more_arrow =
-icon:more_vertical =
-icon:noncheckable =
-icon:novel_view =
-icon:open =
-icon:outline =
-icon:panel =
-icon:pin =
-icon:project_copy =
-icon:project_view =
-icon:quote =
-icon:refresh =
-icon:remove =
-icon:revert =
-icon:settings =
-icon:star =
-icon:stats =
-icon:timer_off =
-icon:timer =
-icon:unchecked =
-icon:view =
diff --git a/novelwriter/assets/icons/material_outline_normal.icons b/novelwriter/assets/icons/material_outline_normal.icons
deleted file mode 100644
index 590e6ee6..00000000
--- a/novelwriter/assets/icons/material_outline_normal.icons
+++ /dev/null
@@ -1,98 +0,0 @@
-# This file is automatically generated. Do not edit.
-
-# Meta
-meta:name = Material Symbols - Outlined
-meta:author = Google
-meta:license = Apache License Version 2.0
-
-# Icons
-icon:alert_error =
-icon:alert_info =
-icon:alert_question =
-icon:alert_warn =
-icon:cls_archive =
-icon:cls_character =
-icon:cls_custom =
-icon:cls_entity =
-icon:cls_none =
-icon:cls_novel =
-icon:cls_object =
-icon:cls_plot =
-icon:cls_template =
-icon:cls_timeline =
-icon:cls_trash =
-icon:cls_world =
-icon:fmt_bold =
-icon:fmt_italic =
-icon:fmt_mark =
-icon:fmt_strike =
-icon:fmt_subscript =
-icon:fmt_superscript =
-icon:fmt_underline =
-icon:fmt_toolbar =
-icon:search =
-icon:search_cancel =
-icon:search_case =
-icon:search_loop =
-icon:search_preserve =
-icon:search_project =
-icon:search_regex =
-icon:search_replace =
-icon:search_word =
-icon:bullet-off =
-icon:bullet-on =
-icon:unfold-hide =
-icon:unfold-show =
-icon:add =
-icon:bookmarks =
-icon:browse =
-icon:cancel =
-icon:checked =
-icon:chevron_down =
-icon:chevron_left =
-icon:chevron_right =
-icon:chevron_up =
-icon:close =
-icon:copy =
-icon:document_add =
-icon:document =
-icon:edit =
-icon:exclude =
-icon:export =
-icon:filter =
-icon:fit_height =
-icon:fit_width =
-icon:folder =
-icon:font =
-icon:import =
-icon:language =
-icon:lines =
-icon:list =
-icon:manuscript =
-icon:margin_bottom =
-icon:margin_left =
-icon:margin_right =
-icon:margin_top =
-icon:maximise =
-icon:minimise =
-icon:more_arrow =
-icon:more_vertical =
-icon:noncheckable =
-icon:novel_view =
-icon:open =
-icon:outline =
-icon:panel =
-icon:pin =
-icon:project_copy =
-icon:project_view =
-icon:quote =
-icon:refresh =
-icon:remove =
-icon:revert =
-icon:settings =
-icon:star =
-icon:stats =
-icon:timer_off =
-icon:timer =
-icon:unchecked =
-icon:view =
diff --git a/novelwriter/assets/icons/material_rounded_bold.icons b/novelwriter/assets/icons/material_rounded_bold.icons
index 7f1a4b3b..dde3f32e 100644
--- a/novelwriter/assets/icons/material_rounded_bold.icons
+++ b/novelwriter/assets/icons/material_rounded_bold.icons
@@ -6,93 +6,93 @@ meta:author = Google
meta:license = Apache License Version 2.0
# Icons
-icon:alert_error =
-icon:alert_info =
-icon:alert_question =
-icon:alert_warn =
-icon:cls_archive =
-icon:cls_character =
-icon:cls_custom =
-icon:cls_entity =
-icon:cls_none =
-icon:cls_novel =
-icon:cls_object =
-icon:cls_plot =
-icon:cls_template =
-icon:cls_timeline =
-icon:cls_trash =
-icon:cls_world =
-icon:fmt_bold =
-icon:fmt_italic =
-icon:fmt_mark =
-icon:fmt_strike =
-icon:fmt_subscript =
-icon:fmt_superscript =
-icon:fmt_underline =
-icon:fmt_toolbar =
-icon:search =
-icon:search_cancel =
-icon:search_case =
-icon:search_loop =
-icon:search_preserve =
-icon:search_project =
-icon:search_regex =
-icon:search_replace =
-icon:search_word =
-icon:bullet-off =
-icon:bullet-on =
-icon:unfold-hide =
-icon:unfold-show =
-icon:add =
-icon:bookmarks =
-icon:browse =
-icon:cancel =
-icon:checked =
-icon:chevron_down =
-icon:chevron_left =
-icon:chevron_right =
-icon:chevron_up =
-icon:close =
-icon:copy =
-icon:document_add =
-icon:document =
-icon:edit =
-icon:exclude =
-icon:export =
-icon:filter =
-icon:fit_height =
-icon:fit_width =
-icon:folder =
-icon:font =
-icon:import =
-icon:language =
-icon:lines =
-icon:list =
-icon:manuscript =
-icon:margin_bottom =
-icon:margin_left =
-icon:margin_right =
-icon:margin_top =
-icon:maximise =
-icon:minimise =
-icon:more_arrow =
-icon:more_vertical =
-icon:noncheckable =
-icon:novel_view =
-icon:open =
-icon:outline =
-icon:panel =
-icon:pin =
-icon:project_copy =
-icon:project_view =
-icon:quote =
-icon:refresh =
-icon:remove =
-icon:revert =
-icon:settings =
-icon:star =
-icon:stats =
-icon:timer_off =
-icon:timer =
-icon:unchecked =
-icon:view =
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_arrow =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/novelwriter/assets/icons/material_rounded_normal.icons b/novelwriter/assets/icons/material_rounded_normal.icons
index ff312875..fe240ee7 100644
--- a/novelwriter/assets/icons/material_rounded_normal.icons
+++ b/novelwriter/assets/icons/material_rounded_normal.icons
@@ -1,7 +1,7 @@
# This file is automatically generated. Do not edit.
# Meta
-meta:name = Material Symbols - Rounded
+meta:name = Material Symbols - Rounded Medium
meta:author = Google
meta:license = Apache License Version 2.0
diff --git a/novelwriter/assets/icons/material_rounded_thin.icons b/novelwriter/assets/icons/material_rounded_thin.icons
new file mode 100644
index 00000000..19a60761
--- /dev/null
+++ b/novelwriter/assets/icons/material_rounded_thin.icons
@@ -0,0 +1,98 @@
+# This file is automatically generated. Do not edit.
+
+# Meta
+meta:name = Material Symbols - Rounded Thin
+meta:author = Google
+meta:license = Apache License Version 2.0
+
+# Icons
+icon:alert_error =
+icon:alert_info =
+icon:alert_question =
+icon:alert_warn =
+icon:cls_archive =
+icon:cls_character =
+icon:cls_custom =
+icon:cls_entity =
+icon:cls_none =
+icon:cls_novel =
+icon:cls_object =
+icon:cls_plot =
+icon:cls_template =
+icon:cls_timeline =
+icon:cls_trash =
+icon:cls_world =
+icon:fmt_bold =
+icon:fmt_italic =
+icon:fmt_mark =
+icon:fmt_strike =
+icon:fmt_subscript =
+icon:fmt_superscript =
+icon:fmt_underline =
+icon:fmt_toolbar =
+icon:search =
+icon:search_cancel =
+icon:search_case =
+icon:search_loop =
+icon:search_preserve =
+icon:search_project =
+icon:search_regex =
+icon:search_replace =
+icon:search_word =
+icon:bullet-off =
+icon:bullet-on =
+icon:unfold-hide =
+icon:unfold-show =
+icon:add =
+icon:bookmarks =
+icon:browse =
+icon:cancel =
+icon:checked =
+icon:chevron_down =
+icon:chevron_left =
+icon:chevron_right =
+icon:chevron_up =
+icon:close =
+icon:copy =
+icon:document_add =
+icon:document =
+icon:edit =
+icon:exclude =
+icon:export =
+icon:filter =
+icon:fit_height =
+icon:fit_width =
+icon:folder =
+icon:font =
+icon:import =
+icon:language =
+icon:lines =
+icon:list =
+icon:manuscript =
+icon:margin_bottom =
+icon:margin_left =
+icon:margin_right =
+icon:margin_top =
+icon:maximise =
+icon:minimise =
+icon:more_arrow =
+icon:more_vertical =
+icon:noncheckable =
+icon:novel_view =
+icon:open =
+icon:outline =
+icon:panel =
+icon:pin =
+icon:project_copy =
+icon:project_view =
+icon:quote =
+icon:refresh =
+icon:remove =
+icon:revert =
+icon:settings =
+icon:star =
+icon:stats =
+icon:timer_off =
+icon:timer =
+icon:unchecked =
+icon:view =
diff --git a/pkgutils.py b/pkgutils.py
index 2e874153..1e714351 100755
--- a/pkgutils.py
+++ b/pkgutils.py
@@ -346,20 +346,14 @@ def buildIconTheme(args: argparse.Namespace) -> None:
style = args.style
if style == "material":
processMaterialIcons(workDir, iconsDir, {
- "material_outline_normal": {
- "name": "Material Symbols - Outlined",
- "style": "outlined",
+ "material_rounded_thin": {
+ "name": "Material Symbols - Rounded Thin",
+ "style": "rounded",
"filled": False,
- "weight": 400,
- },
- "material_outline_bold": {
- "name": "Material Symbols - Outlined Bold",
- "style": "outlined",
- "filled": False,
- "weight": 700,
+ "weight": 200,
},
"material_rounded_normal": {
- "name": "Material Symbols - Rounded",
+ "name": "Material Symbols - Rounded Medium",
"style": "rounded",
"filled": False,
"weight": 400,
@@ -368,10 +362,16 @@ def buildIconTheme(args: argparse.Namespace) -> None:
"name": "Material Symbols - Rounded Bold",
"style": "rounded",
"filled": False,
- "weight": 700,
+ "weight": 600,
+ },
+ "material_filled_thin": {
+ "name": "Material Symbols - Filled Thin",
+ "style": "rounded",
+ "filled": True,
+ "weight": 200,
},
"material_filled_normal": {
- "name": "Material Symbols - Filled",
+ "name": "Material Symbols - Filled Medium",
"style": "rounded",
"filled": True,
"weight": 400,
@@ -380,7 +380,7 @@ def buildIconTheme(args: argparse.Namespace) -> None:
"name": "Material Symbols - Filled Bold",
"style": "rounded",
"filled": True,
- "weight": 700,
+ "weight": 600,
},
})
diff --git a/utils/material_icons.py b/utils/material_icons.py
index 7758759c..4e15371f 100644
--- a/utils/material_icons.py
+++ b/utils/material_icons.py
@@ -3,7 +3,7 @@ novelWriter – Material Icon Theme
=================================
This file is a part of novelWriter
-Copyright (C) 2019 Veronica Berglyd Olsen and novelWriter contributors
+Copyright (C) 2025 Veronica Berglyd Olsen and novelWriter contributors
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
From 5650792be806865684263262603619cca3f673a0 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Wed, 8 Jan 2025 02:09:22 +0100
Subject: [PATCH 12/18] Add icon theme selector to Preferences
---
novelwriter/dialogs/preferences.py | 17 ++++++++++++++++-
novelwriter/gui/theme.py | 20 ++++++++++++++++++--
2 files changed, 34 insertions(+), 3 deletions(-)
diff --git a/novelwriter/dialogs/preferences.py b/novelwriter/dialogs/preferences.py
index 97d5ffb0..8421acf5 100644
--- a/novelwriter/dialogs/preferences.py
+++ b/novelwriter/dialogs/preferences.py
@@ -173,7 +173,19 @@ class GuiPreferences(NDialog):
self.mainForm.addRow(
self.tr("Colour theme"), self.guiTheme,
- self.tr("General colour theme and icons."), stretch=(3, 2)
+ self.tr("User interface colour theme."), stretch=(3, 2)
+ )
+
+ # Icon Theme
+ self.guiIcons = NComboBox(self)
+ self.guiIcons.setMinimumWidth(minWidth)
+ for theme, name in SHARED.theme.iconCache.listThemes():
+ self.guiIcons.addItem(name, theme)
+ self.guiIcons.setCurrentData(CONFIG.guiIcons, "material_rounded_bold")
+
+ self.mainForm.addRow(
+ self.tr("Icon theme"), self.guiIcons,
+ self.tr("User interface icon theme."), stretch=(3, 2)
)
# Application Font Family
@@ -902,13 +914,16 @@ class GuiPreferences(NDialog):
# Appearance
guiLocale = self.guiLocale.currentData()
guiTheme = self.guiTheme.currentData()
+ guiIcons = self.guiIcons.currentData()
updateTheme |= CONFIG.guiTheme != guiTheme
+ updateTheme |= CONFIG.guiIcons != guiIcons
needsRestart |= CONFIG.guiLocale != guiLocale
needsRestart |= CONFIG.guiFont != self._guiFont
CONFIG.guiLocale = guiLocale
CONFIG.guiTheme = guiTheme
+ CONFIG.guiIcons = guiIcons
CONFIG.hideVScroll = self.hideVScroll.isChecked()
CONFIG.hideHScroll = self.hideHScroll.isChecked()
CONFIG.nativeFont = self.nativeFont.isChecked()
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index 2abb4aa4..6bba79a6 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -443,8 +443,9 @@ class GuiTheme:
"""Parse a colour value from a config string."""
return QColor(*parser.rdIntList(section, name, [0, 0, 0, 255]))
- def _setPalette(self, parser: NWConfigParser, section: str,
- name: str, value: QPalette.ColorRole) -> None:
+ def _setPalette(
+ self, parser: NWConfigParser, section: str, name: str, value: QPalette.ColorRole
+ ) -> None:
"""Set a palette colour value from a config string."""
self._guiPalette.setColor(value, self._parseColour(parser, section, name))
return
@@ -515,6 +516,7 @@ class GuiIcons:
self._headerDecNarrow: list[QPixmap] = []
# Icon Theme Path
+ self._themeList: list[tuple[str, str]] = []
self._iconPath = CONFIG.assetPath("icons")
# None Icon
@@ -692,6 +694,20 @@ class GuiIcons:
]
return self._headerDecNarrow[minmax(hLevel, 0, 5)]
+ def listThemes(self) -> list[tuple[str, str]]:
+ """Scan the GUI icons folder and list all themes."""
+ if self._themeList:
+ return self._themeList
+
+ for item in self._iconPath.iterdir():
+ if item.is_file() and item.suffix == ".icons":
+ if name := _loadIconName(item):
+ self._themeList.append((item.stem, name))
+
+ self._themeList = sorted(self._themeList, key=_sortTheme)
+
+ return self._themeList
+
##
# Internal Functions
##
From a0fea3c025ecd07b9c194eba7827992d4d67186e Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Wed, 8 Jan 2025 22:22:09 +0100
Subject: [PATCH 13/18] Separate project tree icons from the rest
---
.../assets/icons/material_filled_bold.icons | 21 +++++---
.../assets/icons/material_filled_normal.icons | 21 +++++---
.../assets/icons/material_filled_thin.icons | 21 +++++---
.../assets/icons/material_rounded_bold.icons | 21 +++++---
.../icons/material_rounded_normal.icons | 21 +++++---
.../assets/icons/material_rounded_thin.icons | 21 +++++---
.../assets/themes/cyberpunk_night.conf | 9 ++++
novelwriter/assets/themes/default_dark.conf | 9 ++++
novelwriter/assets/themes/default_light.conf | 9 ++++
novelwriter/assets/themes/dracula.conf | 10 +++-
novelwriter/assets/themes/solarized_dark.conf | 9 ++++
.../assets/themes/solarized_light.conf | 8 +++
novelwriter/constants.py | 14 -----
novelwriter/extensions/novelselector.py | 4 +-
novelwriter/gui/docviewerpanel.py | 8 +--
novelwriter/gui/itemdetails.py | 4 +-
novelwriter/gui/projtree.py | 18 +++----
novelwriter/gui/theme.py | 54 ++++++++++++-------
novelwriter/tools/lipsum.py | 2 +-
novelwriter/tools/manussettings.py | 4 +-
pkgutils.py | 2 +-
setup/debian/copyright | 39 +++++---------
utils/material_icons.py | 24 +++++----
23 files changed, 215 insertions(+), 138 deletions(-)
diff --git a/novelwriter/assets/icons/material_filled_bold.icons b/novelwriter/assets/icons/material_filled_bold.icons
index 92889201..4abcebf4 100644
--- a/novelwriter/assets/icons/material_filled_bold.icons
+++ b/novelwriter/assets/icons/material_filled_bold.icons
@@ -2,8 +2,8 @@
# Meta
meta:name = Material Symbols - Filled Bold
-meta:author = Google
-meta:license = Apache License Version 2.0
+meta:author = Google Inc
+meta:license = Apache 2.0
# Icons
icon:alert_error =
@@ -22,10 +22,16 @@ icon:cls_template =
icon:cls_trash =
icon:cls_world =
+icon:prj_folder =
+icon:prj_document =
+icon:prj_title =
+icon:prj_chapter =
+icon:prj_scene =
+icon:prj_note =
icon:fmt_bold =
icon:fmt_italic =
icon:fmt_mark =
-icon:fmt_strike =
+icon:fmt_strike =
icon:fmt_subscript =
icon:fmt_superscript =
icon:fmt_underline =
@@ -47,7 +53,7 @@ icon:add =
icon:browse =
icon:cancel =
-icon:checked =
+icon:checked =
icon:chevron_down =
icon:chevron_left =
icon:chevron_right =
@@ -55,10 +61,10 @@ icon:chevron_up =
icon:copy =
icon:document_add =
-icon:document =
+icon:document =
icon:edit =
icon:exclude =
-icon:export =
+icon:export =
icon:filter =
icon:fit_height =
icon:fit_width =
@@ -80,7 +86,7 @@ icon:more_vertical =
icon:novel_view =
icon:open =
-icon:outline =
+icon:outline =
icon:panel =
icon:pin =
icon:project_copy =
@@ -92,6 +98,7 @@ icon:revert =
icon:star =
icon:stats =
+icon:text =
icon:timer_off =
icon:timer =
icon:unchecked =
diff --git a/novelwriter/assets/icons/material_filled_normal.icons b/novelwriter/assets/icons/material_filled_normal.icons
index 2f3d1b84..53e88c4c 100644
--- a/novelwriter/assets/icons/material_filled_normal.icons
+++ b/novelwriter/assets/icons/material_filled_normal.icons
@@ -2,8 +2,8 @@
# Meta
meta:name = Material Symbols - Filled Medium
-meta:author = Google
-meta:license = Apache License Version 2.0
+meta:author = Google Inc
+meta:license = Apache 2.0
# Icons
icon:alert_error =
@@ -22,10 +22,16 @@ icon:cls_template =
icon:cls_trash =
icon:cls_world =
+icon:prj_folder =
+icon:prj_document =
+icon:prj_title =
+icon:prj_chapter =
+icon:prj_scene =
+icon:prj_note =
icon:fmt_bold =
icon:fmt_italic =
icon:fmt_mark =
-icon:fmt_strike =
+icon:fmt_strike =
icon:fmt_subscript =
icon:fmt_superscript =
icon:fmt_underline =
@@ -47,7 +53,7 @@ icon:add =
icon:browse =
icon:cancel =
-icon:checked =
+icon:checked =
icon:chevron_down =
icon:chevron_left =
icon:chevron_right =
@@ -55,10 +61,10 @@ icon:chevron_up =
icon:copy =
icon:document_add =
-icon:document =
+icon:document =
icon:edit =
icon:exclude =
-icon:export =
+icon:export =
icon:filter =
icon:fit_height =
icon:fit_width =
@@ -80,7 +86,7 @@ icon:more_vertical =
icon:novel_view =
icon:open =
-icon:outline =
+icon:outline =
icon:panel =
icon:pin =
icon:project_copy =
@@ -92,6 +98,7 @@ icon:revert =
icon:star =
icon:stats =
+icon:text =
icon:timer_off =
icon:timer =
icon:unchecked =
diff --git a/novelwriter/assets/icons/material_filled_thin.icons b/novelwriter/assets/icons/material_filled_thin.icons
index 70206ae1..43a60e8d 100644
--- a/novelwriter/assets/icons/material_filled_thin.icons
+++ b/novelwriter/assets/icons/material_filled_thin.icons
@@ -2,8 +2,8 @@
# Meta
meta:name = Material Symbols - Filled Thin
-meta:author = Google
-meta:license = Apache License Version 2.0
+meta:author = Google Inc
+meta:license = Apache 2.0
# Icons
icon:alert_error =
@@ -22,10 +22,16 @@ icon:cls_template =
icon:cls_trash =
icon:cls_world =
+icon:prj_folder =
+icon:prj_document =
+icon:prj_title =
+icon:prj_chapter =
+icon:prj_scene =
+icon:prj_note =
icon:fmt_bold =
icon:fmt_italic =
icon:fmt_mark =
-icon:fmt_strike =
+icon:fmt_strike =
icon:fmt_subscript =
icon:fmt_superscript =
icon:fmt_underline =
@@ -47,7 +53,7 @@ icon:add =
icon:browse =
icon:cancel =
-icon:checked =
+icon:checked =
icon:chevron_down =
icon:chevron_left =
icon:chevron_right =
@@ -55,10 +61,10 @@ icon:chevron_up =
icon:copy =
icon:document_add =
-icon:document =
+icon:document =
icon:edit =
icon:exclude =
-icon:export =
+icon:export =
icon:filter =
icon:fit_height =
icon:fit_width =
@@ -80,7 +86,7 @@ icon:more_vertical =
icon:novel_view =
icon:open =
-icon:outline =
+icon:outline =
icon:panel =
icon:pin =
icon:project_copy =
@@ -92,6 +98,7 @@ icon:revert =
icon:star =
icon:stats =
+icon:text =
icon:timer_off =
icon:timer =
icon:unchecked =
diff --git a/novelwriter/assets/icons/material_rounded_bold.icons b/novelwriter/assets/icons/material_rounded_bold.icons
index dde3f32e..30297456 100644
--- a/novelwriter/assets/icons/material_rounded_bold.icons
+++ b/novelwriter/assets/icons/material_rounded_bold.icons
@@ -2,8 +2,8 @@
# Meta
meta:name = Material Symbols - Rounded Bold
-meta:author = Google
-meta:license = Apache License Version 2.0
+meta:author = Google Inc
+meta:license = Apache 2.0
# Icons
icon:alert_error =
@@ -22,10 +22,16 @@ icon:cls_template =
icon:cls_trash =
icon:cls_world =
+icon:prj_folder =
+icon:prj_document =
+icon:prj_title =
+icon:prj_chapter =
+icon:prj_scene =
+icon:prj_note =
icon:fmt_bold =
icon:fmt_italic =
icon:fmt_mark =
-icon:fmt_strike =
+icon:fmt_strike =
icon:fmt_subscript =
icon:fmt_superscript =
icon:fmt_underline =
@@ -47,7 +53,7 @@ icon:add =
icon:browse =
icon:cancel =
-icon:checked =
+icon:checked =
icon:chevron_down =
icon:chevron_left =
icon:chevron_right =
@@ -55,10 +61,10 @@ icon:chevron_up =
icon:copy =
icon:document_add =
-icon:document =
+icon:document =
icon:edit =
icon:exclude =
-icon:export =
+icon:export =
icon:filter =
icon:fit_height =
icon:fit_width =
@@ -80,7 +86,7 @@ icon:more_vertical =
icon:novel_view =
icon:open =
-icon:outline =
+icon:outline =
icon:panel =
icon:pin =
icon:project_copy =
@@ -92,6 +98,7 @@ icon:revert =
icon:star =
icon:stats =
+icon:text =
icon:timer_off =
icon:timer =
icon:unchecked =
diff --git a/novelwriter/assets/icons/material_rounded_normal.icons b/novelwriter/assets/icons/material_rounded_normal.icons
index fe240ee7..f6995c5b 100644
--- a/novelwriter/assets/icons/material_rounded_normal.icons
+++ b/novelwriter/assets/icons/material_rounded_normal.icons
@@ -2,8 +2,8 @@
# Meta
meta:name = Material Symbols - Rounded Medium
-meta:author = Google
-meta:license = Apache License Version 2.0
+meta:author = Google Inc
+meta:license = Apache 2.0
# Icons
icon:alert_error =
@@ -22,10 +22,16 @@ icon:cls_template =
icon:cls_trash =
icon:cls_world =
+icon:prj_folder =
+icon:prj_document =
+icon:prj_title =
+icon:prj_chapter =
+icon:prj_scene =
+icon:prj_note =
icon:fmt_bold =
icon:fmt_italic =
icon:fmt_mark =
-icon:fmt_strike =
+icon:fmt_strike =
icon:fmt_subscript =
icon:fmt_superscript =
icon:fmt_underline =
@@ -47,7 +53,7 @@ icon:add =
icon:browse =
icon:cancel =
-icon:checked =
+icon:checked =
icon:chevron_down =
icon:chevron_left =
icon:chevron_right =
@@ -55,10 +61,10 @@ icon:chevron_up =
icon:copy =
icon:document_add =
-icon:document =
+icon:document =
icon:edit =
icon:exclude =
-icon:export =
+icon:export =
icon:filter =
icon:fit_height =
icon:fit_width =
@@ -80,7 +86,7 @@ icon:more_vertical =
icon:novel_view =
icon:open =
-icon:outline =
+icon:outline =
icon:panel =
icon:pin =
icon:project_copy =
@@ -92,6 +98,7 @@ icon:revert =
icon:star =
icon:stats =
+icon:text =
icon:timer_off =
icon:timer =
icon:unchecked =
diff --git a/novelwriter/assets/icons/material_rounded_thin.icons b/novelwriter/assets/icons/material_rounded_thin.icons
index 19a60761..e809255b 100644
--- a/novelwriter/assets/icons/material_rounded_thin.icons
+++ b/novelwriter/assets/icons/material_rounded_thin.icons
@@ -2,8 +2,8 @@
# Meta
meta:name = Material Symbols - Rounded Thin
-meta:author = Google
-meta:license = Apache License Version 2.0
+meta:author = Google Inc
+meta:license = Apache 2.0
# Icons
icon:alert_error =
@@ -22,10 +22,16 @@ icon:cls_template =
icon:cls_trash =
icon:cls_world =
+icon:prj_folder =
+icon:prj_document =
+icon:prj_title =
+icon:prj_chapter =
+icon:prj_scene =
+icon:prj_note =
icon:fmt_bold =
icon:fmt_italic =
icon:fmt_mark =
-icon:fmt_strike =
+icon:fmt_strike =
icon:fmt_subscript =
icon:fmt_superscript =
icon:fmt_underline =
@@ -47,7 +53,7 @@ icon:add =
icon:browse =
icon:cancel =
-icon:checked =
+icon:checked =
icon:chevron_down =
icon:chevron_left =
icon:chevron_right =
@@ -55,10 +61,10 @@ icon:chevron_up =
icon:copy =
icon:document_add =
-icon:document =
+icon:document =
icon:edit =
icon:exclude =
-icon:export =
+icon:export =
icon:filter =
icon:fit_height =
icon:fit_width =
@@ -80,7 +86,7 @@ icon:more_vertical =
icon:novel_view =
icon:open =
-icon:outline =
+icon:outline =
icon:panel =
icon:pin =
icon:project_copy =
@@ -92,6 +98,7 @@ icon:revert =
icon:star =
icon:stats =
+icon:text =
icon:timer_off =
icon:timer =
icon:unchecked =
diff --git a/novelwriter/assets/themes/cyberpunk_night.conf b/novelwriter/assets/themes/cyberpunk_night.conf
index 54c68b6c..143e1f20 100644
--- a/novelwriter/assets/themes/cyberpunk_night.conf
+++ b/novelwriter/assets/themes/cyberpunk_night.conf
@@ -16,6 +16,15 @@ aqua = 0, 255, 255
blue = 77, 77, 255
purple = 50, 0, 180
+[Project]
+root = 77, 77, 255
+folder = 255, 255, 0
+file = 150, 150, 150
+title = 0, 255, 0
+chapter = 242, 72, 23
+scene = 77, 77, 255
+note = 255, 255, 0
+
[Palette]
window = 0, 0, 0
windowtext = 150, 150, 150
diff --git a/novelwriter/assets/themes/default_dark.conf b/novelwriter/assets/themes/default_dark.conf
index 17fbe2cd..39b5369c 100644
--- a/novelwriter/assets/themes/default_dark.conf
+++ b/novelwriter/assets/themes/default_dark.conf
@@ -17,6 +17,15 @@ aqua = 102, 204, 204
blue = 102, 153, 204
purple = 204, 153, 204
+[Project]
+root = 102, 153, 204
+folder = 255, 204, 102
+file = 204, 204, 204
+title = 153, 204, 153
+chapter = 242, 119, 122
+scene = 102, 153, 204
+note = 255, 204, 102
+
[Palette]
window = 54, 54, 54
windowtext = 204, 204, 204
diff --git a/novelwriter/assets/themes/default_light.conf b/novelwriter/assets/themes/default_light.conf
index f3374a24..c52d1d3c 100644
--- a/novelwriter/assets/themes/default_light.conf
+++ b/novelwriter/assets/themes/default_light.conf
@@ -17,6 +17,15 @@ aqua = 62, 153, 159
blue = 66, 113, 174
purple = 137, 89, 168
+[Project]
+root = 66, 113, 174
+folder = 234, 183, 0
+file = 77, 77, 76
+title = 113, 140, 0
+chapter = 240, 40, 41
+scene = 66, 113, 174
+note = 234, 183, 0
+
[Palette]
window = 239, 239, 239
windowtext = 0, 0, 0
diff --git a/novelwriter/assets/themes/dracula.conf b/novelwriter/assets/themes/dracula.conf
index f9e5a41e..5bcd14f3 100644
--- a/novelwriter/assets/themes/dracula.conf
+++ b/novelwriter/assets/themes/dracula.conf
@@ -29,9 +29,17 @@ orange = 255, 184, 108
yellow = 241, 250, 140
green = 80, 250, 123
aqua = 139, 233, 253
-blue = 255, 121, 198
+blue = 139, 233, 253
purple = 189, 147, 249
+[Project]
+root = 189, 147, 249
+folder = 241, 250, 140
+file = 248, 248, 242
+title = 80, 250, 123
+chapter = 255, 85, 85
+scene = 139, 233, 253
+note = 241, 250, 140
[Palette]
window = 68, 71, 90
diff --git a/novelwriter/assets/themes/solarized_dark.conf b/novelwriter/assets/themes/solarized_dark.conf
index 904dc734..7bcc1073 100644
--- a/novelwriter/assets/themes/solarized_dark.conf
+++ b/novelwriter/assets/themes/solarized_dark.conf
@@ -16,6 +16,15 @@ aqua = 42, 161, 152
blue = 38, 139, 210
purple = 108, 113, 196
+[Project]
+root = 42, 161, 152
+folder = 42, 161, 152
+file = 253, 246, 227
+title = 133, 153, 0
+chapter = 220, 50, 47
+scene = 38, 139, 210
+note = 181, 137, 0
+
[Palette]
window = 0, 43, 54
windowtext = 253, 246, 227
diff --git a/novelwriter/assets/themes/solarized_light.conf b/novelwriter/assets/themes/solarized_light.conf
index 2cea39a9..6cf7c7d6 100644
--- a/novelwriter/assets/themes/solarized_light.conf
+++ b/novelwriter/assets/themes/solarized_light.conf
@@ -16,6 +16,14 @@ aqua = 42, 161, 152
blue = 38, 139, 210
purple = 108, 113, 196
+[Project]
+root = 42, 161, 152
+folder = 42, 161, 152
+file = 0, 43, 54
+title = 133, 153, 0
+chapter = 220, 50, 47
+scene = 38, 139, 210
+note = 181, 137, 0
[Palette]
window = 238, 232, 213
diff --git a/novelwriter/constants.py b/novelwriter/constants.py
index 8213cc21..bdedab10 100644
--- a/novelwriter/constants.py
+++ b/novelwriter/constants.py
@@ -258,20 +258,6 @@ class nwLabels:
nwItemClass.TEMPLATE: "cls_template",
nwItemClass.TRASH: "cls_trash",
}
- CLASS_COLOR = {
- nwItemClass.NO_CLASS: "default",
- nwItemClass.NOVEL: "red",
- nwItemClass.PLOT: "blue",
- nwItemClass.CHARACTER: "blue",
- nwItemClass.WORLD: "blue",
- nwItemClass.TIMELINE: "blue",
- nwItemClass.OBJECT: "blue",
- nwItemClass.ENTITY: "blue",
- nwItemClass.CUSTOM: "blue",
- nwItemClass.ARCHIVE: "red",
- nwItemClass.TEMPLATE: "yellow",
- nwItemClass.TRASH: "red",
- }
LAYOUT_NAME = {
nwItemLayout.NO_LAYOUT: QT_TRANSLATE_NOOP("Constant", "None"),
nwItemLayout.DOCUMENT: QT_TRANSLATE_NOOP("Constant", "Novel Document"),
diff --git a/novelwriter/extensions/novelselector.py b/novelwriter/extensions/novelselector.py
index e57a3bce..0f083151 100644
--- a/novelwriter/extensions/novelselector.py
+++ b/novelwriter/extensions/novelselector.py
@@ -94,9 +94,7 @@ class NovelSelector(QComboBox):
self._firstHandle = None
self.clear()
- icon = SHARED.theme.getIcon(
- nwLabels.CLASS_ICON[nwItemClass.NOVEL], nwLabels.CLASS_COLOR[nwItemClass.NOVEL]
- )
+ icon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[nwItemClass.NOVEL], "blue")
handle = self.currentData()
for tHandle, nwItem in SHARED.project.tree.iterRoots(nwItemClass.NOVEL):
if self._listFormat:
diff --git a/novelwriter/gui/docviewerpanel.py b/novelwriter/gui/docviewerpanel.py
index 262817a9..f3c4359a 100644
--- a/novelwriter/gui/docviewerpanel.py
+++ b/novelwriter/gui/docviewerpanel.py
@@ -410,9 +410,7 @@ class _ViewPanelKeyWords(QTreeWidget):
treeHeader.setSectionsMovable(False)
# Cache Icons Locally
- self._classIcon = SHARED.theme.getIcon(
- nwLabels.CLASS_ICON[itemClass], nwLabels.CLASS_COLOR[itemClass]
- )
+ self._classIcon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[itemClass], "root")
self._editIcon = SHARED.theme.getIcon("edit", "green")
self._viewIcon = SHARED.theme.getIcon("view", "blue")
@@ -424,9 +422,7 @@ class _ViewPanelKeyWords(QTreeWidget):
def updateTheme(self) -> None:
"""Update theme elements."""
- self._classIcon = SHARED.theme.getIcon(
- nwLabels.CLASS_ICON[self._class], nwLabels.CLASS_COLOR[self._class]
- )
+ self._classIcon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[self._class], "root")
self._editIcon = SHARED.theme.getIcon("edit", "green")
self._viewIcon = SHARED.theme.getIcon("view", "blue")
for i in range(self.topLevelItemCount()):
diff --git a/novelwriter/gui/itemdetails.py b/novelwriter/gui/itemdetails.py
index 32fd926f..47340c7c 100644
--- a/novelwriter/gui/itemdetails.py
+++ b/novelwriter/gui/itemdetails.py
@@ -255,9 +255,7 @@ class GuiItemDetails(QWidget):
# Class
# =====
- classIcon = SHARED.theme.getIcon(
- nwLabels.CLASS_ICON[nwItem.itemClass], nwLabels.CLASS_COLOR[nwItem.itemClass]
- )
+ classIcon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[nwItem.itemClass], "root")
self.classIcon.setPixmap(classIcon.pixmap(iPx, iPx))
self.classData.setText(trConst(nwLabels.CLASS_NAME[nwItem.itemClass]))
diff --git a/novelwriter/gui/projtree.py b/novelwriter/gui/projtree.py
index 61da1285..4b5490f8 100644
--- a/novelwriter/gui/projtree.py
+++ b/novelwriter/gui/projtree.py
@@ -369,11 +369,11 @@ class GuiProjectToolBar(QWidget):
self.tbAdd.setThemeIcon("add", "green")
self.tbMore.setThemeIcon("more_vertical")
- self.aAddEmpty.setIcon(SHARED.theme.getIcon("document"))
- self.aAddChap.setIcon(SHARED.theme.getIcon("document", "red"))
- self.aAddScene.setIcon(SHARED.theme.getIcon("document", "blue"))
- self.aAddNote.setIcon(SHARED.theme.getIcon("document", "yellow"))
- self.aAddFolder.setIcon(SHARED.theme.getIcon("folder"))
+ self.aAddEmpty.setIcon(SHARED.theme.getIcon("prj_document", "file"))
+ self.aAddChap.setIcon(SHARED.theme.getIcon("prj_chapter", "chapter"))
+ self.aAddScene.setIcon(SHARED.theme.getIcon("prj_scene", "scene"))
+ self.aAddNote.setIcon(SHARED.theme.getIcon("prj_note", "note"))
+ self.aAddFolder.setIcon(SHARED.theme.getIcon("prj_folder", "folder"))
self.buildTemplatesMenu()
self.buildQuickLinksMenu()
@@ -394,9 +394,7 @@ class GuiProjectToolBar(QWidget):
for tHandle, nwItem in SHARED.project.tree.iterRoots(None):
action = self.mQuick.addAction(nwItem.itemName)
action.setData(tHandle)
- action.setIcon(SHARED.theme.getIcon(
- nwLabels.CLASS_ICON[nwItem.itemClass], nwLabels.CLASS_COLOR[nwItem.itemClass]
- ))
+ action.setIcon(SHARED.theme.getIcon(nwLabels.CLASS_ICON[nwItem.itemClass], "root"))
action.triggered.connect(
qtLambda(self.projView.setSelectedHandle, tHandle, doScroll=True)
)
@@ -443,9 +441,7 @@ class GuiProjectToolBar(QWidget):
"""Build the rood folder menu."""
def addClass(itemClass: nwItemClass) -> None:
aNew = self.mAddRoot.addAction(trConst(nwLabels.CLASS_NAME[itemClass]))
- aNew.setIcon(SHARED.theme.getIcon(
- nwLabels.CLASS_ICON[itemClass], nwLabels.CLASS_COLOR[itemClass]
- ))
+ aNew.setIcon(SHARED.theme.getIcon(nwLabels.CLASS_ICON[itemClass], "root"))
aNew.triggered.connect(
qtLambda(self.projTree.newTreeItem, nwItemType.ROOT, itemClass)
)
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index 6bba79a6..924ec88c 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -260,6 +260,17 @@ class GuiTheme:
self.iconCache.setIconColor("blue", self._parseColour(parser, sec, "blue"))
self.iconCache.setIconColor("purple", self._parseColour(parser, sec, "purple"))
+ # Project
+ sec = "Project"
+ if parser.has_section(sec):
+ self.iconCache.setIconColor("root", self._parseColour(parser, sec, "root"))
+ self.iconCache.setIconColor("folder", self._parseColour(parser, sec, "folder"))
+ self.iconCache.setIconColor("file", self._parseColour(parser, sec, "file"))
+ self.iconCache.setIconColor("title", self._parseColour(parser, sec, "title"))
+ self.iconCache.setIconColor("chapter", self._parseColour(parser, sec, "chapter"))
+ self.iconCache.setIconColor("scene", self._parseColour(parser, sec, "scene"))
+ self.iconCache.setIconColor("note", self._parseColour(parser, sec, "note"))
+
# Palette
sec = "Palette"
if parser.has_section(sec):
@@ -648,20 +659,27 @@ class GuiIcons:
color = "default"
if tType == nwItemType.ROOT:
name = nwLabels.CLASS_ICON[tClass]
- color = nwLabels.CLASS_COLOR[tClass]
+ color = "root"
elif tType == nwItemType.FOLDER:
- name = "folder"
+ name = "prj_folder"
+ color = "folder"
elif tType == nwItemType.FILE:
- name = "document"
if tLayout == nwItemLayout.DOCUMENT:
if hLevel == "H1":
- color = "green"
+ name = "prj_title"
+ color = "title"
elif hLevel == "H2":
- color = "red"
+ name = "prj_chapter"
+ color = "chapter"
elif hLevel == "H3":
- color = "blue"
+ name = "prj_scene"
+ color = "scene"
+ else:
+ name = "prj_document"
+ color = "file"
elif tLayout == nwItemLayout.NOTE:
- color = "yellow"
+ name = "prj_note"
+ color = "note"
if name is None:
return self._noIcon
@@ -672,11 +690,11 @@ class GuiIcons:
if not self._headerDec:
iPx = self.mainTheme.baseIconHeight
self._headerDec = [
- self._generateDecoration("default", iPx, 0),
- self._generateDecoration("green", iPx, 0),
- self._generateDecoration("red", iPx, 1),
- self._generateDecoration("blue", iPx, 2),
- self._generateDecoration("default", iPx, 3),
+ self._generateDecoration("file", iPx, 0),
+ self._generateDecoration("title", iPx, 0),
+ self._generateDecoration("chapter", iPx, 1),
+ self._generateDecoration("scene", iPx, 2),
+ self._generateDecoration("file", iPx, 3),
]
return self._headerDec[minmax(hLevel, 0, 4)]
@@ -685,12 +703,12 @@ class GuiIcons:
if not self._headerDecNarrow:
iPx = self.mainTheme.baseIconHeight
self._headerDecNarrow = [
- self._generateDecoration("default", iPx, 0),
- self._generateDecoration("green", iPx, 0),
- self._generateDecoration("red", iPx, 0),
- self._generateDecoration("blue", iPx, 0),
- self._generateDecoration("default", iPx, 0),
- self._generateDecoration("yellow", iPx, 0),
+ self._generateDecoration("file", iPx, 0),
+ self._generateDecoration("title", iPx, 0),
+ self._generateDecoration("chapter", iPx, 0),
+ self._generateDecoration("scene", iPx, 0),
+ self._generateDecoration("file", iPx, 0),
+ self._generateDecoration("note", iPx, 0),
]
return self._headerDecNarrow[minmax(hLevel, 0, 5)]
diff --git a/novelwriter/tools/lipsum.py b/novelwriter/tools/lipsum.py
index 1ca20005..df02d82d 100644
--- a/novelwriter/tools/lipsum.py
+++ b/novelwriter/tools/lipsum.py
@@ -60,7 +60,7 @@ class GuiLipsum(NDialog):
# Icon
self.docIcon = QLabel(self)
- self.docIcon.setPixmap(SHARED.theme.getPixmap("document", (nPx, nPx), "blue"))
+ self.docIcon.setPixmap(SHARED.theme.getPixmap("text", (nPx, nPx), "blue"))
self.leftBox = QVBoxLayout()
self.leftBox.setSpacing(vSp)
diff --git a/novelwriter/tools/manussettings.py b/novelwriter/tools/manussettings.py
index ab9cb041..c0202e2f 100644
--- a/novelwriter/tools/manussettings.py
+++ b/novelwriter/tools/manussettings.py
@@ -459,13 +459,13 @@ class _FilterTab(NFixedPage):
self.filterOpt.clear()
self.filterOpt.addLabel(self._build.getLabel("filter"))
self.filterOpt.addItem(
- SHARED.theme.getIcon("document", "blue"),
+ SHARED.theme.getIcon("prj_scene", "scene"),
self._build.getLabel("filter.includeNovel"),
"doc:filter.includeNovel",
default=self._build.getBool("filter.includeNovel")
)
self.filterOpt.addItem(
- SHARED.theme.getIcon("document", "yellow"),
+ SHARED.theme.getIcon("prj_note", "note"),
self._build.getLabel("filter.includeNotes"),
"doc:filter.includeNotes",
default=self._build.getBool("filter.includeNotes")
diff --git a/pkgutils.py b/pkgutils.py
index 1e714351..060a1220 100755
--- a/pkgutils.py
+++ b/pkgutils.py
@@ -344,7 +344,7 @@ def buildIconTheme(args: argparse.Namespace) -> None:
iconsDir = CURR_DIR / "novelwriter" / "assets" / "icons"
style = args.style
- if style == "material":
+ if style in ("all", "material"):
processMaterialIcons(workDir, iconsDir, {
"material_rounded_thin": {
"name": "Material Symbols - Rounded Thin",
diff --git a/setup/debian/copyright b/setup/debian/copyright
index dfa36a1f..2b2a3300 100644
--- a/setup/debian/copyright
+++ b/setup/debian/copyright
@@ -19,32 +19,17 @@ License: GPL-3.0-or-later
You should have received a copy of the GNU General Public License
along with this program. If not, see .
-Files: novelwriter/assets/icons/typicons_*.svg
-Copyright: 2019, Stephen Hutchings
-License: CC-BY-SA-4.0
- This work is licensed under the Creative Commons Attribution-ShareAlike 4.0
- International License. To view a copy of this license, visit
- http://creativecommons.org/licenses/by-sa/4.0/ or send a letter to Creative
- Commons, PO Box 1866, Mountain View, CA 94042, USA.
+Files: novelwriter/assets/icons/material_*
+Copyright: Google Inc
+License: Apache-2.0
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
.
- Share — copy and redistribute the material in any medium or format
+ http://www.apache.org/licenses/LICENSE-2.0
.
- Adapt — remix, transform, and build upon the material for any purpose, even
- commercially. This license is acceptable for Free Cultural Works. The licensor
- cannot revoke these freedoms as long as you follow the license terms.
- .
- Attribution — You must give appropriate credit, provide a link to the license,
- and indicate if changes were made. You may do so in any reasonable manner, but
- not in any way that suggests the licensor endorses you or your use.
- .
- ShareAlike — If you remix, transform, or build upon the material, you must
- distribute your contributions under the same license as the original.
- No additional restrictions — You may not apply legal terms or technological
- measures that legally restrict others from doing anything the license permits.
- .
- Notices: You do not have to comply with the license for elements of the
- material in the public domain or where your use is permitted by an applicable
- exception or limitation. No warranties are given. The license may not give you
- all of the permissions necessary for your intended use. For example, other
- rights such as publicity, privacy, or moral rights may limit how you use the
- material.
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
diff --git a/utils/material_icons.py b/utils/material_icons.py
index 4e15371f..0b4963ac 100644
--- a/utils/material_icons.py
+++ b/utils/material_icons.py
@@ -27,8 +27,6 @@ from pathlib import Path
from lxml import etree
MATERIAL_REPO = "https://github.com/google/material-design-icons.git"
-GRADE = ""
-
ICON_MAP = {
"alert_error": "error",
"alert_info": "info",
@@ -48,10 +46,17 @@ ICON_MAP = {
"cls_trash": "delete",
"cls_world": "globe",
+ "prj_folder": "folder",
+ "prj_document": "news",
+ "prj_title": "news",
+ "prj_chapter": "news",
+ "prj_scene": "news",
+ "prj_note": "sticky_note_2",
+
"fmt_bold": "format_bold",
"fmt_italic": "format_italic",
"fmt_mark": "format_ink_highlighter",
- "fmt_strike": "format_strikethrough",
+ "fmt_strike": "strikethrough_s",
"fmt_subscript": "subscript",
"fmt_superscript": "superscript",
"fmt_underline": "format_underlined",
@@ -76,7 +81,7 @@ ICON_MAP = {
"bookmarks": "bookmarks",
"browse": "folder_open",
"cancel": "cancel",
- "checked": "select_check_box",
+ "checked": "check_box",
"chevron_down": "keyboard_arrow_down",
"chevron_left": "arrow_back_ios",
"chevron_right": "arrow_forward_ios",
@@ -84,10 +89,10 @@ ICON_MAP = {
"close": "close",
"copy": "content_copy",
"document_add": "note_add",
- "document": "description",
+ "document": "docs",
"edit": "edit",
"exclude": "do_not_disturb_on",
- "export": "share_windows",
+ "export": "file_export",
"filter": "filter_alt",
"fit_height": "fit_page_height",
"fit_width": "fit_page_width",
@@ -109,7 +114,7 @@ ICON_MAP = {
"noncheckable": "indeterminate_check_box",
"novel_view": "book_4_spark",
"open": "open_in_new",
- "outline": "table",
+ "outline": "summarize",
"panel": "dock_to_bottom",
"pin": "keep",
"project_copy": "folder_copy",
@@ -121,6 +126,7 @@ ICON_MAP = {
"settings": "settings",
"star": "star",
"stats": "bar_chart",
+ "text": "subject",
"timer_off": "timer_off",
"timer": "timer",
"unchecked": "disabled_by_default",
@@ -161,8 +167,8 @@ def processMaterialIcons(workDir: Path, iconsDir: Path, jobs: dict) -> None:
icons.write("# This file is automatically generated. Do not edit.\n\n")
icons.write("# Meta\n")
icons.write(f"meta:name = {name}\n")
- icons.write("meta:author = Google\n")
- icons.write("meta:license = Apache License Version 2.0\n")
+ icons.write("meta:author = Google Inc\n")
+ icons.write("meta:license = Apache 2.0\n")
icons.write("\n")
icons.write("# Icons\n")
iconSrc = srcRepo / "symbols" / "web"
From a6fde426a7e36cd4f8143e810672d521337491e5 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Wed, 8 Jan 2025 22:22:53 +0100
Subject: [PATCH 14/18] Add override settings for project tree icon colours
---
novelwriter/assets/themes/dracula.conf | 2 +-
novelwriter/config.py | 11 +++++---
novelwriter/constants.py | 11 ++++++++
novelwriter/dialogs/preferences.py | 37 ++++++++++++++++++--------
novelwriter/gui/theme.py | 34 +++++++++++++++++++++--
5 files changed, 78 insertions(+), 17 deletions(-)
diff --git a/novelwriter/assets/themes/dracula.conf b/novelwriter/assets/themes/dracula.conf
index 5bcd14f3..d874e832 100644
--- a/novelwriter/assets/themes/dracula.conf
+++ b/novelwriter/assets/themes/dracula.conf
@@ -29,7 +29,7 @@ orange = 255, 184, 108
yellow = 241, 250, 140
green = 80, 250, 123
aqua = 139, 233, 253
-blue = 139, 233, 253
+blue = 147, 207, 249
purple = 189, 147, 249
[Project]
diff --git a/novelwriter/config.py b/novelwriter/config.py
index 697dd711..1e173da3 100644
--- a/novelwriter/config.py
+++ b/novelwriter/config.py
@@ -114,7 +114,6 @@ class Config:
self.guiLocale = self._qLocale.name()
self.guiTheme = "default" # GUI theme
self.guiSyntax = "default_light" # Syntax theme
- self.guiIcons = "material_rounded_normal" # Icons theme
self.guiFont = QFont() # Main GUI font
self.guiScale = 1.0 # Set automatically by Theme class
self.hideVScroll = False # Hide vertical scroll bars on main widgets
@@ -122,6 +121,10 @@ class Config:
self.lastNotes = "0x0" # The latest release notes that have been shown
self.nativeFont = True # Use native font dialog
+ # Icons
+ self.iconTheme = "material_rounded_normal" # Icons theme
+ self.iconColTree = "theme" # Project tree icon colours
+
# Size Settings
self._mainWinSize = [1200, 650] # Last size of the main GUI window
self._welcomeSize = [800, 550] # Last size of the welcome window
@@ -606,7 +609,8 @@ class Config:
self.setGuiFont(conf.rdStr(sec, "font", ""))
self.guiTheme = conf.rdStr(sec, "theme", self.guiTheme)
self.guiSyntax = conf.rdStr(sec, "syntax", self.guiSyntax)
- self.guiIcons = conf.rdStr(sec, "icons", self.guiIcons)
+ self.iconTheme = conf.rdStr(sec, "icons", self.iconTheme)
+ self.iconColTree = conf.rdStr(sec, "iconcoltree", self.iconColTree)
self.guiLocale = conf.rdStr(sec, "localisation", self.guiLocale)
self.hideVScroll = conf.rdBool(sec, "hidevscroll", self.hideVScroll)
self.hideHScroll = conf.rdBool(sec, "hidehscroll", self.hideHScroll)
@@ -718,7 +722,8 @@ class Config:
"font": self.guiFont.toString(),
"theme": str(self.guiTheme),
"syntax": str(self.guiSyntax),
- "icons": str(self.guiIcons),
+ "icons": str(self.iconTheme),
+ "iconcoltree": str(self.iconColTree),
"localisation": str(self.guiLocale),
"hidevscroll": str(self.hideVScroll),
"hidehscroll": str(self.hideHScroll),
diff --git a/novelwriter/constants.py b/novelwriter/constants.py
index bdedab10..e908cb20 100644
--- a/novelwriter/constants.py
+++ b/novelwriter/constants.py
@@ -426,6 +426,17 @@ class nwLabels:
"Letter": (215.9, 279.4),
"Custom": (-1.0, -1.0),
}
+ THEME_COLORS = {
+ "theme": QT_TRANSLATE_NOOP("Constant", "Theme Colours"),
+ "default": QT_TRANSLATE_NOOP("Constant", "No Colours"),
+ "red": QT_TRANSLATE_NOOP("Constant", "Red"),
+ "orange": QT_TRANSLATE_NOOP("Constant", "Orange"),
+ "yellow": QT_TRANSLATE_NOOP("Constant", "Yellow"),
+ "green": QT_TRANSLATE_NOOP("Constant", "Green"),
+ "aqua": QT_TRANSLATE_NOOP("Constant", "Aqua"),
+ "blue": QT_TRANSLATE_NOOP("Constant", "Blue"),
+ "purple": QT_TRANSLATE_NOOP("Constant", "Purple"),
+ }
class nwHeadFmt:
diff --git a/novelwriter/dialogs/preferences.py b/novelwriter/dialogs/preferences.py
index 8421acf5..9f6de15a 100644
--- a/novelwriter/dialogs/preferences.py
+++ b/novelwriter/dialogs/preferences.py
@@ -35,7 +35,7 @@ from PyQt5.QtWidgets import (
from novelwriter import CONFIG, SHARED
from novelwriter.common import compact, describeFont, uniqueCompact
-from novelwriter.constants import nwUnicode
+from novelwriter.constants import nwLabels, nwUnicode, trConst
from novelwriter.dialogs.quotes import GuiQuoteSelect
from novelwriter.extensions.configlayout import NColourLabel, NScrollableForm
from novelwriter.extensions.modified import (
@@ -177,17 +177,29 @@ class GuiPreferences(NDialog):
)
# Icon Theme
- self.guiIcons = NComboBox(self)
- self.guiIcons.setMinimumWidth(minWidth)
+ self.iconTheme = NComboBox(self)
+ self.iconTheme.setMinimumWidth(minWidth)
for theme, name in SHARED.theme.iconCache.listThemes():
- self.guiIcons.addItem(name, theme)
- self.guiIcons.setCurrentData(CONFIG.guiIcons, "material_rounded_bold")
+ self.iconTheme.addItem(name, theme)
+ self.iconTheme.setCurrentData(CONFIG.iconTheme, "material_rounded_bold")
self.mainForm.addRow(
- self.tr("Icon theme"), self.guiIcons,
+ self.tr("Icon theme"), self.iconTheme,
self.tr("User interface icon theme."), stretch=(3, 2)
)
+ # Tree Icon Colours
+ self.iconColTree = NComboBox(self)
+ self.iconColTree.setMinimumWidth(minWidth)
+ for key, label in nwLabels.THEME_COLORS.items():
+ self.iconColTree.addItem(trConst(label), key)
+ self.iconColTree.setCurrentData(CONFIG.iconColTree, "theme")
+
+ self.mainForm.addRow(
+ self.tr("Project tree icon colours"), self.iconColTree,
+ self.tr("Override colours for project icons."), stretch=(3, 2)
+ )
+
# Application Font Family
self.guiFont = QLineEdit(self)
self.guiFont.setReadOnly(True)
@@ -912,18 +924,21 @@ class GuiPreferences(NDialog):
refreshTree = False
# Appearance
- guiLocale = self.guiLocale.currentData()
- guiTheme = self.guiTheme.currentData()
- guiIcons = self.guiIcons.currentData()
+ guiLocale = self.guiLocale.currentData()
+ guiTheme = self.guiTheme.currentData()
+ iconTheme = self.iconTheme.currentData()
+ iconColTree = self.iconColTree.currentData()
updateTheme |= CONFIG.guiTheme != guiTheme
- updateTheme |= CONFIG.guiIcons != guiIcons
+ updateTheme |= CONFIG.iconTheme != iconTheme
+ updateTheme |= CONFIG.iconColTree != iconColTree
needsRestart |= CONFIG.guiLocale != guiLocale
needsRestart |= CONFIG.guiFont != self._guiFont
CONFIG.guiLocale = guiLocale
CONFIG.guiTheme = guiTheme
- CONFIG.guiIcons = guiIcons
+ CONFIG.iconTheme = iconTheme
+ CONFIG.iconColTree = iconColTree
CONFIG.hideVScroll = self.hideVScroll.isChecked()
CONFIG.hideHScroll = self.hideHScroll.isChecked()
CONFIG.nativeFont = self.nativeFont.isChecked()
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index 924ec88c..4eef28e8 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -318,7 +318,7 @@ class GuiTheme:
)
# Load icons after theme is parsed
- self.iconCache.loadTheme(CONFIG.guiIcons)
+ self.iconCache.loadTheme(CONFIG.iconTheme)
# Apply styles
QApplication.setPalette(self._guiPalette)
@@ -542,8 +542,27 @@ class GuiIcons:
def clear(self) -> None:
"""Clear the icon cache."""
+ text = QApplication.palette().windowText().color()
+ default = text.name(QColor.NameFormat.HexRgb).encode("utf-8")
+
self._svgData = {}
- self._svgColours = {}
+ self._svgColours = {
+ "default": default,
+ "red": b"#ff0000",
+ "orange": b"#ff7f00",
+ "yellow": b"#ffff00",
+ "green": b"#00ff00",
+ "aqua": b"#00ffff",
+ "blue": b"#0000ff",
+ "purple": b"#ff00ff",
+ "root": b"#0000ff",
+ "folder": b"#ffff00",
+ "file": default,
+ "title": b"#00ff00",
+ "chapter": b"#ff0000",
+ "scene": b"#0000ff",
+ "note": b"#ffff00",
+ }
self._qIcons = {}
self._headerDec = []
self._headerDecNarrow = []
@@ -583,6 +602,17 @@ class GuiIcons:
logException()
return False
+ # Set colour overrides for project item icons
+ if (override := CONFIG.iconColTree) != "theme":
+ color = self._svgColours.get(override, b"#000000")
+ self._svgColours["root"] = color
+ self._svgColours["folder"] = color
+ self._svgColours["file"] = color
+ self._svgColours["title"] = color
+ self._svgColours["chapter"] = color
+ self._svgColours["scene"] = color
+ self._svgColours["note"] = color
+
return True
def setIconColor(self, key: str, color: QColor) -> None:
From c3fc1d4e5a04bb6dd50242ec1686613676877a82 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Fri, 10 Jan 2025 02:24:24 +0100
Subject: [PATCH 15/18] Update tests
---
novelwriter/gui/theme.py | 1 -
tests/reference/baseConfig_novelwriter.conf | 4 +-
tests/test_gui/test_gui_theme.py | 103 ++++++++++++--------
3 files changed, 65 insertions(+), 43 deletions(-)
diff --git a/novelwriter/gui/theme.py b/novelwriter/gui/theme.py
index 4eef28e8..6f33108b 100644
--- a/novelwriter/gui/theme.py
+++ b/novelwriter/gui/theme.py
@@ -835,6 +835,5 @@ def _loadIconName(path: Path) -> str:
except Exception:
logger.error("Could not load file: %s", path)
logException()
- return ""
return ""
diff --git a/tests/reference/baseConfig_novelwriter.conf b/tests/reference/baseConfig_novelwriter.conf
index 3bd03bbe..c4cdca5c 100644
--- a/tests/reference/baseConfig_novelwriter.conf
+++ b/tests/reference/baseConfig_novelwriter.conf
@@ -1,10 +1,12 @@
[Meta]
-timestamp = 2024-12-29 17:30:10
+timestamp = 2025-01-10 02:00:06
[Main]
font =
theme = default
syntax = default_light
+icons = material_rounded_normal
+iconcoltree = theme
localisation = en_GB
hidevscroll = False
hidehscroll = False
diff --git a/tests/test_gui/test_gui_theme.py b/tests/test_gui/test_gui_theme.py
index b4a45659..e8cc42ee 100644
--- a/tests/test_gui/test_gui_theme.py
+++ b/tests/test_gui/test_gui_theme.py
@@ -276,7 +276,7 @@ def testGuiTheme_Syntax(qtbot, monkeypatch, nwGUI):
@pytest.mark.gui
-def testGuiTheme_IconThemes(qtbot, caplog, monkeypatch, tstPaths):
+def testGuiTheme_IconThemes(qtbot, caplog, monkeypatch, nwGUI, tstPaths):
"""Test the icon cache class."""
iconCache = SHARED.theme.iconCache
@@ -289,43 +289,64 @@ def testGuiTheme_IconThemes(qtbot, caplog, monkeypatch, tstPaths):
# Check handling of unreadable file
with monkeypatch.context() as mp:
mp.setattr("builtins.open", causeOSError)
- assert iconCache.loadTheme("typicons_dark") is False
-
- # Load a broken theme file
- iconsDir = tstPaths.cnfDir / "icons"
- testIcons = iconsDir / "testicons"
- testIcons.mkdir()
- writeFile(testIcons / "icons.conf", (
- "[Main]\n"
- "name = Test Icons\n"
- "\n"
- "[Map]\n"
- "add = add.svg\n"
- "stuff = stuff.svg\n"
- ))
-
- iconPath = iconCache._iconPath
- iconCache._iconPath = tstPaths.cnfDir / "icons"
-
- caplog.clear()
- assert iconCache.loadTheme("testicons") is True
- assert "Unknown icon name 'stuff' in config file" in caplog.text
- assert "Icon file 'add.svg' not in theme folder" in caplog.text
-
- iconCache._iconPath = iconPath
+ assert iconCache.loadTheme("material_rounded_normal") is False
# Load working theme file
- assert iconCache.loadTheme("typicons_dark") is True
- assert "add" in iconCache._themeMap
+ assert iconCache.loadTheme("material_rounded_normal") is True
+ assert iconCache.themeName == "Material Symbols - Rounded Medium"
+
+ # Load with project colour override
+ purple = iconCache._svgColours["purple"]
+ assert iconCache._svgColours["root"] != purple
+ assert iconCache._svgColours["folder"] != purple
+ assert iconCache._svgColours["file"] != purple
+ assert iconCache._svgColours["title"] != purple
+ assert iconCache._svgColours["chapter"] != purple
+ assert iconCache._svgColours["scene"] != purple
+ assert iconCache._svgColours["note"] != purple
+
+ CONFIG.iconColTree = "purple"
+ assert iconCache.loadTheme("material_rounded_normal") is True
+ assert iconCache._svgColours["root"] == purple
+ assert iconCache._svgColours["folder"] == purple
+ assert iconCache._svgColours["file"] == purple
+ assert iconCache._svgColours["title"] == purple
+ assert iconCache._svgColours["chapter"] == purple
+ assert iconCache._svgColours["scene"] == purple
+ assert iconCache._svgColours["note"] == purple
+
+ # Change some colours
+ iconCache.setIconColor("root", QColor(255, 255, 255))
+ assert iconCache._svgColours["root"] != purple
+ assert iconCache._svgColours["root"] == b"#ffffff"
+
+ # List Themes
+ # ===========
+
+ # Load error returns empty list
+ with monkeypatch.context() as mp:
+ mp.setattr("builtins.open", causeOSError)
+ themes = iconCache.listThemes()
+ assert themes == []
+
+ # Successful read
+ themes = iconCache.listThemes()
+ assert len(themes) > 1
+ assert "material_rounded_normal" in dict(themes)
+
+ # Load error doesn't matter on second read since list is cached
+ with monkeypatch.context() as mp:
+ mp.setattr("builtins.open", causeOSError)
+ assert iconCache.listThemes() == themes
# qtbot.stop()
@pytest.mark.gui
-def testGuiTheme_LoadIcons(qtbot):
+def testGuiTheme_LoadIcons(qtbot, nwGUI):
"""Test the icon cache class."""
iconCache = SHARED.theme.iconCache
- assert iconCache.loadTheme("typicons_dark") is True
+ assert iconCache.loadTheme("material_rounded_normal") is True
# Load Icons
# ==========
@@ -376,47 +397,47 @@ def testGuiTheme_LoadIcons(qtbot):
# Root -> Not Null
assert iconCache.getItemIcon(
nwItemType.ROOT, nwItemClass.NOVEL, nwItemLayout.NO_LAYOUT, hLevel="H0"
- ) == iconCache.getIcon(nwLabels.CLASS_ICON[nwItemClass.NOVEL])
+ ) == iconCache.getIcon(nwLabels.CLASS_ICON[nwItemClass.NOVEL], "root")
# Folder -> Not Null
assert iconCache.getItemIcon(
nwItemType.FOLDER, nwItemClass.NOVEL, nwItemLayout.NO_LAYOUT, hLevel="H0"
- ) == iconCache.getIcon("proj_folder")
+ ) == iconCache.getIcon("prj_folder", "folder")
# Document H0 -> Not Null
assert iconCache.getItemIcon(
nwItemType.FILE, nwItemClass.NOVEL, nwItemLayout.NO_LAYOUT, hLevel="H0"
- ) == iconCache.getIcon("proj_document")
+ ) == iconCache._noIcon
# Document H1 -> Not Null
assert iconCache.getItemIcon(
nwItemType.FILE, nwItemClass.NOVEL, nwItemLayout.DOCUMENT, hLevel="H1"
- ) == iconCache.getIcon("proj_title")
+ ) == iconCache.getIcon("prj_title", "title")
# Document H2 -> Not Null
assert iconCache.getItemIcon(
nwItemType.FILE, nwItemClass.NOVEL, nwItemLayout.DOCUMENT, hLevel="H2"
- ) == iconCache.getIcon("proj_chapter")
+ ) == iconCache.getIcon("prj_chapter", "chapter")
# Document H3 -> Not Null
assert iconCache.getItemIcon(
nwItemType.FILE, nwItemClass.NOVEL, nwItemLayout.DOCUMENT, hLevel="H3"
- ) == iconCache.getIcon("proj_scene")
+ ) == iconCache.getIcon("prj_scene", "scene")
# Document H4 -> Not Null
assert iconCache.getItemIcon(
nwItemType.FILE, nwItemClass.NOVEL, nwItemLayout.DOCUMENT, hLevel="H4"
- ) == iconCache.getIcon("proj_section")
+ ) == iconCache.getIcon("prj_document", "file")
# Document H5 -> Not Null
assert iconCache.getItemIcon(
- nwItemType.FILE, nwItemClass.NOVEL, nwItemLayout.NO_LAYOUT, hLevel="H4"
- ) == iconCache.getIcon("proj_document")
+ nwItemType.FILE, nwItemClass.NOVEL, nwItemLayout.DOCUMENT, hLevel="H5"
+ ) == iconCache.getIcon("prj_document", "file")
# Note -> Not Null
assert iconCache.getItemIcon(
nwItemType.FILE, nwItemClass.NOVEL, nwItemLayout.NOTE, hLevel="H5"
- ) == iconCache.getIcon("proj_note")
+ ) == iconCache.getIcon("prj_note", "note")
# No Type -> Null
assert iconCache.getItemIcon(
@@ -427,10 +448,10 @@ def testGuiTheme_LoadIcons(qtbot):
@pytest.mark.gui
-def testGuiTheme_LoadDecorations(qtbot, monkeypatch):
+def testGuiTheme_LoadDecorations(qtbot, monkeypatch, nwGUI):
"""Test the icon cache class."""
iconCache = SHARED.theme.iconCache
- assert iconCache.loadTheme("typicons_dark") is True
+ assert iconCache.loadTheme("material_rounded_normal") is True
# Load Decorations
# ================
From 9e9c24d8c0ac3d6353f2d29a28788a923d29541e Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Fri, 10 Jan 2025 03:01:25 +0100
Subject: [PATCH 16/18] Drop lxml, it's not needed
---
utils/material_icons.py | 8 ++++----
1 file changed, 4 insertions(+), 4 deletions(-)
diff --git a/utils/material_icons.py b/utils/material_icons.py
index 0b4963ac..b57219d2 100644
--- a/utils/material_icons.py
+++ b/utils/material_icons.py
@@ -23,9 +23,9 @@ from __future__ import annotations
import subprocess
from pathlib import Path
+from xml.etree import ElementTree as ET
-from lxml import etree
-
+ET.register_namespace("", "http://www.w3.org/2000/svg")
MATERIAL_REPO = "https://github.com/google/material-design-icons.git"
ICON_MAP = {
"alert_error": "error",
@@ -136,11 +136,11 @@ ICON_MAP = {
def _fixXml(svg: str) -> str:
"""Clean up the SVG XML and add needed fields."""
- xSvg = etree.fromstring(svg) # type: ignore
+ xSvg = ET.fromstring(svg)
xSvg.set("fill", "#000000")
xSvg.set("height", "128")
xSvg.set("width", "128")
- return etree.tostring(xSvg).decode()
+ return ET.tostring(xSvg).decode()
def processMaterialIcons(workDir: Path, iconsDir: Path, jobs: dict) -> None:
From acca753a7792ed20cf7b65f031c8136a7c5a6763 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Fri, 10 Jan 2025 12:22:05 +0100
Subject: [PATCH 17/18] Fix view panel theme update
---
novelwriter/gui/docviewerpanel.py | 11 +++--------
1 file changed, 3 insertions(+), 8 deletions(-)
diff --git a/novelwriter/gui/docviewerpanel.py b/novelwriter/gui/docviewerpanel.py
index f3c4359a..7bcb52b5 100644
--- a/novelwriter/gui/docviewerpanel.py
+++ b/novelwriter/gui/docviewerpanel.py
@@ -104,11 +104,12 @@ class GuiDocViewerPanel(QWidget):
self.optsButton.setThemeIcon("more_vertical")
self.optsButton.setStyleSheet(SHARED.theme.getStyleSheet(STYLES_MIN_TOOLBUTTON))
self.mainTabs.setStyleSheet(SHARED.theme.getStyleSheet(STYLES_FLAT_TABS))
- self.updateHandle(self._lastHandle)
if updateTabs:
self.tabBackRefs.updateTheme()
+ self.tabBackRefs.refreshContent(self._lastHandle)
for tab in self.kwTabs.values():
tab.updateTheme()
+ self._loadAllTags()
return
def openProjectTasks(self) -> None:
@@ -410,9 +411,7 @@ class _ViewPanelKeyWords(QTreeWidget):
treeHeader.setSectionsMovable(False)
# Cache Icons Locally
- self._classIcon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[itemClass], "root")
- self._editIcon = SHARED.theme.getIcon("edit", "green")
- self._viewIcon = SHARED.theme.getIcon("view", "blue")
+ self.updateTheme()
# Signals
self.clicked.connect(self._treeItemClicked)
@@ -425,10 +424,6 @@ class _ViewPanelKeyWords(QTreeWidget):
self._classIcon = SHARED.theme.getIcon(nwLabels.CLASS_ICON[self._class], "root")
self._editIcon = SHARED.theme.getIcon("edit", "green")
self._viewIcon = SHARED.theme.getIcon("view", "blue")
- for i in range(self.topLevelItemCount()):
- if item := self.topLevelItem(i):
- item.setIcon(self.C_EDIT, self._editIcon)
- item.setIcon(self.C_VIEW, self._viewIcon)
return
def countEntries(self) -> int:
From 591a17eb19b099ceb1e354443f5bf1d122f4d016 Mon Sep 17 00:00:00 2001
From: Veronica Berglyd Olsen <1619840+vkbo@users.noreply.github.com>
Date: Fri, 10 Jan 2025 12:30:28 +0100
Subject: [PATCH 18/18] Update license info
---
CREDITS.md | 6 ++----
novelwriter/assets/text/credits_en.htm | 6 ++----
setup/iss_license.txt | 8 ++++----
3 files changed, 8 insertions(+), 12 deletions(-)
diff --git a/CREDITS.md b/CREDITS.md
index 39ff5f68..ef2b2224 100644
--- a/CREDITS.md
+++ b/CREDITS.md
@@ -54,7 +54,7 @@ The following libraries are dependencies of novelWriter:
Some of the assets bundled with novelWriter were adapted from the following sources:
-* **Typicons** icons by Stephen Hutchings (CC BY-SA 4.0)
+* **Material Symbols** icons by Google Inc (Apache 2.0)
* **Tomorrow** syntax themes by Chris Kempson (MIT License)
* **Owl** syntax themes by Sarah Drasner (MIT License)
* **Solarized** themes by Ethan Schoonover (MIT License)
@@ -64,11 +64,9 @@ Some of the assets bundled with novelWriter were adapted from the following sour
## Fonts
-The font used for the main novelWriter logo, mimetype and text banners is Pridi. Other fonts are
-used on buttons and icons.
+The font used for the main novelWriter logo, mimetype and text banners is Pridi.
* **Pridi** by Cadson Demak (Open Font License, Version 1.1)
-* **Source Sans Pro** by Paul D. Hunt (SIL Open Font License)
## Special Mentions
diff --git a/novelwriter/assets/text/credits_en.htm b/novelwriter/assets/text/credits_en.htm
index 6ca34707..aa90ae45 100644
--- a/novelwriter/assets/text/credits_en.htm
+++ b/novelwriter/assets/text/credits_en.htm
@@ -65,7 +65,7 @@ more contributions are listed on the project's Members page.
Some of the assets bundled with novelWriter were adapted from the following sources:
- - Typicons icons by Stephen Hutchings (CC BY-SA 4.0)
+ - Material Symbols icons by Google Inc (Apache 2.0)
- Tomorrow syntax themes by Chris Kempson (MIT License)
- Owl syntax themes by Sarah Drasner (MIT License)
- Solarized themes by Ethan Schoonover (MIT License)
@@ -76,12 +76,10 @@ more contributions are listed on the project's Members page.
Fonts
-The font used for the main novelWriter logo, mimetype and text banners is Pridi. Other fonts are
-used on buttons and icons.
+The font used for the main novelWriter logo, mimetype and text banners is Pridi.
- Pridi by Cadson Demak (Open Font License, Version 1.1)
- - Source Sans Pro by Paul D. Hunt (SIL Open Font License)
Special Mentions
diff --git a/setup/iss_license.txt b/setup/iss_license.txt
index f17d559d..63726dba 100644
--- a/setup/iss_license.txt
+++ b/setup/iss_license.txt
@@ -38,7 +38,7 @@ Copyright: Dimitri Merejkowsky
Website:
License: LGPL v2.1
-Typicons
-Copyright: Stephen Hutchings
-Website:
-License: CC BY-SA 4.0
+Material Symbols
+Copyright: Google Inc
+Website:
+License: Apache 2.0