Merge branch 'theme_fixes' of https://github.com/HeyMyian/novelWriter into theme_fixes

This commit is contained in:
HeyMyian
2025-09-02 21:02:40 +02:00
12 changed files with 26 additions and 18 deletions
+1
View File
@@ -445,6 +445,7 @@ def fontMatcher(font: QFont) -> QFont:
default Qt font matching algorithm doesn't handle well changing default Qt font matching algorithm doesn't handle well changing
application fonts at runtime. application fonts at runtime.
""" """
font.setStyleName(None) # Make sure no font style name is set from config, see #2502
info = QFontInfo(font) info = QFontInfo(font)
if (famRequest := font.family()) != (famActual := info.family()): if (famRequest := font.family()) != (famActual := info.family()):
logger.warning("Font mismatch: Requested '%s', but got '%s'", famRequest, famActual) logger.warning("Font mismatch: Requested '%s', but got '%s'", famRequest, famActual)
+1 -1
View File
@@ -202,7 +202,7 @@ class Config:
self.doJustify = False # Justify text self.doJustify = False # Justify text
self.showTabsNSpaces = False # Show tabs and spaces in editor self.showTabsNSpaces = False # Show tabs and spaces in editor
self.showLineEndings = False # Show line endings in editor self.showLineEndings = False # Show line endings in editor
self.showMultiSpaces = True # Highlight multiple spaces in the text self.showMultiSpaces = False # Highlight multiple spaces in the text
self.doReplace = True # Enable auto-replace as you type self.doReplace = True # Enable auto-replace as you type
self.doReplaceSQuote = True # Smart single quotes self.doReplaceSQuote = True # Smart single quotes
+1 -1
View File
@@ -701,7 +701,7 @@ class GuiPreferences(NDialog):
self.showMultiSpaces = NSwitch(self) self.showMultiSpaces = NSwitch(self)
self.showMultiSpaces.setChecked(CONFIG.showMultiSpaces) self.showMultiSpaces.setChecked(CONFIG.showMultiSpaces)
self.mainForm.addRow( self.mainForm.addRow(
self.tr("Highlight multiple or trailing spaces"), self.showMultiSpaces, self.tr("Highlight multiple spaces between words"), self.showMultiSpaces,
self.tr("Applies to the document editor only.") self.tr("Applies to the document editor only.")
) )
+4 -4
View File
@@ -141,7 +141,7 @@ class GuiDocHighlighter(QSyntaxHighlighter):
# Multiple or Trailing Spaces # Multiple or Trailing Spaces
if CONFIG.showMultiSpaces: if CONFIG.showMultiSpaces:
rxRule = re.compile(r"[ ]{2,}|[ ]*$", re.UNICODE) rxRule = re.compile(r"\s{2,}")
hlRule = { hlRule = {
0: self._hStyles["mspaces"], 0: self._hStyles["mspaces"],
} }
@@ -150,7 +150,7 @@ class GuiDocHighlighter(QSyntaxHighlighter):
self._cmnRules.append((rxRule, hlRule)) self._cmnRules.append((rxRule, hlRule))
# Non-Breaking Spaces # Non-Breaking Spaces
rxRule = re.compile(f"[{nwUnicode.U_NBSP}{nwUnicode.U_THNBSP}]+", re.UNICODE) rxRule = re.compile(f"[{nwUnicode.U_NBSP}{nwUnicode.U_THNBSP}]+")
hlRule = { hlRule = {
0: self._hStyles["nobreak"], 0: self._hStyles["nobreak"],
} }
@@ -239,7 +239,7 @@ class GuiDocHighlighter(QSyntaxHighlighter):
self._cmnRules.append((rxRule, hlRule)) self._cmnRules.append((rxRule, hlRule))
# Alignment Tags # Alignment Tags
rxRule = re.compile(r"(^>{1,2}|<{1,2}$)", re.UNICODE) rxRule = re.compile(r"(^>{1,2}|<{1,2}$)")
hlRule = { hlRule = {
1: self._hStyles["markup"], 1: self._hStyles["markup"],
} }
@@ -247,7 +247,7 @@ class GuiDocHighlighter(QSyntaxHighlighter):
self._txtRules.append((rxRule, hlRule)) self._txtRules.append((rxRule, hlRule))
# Auto-Replace Tags # Auto-Replace Tags
rxRule = re.compile(r"<(\S+?)>", re.UNICODE) rxRule = re.compile(r"<(\S+?)>")
hlRule = { hlRule = {
0: self._hStyles["replace"], 0: self._hStyles["replace"],
} }
-1
View File
@@ -124,7 +124,6 @@ markers = [
"base: Base classes tests", "base: Base classes tests",
"core: Core classes tests", "core: Core classes tests",
"gui: GUI classes tests", "gui: GUI classes tests",
"serial",
] ]
[tool.coverage.run] [tool.coverage.run]
+1
View File
@@ -18,6 +18,7 @@ if __name__ == "__main__":
args = parser.parse_args() args = parser.parse_args()
env = os.environ.copy() env = os.environ.copy()
env["QT_SCALE_FACTOR"] = "1.0"
cmd = [sys.executable, "-m", "pytest", "-vv"] cmd = [sys.executable, "-m", "pytest", "-vv"]
if args.o: if args.o:
+3 -3
View File
@@ -10,9 +10,9 @@ synchronisation tools. All text is saved as plain text files with a meta data he
project structure is stored in a single project XML file, and other meta data is primarily saved as project structure is stored in a single project XML file, and other meta data is primarily saved as
JSON files. JSON files.
The application is written with Python 3 (3.10+) using Qt6 and PyQt6 (5.10+). It is developed on The application is written with Python 3 using Qt6 and PyQt6. It is developed on Linux, but should
Linux, but should in principle work fine on other operating systems as well as long as dependencies in principle work fine on other operating systems as well as long as dependencies are met. It is
are met. It is regularly tested on Debian and Ubuntu Linux, Windows, and MacOS. regularly tested on Debian and Ubuntu Linux, Windows, and MacOS.
novelWriter is developed and maintained by [Veronica Berglyd Olsen](https://github.com/vkbo). novelWriter is developed and maintained by [Veronica Berglyd Olsen](https://github.com/vkbo).
+1 -1
View File
@@ -1,6 +1,6 @@
novelWriter License novelWriter License
Copyright (C) 2018-2025 Veronica Berglyd Olsen Copyright (C) Veronica Berglyd Olsen and novelWriter contributors
License: GPL v3+ <https://www.gnu.org/licenses/gpl-3.0.html> License: GPL v3+ <https://www.gnu.org/licenses/gpl-3.0.html>
This program is free software: you can redistribute it and/or modify This program is free software: you can redistribute it and/or modify
+2 -2
View File
@@ -1,5 +1,5 @@
[Meta] [Meta]
timestamp = 2025-06-14 17:03:01 timestamp = 2025-08-24 15:30:16
[Main] [Main]
font = font =
@@ -63,7 +63,7 @@ fmtpadthin = False
spellcheck = en spellcheck = en
showtabsnspaces = False showtabsnspaces = False
showlineendings = False showlineendings = False
showmultispaces = True showmultispaces = False
incnoteswcount = True incnoteswcount = True
showfullpath = True showfullpath = True
dialogstyle = 2 dialogstyle = 2
+5
View File
@@ -537,6 +537,11 @@ def testBaseCommon_fontMatcher(monkeypatch):
nonsense = QFont("nonesense", 10) nonsense = QFont("nonesense", 10)
assert fontMatcher(nonsense) is nonsense assert fontMatcher(nonsense) is nonsense
# Style is reset
nonsense.setStyleName("blabla")
assert nonsense.styleName() == "blabla"
assert fontMatcher(nonsense).styleName() == ""
# General font # General font
if len(QFontDatabase.families()) > 1: if len(QFontDatabase.families()) > 1:
fontOne = QFont(QFontDatabase.families()[0]) fontOne = QFont(QFontDatabase.families()[0])
+3 -3
View File
@@ -279,7 +279,7 @@ def testDlgPreferences_Settings(qtbot, monkeypatch, nwGUI, fncPath, tstPaths):
prefs.altDialogOpen.setText("%") # Symbol also tests for #2455 prefs.altDialogOpen.setText("%") # Symbol also tests for #2455
prefs.altDialogClose.setText("%") # Symbol also tests for #2455 prefs.altDialogClose.setText("%") # Symbol also tests for #2455
prefs.highlightEmph.setChecked(False) prefs.highlightEmph.setChecked(False)
prefs.showMultiSpaces.setChecked(False) prefs.showMultiSpaces.setChecked(True)
prefs._insertDialogLineSymbol(nwUnicode.U_ENDASH) prefs._insertDialogLineSymbol(nwUnicode.U_ENDASH)
assert prefs.dialogLine.text() == f"{nwUnicode.U_ENDASH} {nwUnicode.U_EMDASH}" assert prefs.dialogLine.text() == f"{nwUnicode.U_ENDASH} {nwUnicode.U_EMDASH}"
@@ -292,7 +292,7 @@ def testDlgPreferences_Settings(qtbot, monkeypatch, nwGUI, fncPath, tstPaths):
assert CONFIG.altDialogOpen == "" assert CONFIG.altDialogOpen == ""
assert CONFIG.altDialogClose == "" assert CONFIG.altDialogClose == ""
assert CONFIG.highlightEmph is True assert CONFIG.highlightEmph is True
assert CONFIG.showMultiSpaces is True assert CONFIG.showMultiSpaces is False
# Text Automation # Text Automation
prefs.doReplaceSQuote.setChecked(False) prefs.doReplaceSQuote.setChecked(False)
@@ -413,7 +413,7 @@ def testDlgPreferences_Settings(qtbot, monkeypatch, nwGUI, fncPath, tstPaths):
assert CONFIG.altDialogOpen == "%" assert CONFIG.altDialogOpen == "%"
assert CONFIG.altDialogClose == "%" assert CONFIG.altDialogClose == "%"
assert CONFIG.highlightEmph is False assert CONFIG.highlightEmph is False
assert CONFIG.showMultiSpaces is False assert CONFIG.showMultiSpaces is True
# Text Automation # Text Automation
assert CONFIG.doReplace is False assert CONFIG.doReplace is False
+4 -2
View File
@@ -431,11 +431,13 @@ def testGuiTheme_LoadIcons():
assert qIcon.isNull() is False assert qIcon.isNull() is False
# Load it as a pixmap with a size # Load it as a pixmap with a size
# If this part of the test fails, you may need to set the
# environment variable: QT_SCALE_FACTOR=1
qPix = iconCache.getPixmap("add", (50, 50)) qPix = iconCache.getPixmap("add", (50, 50))
assert isinstance(qPix, QPixmap) assert isinstance(qPix, QPixmap)
assert qPix.isNull() is False assert qPix.isNull() is False
assert qPix.width() == 50 assert qPix.width() == 50, "If this fails, make sure QT_SCALE_FACTOR=1"
assert qPix.height() == 50 assert qPix.height() == 50, "If this fails, make sure QT_SCALE_FACTOR=1"
# Load app icon # Load app icon
qIcon = iconCache.getIcon("novelwriter") qIcon = iconCache.getIcon("novelwriter")