Remove scaling and add slots to main config class

This commit is contained in:
Veronica Berglyd Olsen
2025-01-12 23:30:27 +01:00
parent 0728b35735
commit 717ade24e3
9 changed files with 87 additions and 127 deletions
+51 -73
View File
@@ -52,6 +52,31 @@ logger = logging.getLogger(__name__)
class Config:
__slots__ = (
"_confPath", "_dataPath", "_homePath", "_backPath", "_appPath", "_appRoot", "_hasError",
"_errData", "_nwLangPath", "_qtLangPath", "_qLocale", "_dLocale", "_dShortDate",
"_dShortDateTime", "_qtTrans", "_recentProjects", "_recentPaths", "_backupPath",
"appName", "appHandle", "pdfDocs", "guiLocale", "guiTheme", "guiSyntax", "guiFont",
"hideVScroll", "hideHScroll", "lastNotes", "nativeFont", "iconTheme", "iconColTree",
"iconColDocs", "mainWinSize", "welcomeWinSize", "prefsWinSize", "mainPanePos",
"viewPanePos", "outlinePanePos", "autoSaveProj", "autoSaveDoc", "emphLabels",
"backupOnClose", "askBeforeBackup", "textFont", "textWidth", "textMargin", "tabWidth",
"focusWidth", "hideFocusFooter", "showFullPath", "autoSelect", "doJustify",
"showTabsNSpaces", "showLineEndings", "showMultiSpaces", "doReplace", "doReplaceSQuote",
"doReplaceDQuote", "doReplaceDash", "doReplaceDots", "autoScroll", "autoScrollPos",
"scrollPastEnd", "dialogStyle", "allowOpenDial", "dialogLine", "narratorBreak",
"narratorDialog", "altDialogOpen", "altDialogClose", "highlightEmph", "stopWhenIdle",
"userIdleTime", "incNotesWCount", "fmtApostrophe", "fmtSQuoteOpen", "fmtSQuoteClose",
"fmtDQuoteOpen", "fmtDQuoteClose", "fmtPadBefore", "fmtPadAfter", "fmtPadThin",
"spellLanguage", "showViewerPanel", "showEditToolBar", "showSessionTime", "viewComments",
"viewSynopsis", "searchCase", "searchWord", "searchRegEx", "searchLoop", "searchNextFile",
"searchMatchCap", "searchProjCase", "searchProjWord", "searchProjRegEx", "verQtString",
"verQtValue", "verPyQtString", "verPyQtValue", "verPyString", "osType", "osLinux",
"osWindows", "osDarwin", "osUnknown", "hostName", "kernelVer", "isDebug", "memInfo",
"hasEnchant",
)
LANG_NW = 1
LANG_PROJ = 2
@@ -126,12 +151,12 @@ class Config:
self.iconColDocs = False # Keep theme colours on documents
# Size Settings
self._mainWinSize = [1200, 650] # Last size of the main GUI window
self._welcomeSize = [800, 550] # Last size of the welcome window
self._prefsWinSize = [700, 615] # Last size of the Preferences dialog
self._mainPanePos = [300, 800] # Last position of the main window splitter
self._viewPanePos = [500, 150] # Last position of the document viewer splitter
self._outlnPanePos = [500, 150] # Last position of the outline panel splitter
self.mainWinSize = [1200, 650] # Last size of the main GUI window
self.welcomeWinSize = [800, 550] # Last size of the welcome window
self.prefsWinSize = [700, 615] # Last size of the Preferences dialog
self.mainPanePos = [300, 800] # Last position of the main window splitter
self.viewPanePos = [500, 150] # Last position of the document viewer splitter
self.outlinePanePos = [500, 150] # Last position of the outline panel splitter
# Project Settings
self.autoSaveProj = 60 # Interval for auto-saving project, in seconds
@@ -269,30 +294,6 @@ class Config:
def recentProjects(self) -> RecentProjects:
return self._recentProjects
@property
def mainWinSize(self) -> list[int]:
return self._mainWinSize
@property
def welcomeWinSize(self) -> list[int]:
return self._welcomeSize
@property
def preferencesWinSize(self) -> list[int]:
return self._prefsWinSize
@property
def mainPanePos(self) -> list[int]:
return self._mainPanePos
@property
def viewPanePos(self) -> list[int]:
return self._viewPanePos
@property
def outlinePanePos(self) -> list[int]:
return self._outlnPanePos
##
# Getters
##
@@ -300,17 +301,9 @@ class Config:
def getTextWidth(self, focusMode: bool = False) -> int:
"""Get the text with for the correct editor mode."""
if focusMode:
return self.pxInt(max(self.focusWidth, 200))
return max(self.focusWidth, 200)
else:
return self.pxInt(max(self.textWidth, 200))
def getTextMargin(self) -> int:
"""Get the scaled text margin."""
return self.pxInt(max(self.textMargin, 0))
def getTabWidth(self) -> int:
"""Get the scaled tab width."""
return self.pxInt(max(self.tabWidth, 0))
return max(self.textWidth, 200)
##
# Setters
@@ -322,35 +315,20 @@ class Config:
adjust it a bit, and we don't want the main window to shrink or
grow each time the app is opened.
"""
if abs(self._mainWinSize[0] - width) > 5:
self._mainWinSize[0] = width
if abs(self._mainWinSize[1] - height) > 5:
self._mainWinSize[1] = height
if abs(self.mainWinSize[0] - width) > 5:
self.mainWinSize[0] = width
if abs(self.mainWinSize[1] - height) > 5:
self.mainWinSize[1] = height
return
def setWelcomeWinSize(self, width: int, height: int) -> None:
"""Set the size of the Preferences dialog window."""
self._welcomeSize = [width, height]
self.welcomeWinSize = [width, height]
return
def setPreferencesWinSize(self, width: int, height: int) -> None:
"""Set the size of the Preferences dialog window."""
self._prefsWinSize = [width, height]
return
def setMainPanePos(self, pos: list[int]) -> None:
"""Set the position of the main GUI splitter."""
self._mainPanePos = pos
return
def setViewPanePos(self, pos: list[int]) -> None:
"""Set the position of the viewer meta data splitter."""
self._viewPanePos = pos
return
def setOutlinePanePos(self, pos: list[int]) -> None:
"""Set the position of the outline details splitter."""
self._outlnPanePos = pos
self.prefsWinSize = [width, height]
return
def setLastPath(self, key: str, path: str | Path) -> None:
@@ -614,12 +592,12 @@ class Config:
# Sizes
sec = "Sizes"
self._mainWinSize = conf.rdIntList(sec, "mainwindow", self._mainWinSize)
self._welcomeSize = conf.rdIntList(sec, "welcome", self._welcomeSize)
self._prefsWinSize = conf.rdIntList(sec, "preferences", self._prefsWinSize)
self._mainPanePos = conf.rdIntList(sec, "mainpane", self._mainPanePos)
self._viewPanePos = conf.rdIntList(sec, "viewpane", self._viewPanePos)
self._outlnPanePos = conf.rdIntList(sec, "outlinepane", self._outlnPanePos)
self.mainWinSize = conf.rdIntList(sec, "mainwindow", self.mainWinSize)
self.welcomeWinSize = conf.rdIntList(sec, "welcome", self.welcomeWinSize)
self.prefsWinSize = conf.rdIntList(sec, "preferences", self.prefsWinSize)
self.mainPanePos = conf.rdIntList(sec, "mainpane", self.mainPanePos)
self.viewPanePos = conf.rdIntList(sec, "viewpane", self.viewPanePos)
self.outlinePanePos = conf.rdIntList(sec, "outlinepane", self.outlinePanePos)
# Project
sec = "Project"
@@ -728,12 +706,12 @@ class Config:
}
conf["Sizes"] = {
"mainwindow": self._packList(self._mainWinSize),
"welcome": self._packList(self._welcomeSize),
"preferences": self._packList(self._prefsWinSize),
"mainpane": self._packList(self._mainPanePos),
"viewpane": self._packList(self._viewPanePos),
"outlinepane": self._packList(self._outlnPanePos),
"mainwindow": self._packList(self.mainWinSize),
"welcome": self._packList(self.welcomeWinSize),
"preferences": self._packList(self.prefsWinSize),
"mainpane": self._packList(self.mainPanePos),
"viewpane": self._packList(self.viewPanePos),
"outlinepane": self._packList(self.outlinePanePos),
}
conf["Project"] = {
+1 -1
View File
@@ -59,7 +59,7 @@ class GuiPreferences(NDialog):
self.setObjectName("GuiPreferences")
self.setWindowTitle(self.tr("Preferences"))
self.setMinimumSize(CONFIG.pxInt(600), CONFIG.pxInt(500))
self.resize(*CONFIG.preferencesWinSize)
self.resize(*CONFIG.prefsWinSize)
# Title
self.titleLabel = NColourLabel(
+2 -2
View File
@@ -331,7 +331,7 @@ class GuiDocEditor(QPlainTextEdit):
# Due to cursor visibility, a part of the margin must be
# allocated to the document itself. See issue #1112.
self._qDocument.setDocumentMargin(4)
self._vpMargin = max(CONFIG.getTextMargin() - 4, 0)
self._vpMargin = max(CONFIG.textMargin - 4, 0)
self.setViewportMargins(self._vpMargin, self._vpMargin, self._vpMargin, self._vpMargin)
# Also set the document text options for the document text flow
@@ -359,7 +359,7 @@ class GuiDocEditor(QPlainTextEdit):
self.setHorizontalScrollBarPolicy(QtScrollAsNeeded)
# Refresh the tab stops
self.setTabStopDistance(CONFIG.getTabWidth())
self.setTabStopDistance(CONFIG.tabWidth)
# If we have a document open, we should refresh it in case the
# font changed, otherwise we just clear the editor entirely,
+3 -3
View File
@@ -200,7 +200,7 @@ class GuiDocViewer(QTextBrowser):
self.setHorizontalScrollBarPolicy(QtScrollAsNeeded)
# Refresh the tab stops
self.setTabStopDistance(CONFIG.getTabWidth())
self.setTabStopDistance(CONFIG.tabWidth)
# If we have a document open, we should reload it in case the font changed
self.reloadText()
@@ -250,7 +250,7 @@ class GuiDocViewer(QTextBrowser):
self.setDocumentTitle(tHandle)
self.setDocument(qDoc.document)
self.setTabStopDistance(CONFIG.getTabWidth())
self.setTabStopDistance(CONFIG.tabWidth)
if self._docHandle == tHandle:
# This is a refresh, so we set the scrollbar back to where it was
@@ -308,7 +308,7 @@ class GuiDocViewer(QTextBrowser):
"""Automatically adjust the margins so the text is centred."""
wW = self.width()
wH = self.height()
cM = CONFIG.getTextMargin()
cM = CONFIG.textMargin
vBar = self.verticalScrollBar()
sW = vBar.width() if vBar.isVisible() else 0
+3 -3
View File
@@ -860,10 +860,10 @@ class GuiMain(QMainWindow):
logger.info("Exiting novelWriter")
if not SHARED.focusMode:
CONFIG.setMainPanePos(self.splitMain.sizes())
CONFIG.setOutlinePanePos(self.outlineView.splitSizes())
CONFIG.mainPanePos = self.splitMain.sizes()
CONFIG.outlinePanePos = self.outlineView.splitSizes()
if self.docViewerPanel.isVisible():
CONFIG.setViewPanePos(self.splitView.sizes())
CONFIG.viewPanePos = self.splitView.sizes()
CONFIG.showViewerPanel = self.docViewerPanel.isVisible()
wFull = Qt.WindowState.WindowFullScreen
+4 -4
View File
@@ -750,11 +750,11 @@ class _PreviewWidget(QTextBrowser):
self.setPalette(dPalette)
self.setMinimumWidth(40*SHARED.theme.textNWidth)
self.setTabStopDistance(CONFIG.getTabWidth())
self.setTabStopDistance(CONFIG.tabWidth)
self.setOpenExternalLinks(False)
self.setOpenLinks(False)
self.document().setDocumentMargin(CONFIG.getTextMargin())
self.document().setDocumentMargin(CONFIG.textMargin)
self.setPlaceholderText(self.tr(
"Press the \"Preview\" button to generate ..."
))
@@ -852,9 +852,9 @@ class _PreviewWidget(QTextBrowser):
self.buildProgress.setCentreText(self.tr("Processing ..."))
QApplication.processEvents()
document.setDocumentMargin(CONFIG.getTextMargin())
document.setDocumentMargin(CONFIG.textMargin)
self.setDocument(document)
self.setTabStopDistance(CONFIG.getTabWidth())
self.setTabStopDistance(CONFIG.tabWidth)
self._docTime = int(time())
self._updateBuildAge()
+4 -27
View File
@@ -254,52 +254,29 @@ def testBaseConfig_SettersGetters(fncPath):
tstConf.setMainWinSize(70, 70)
assert tstConf.mainWinSize == [70, 70]
assert tstConf._mainWinSize == [70, 70]
assert tstConf.mainWinSize == [70, 70]
tstConf.setMainWinSize(1200, 650)
# Welcome Window Size
tstConf.setWelcomeWinSize(70, 70)
assert tstConf.welcomeWinSize == [70, 70]
assert tstConf._welcomeSize == [70, 70]
assert tstConf.welcomeWinSize == [70, 70]
tstConf.setWelcomeWinSize(800, 500)
# Preferences Size
tstConf.setPreferencesWinSize(70, 70)
assert tstConf.preferencesWinSize == [70, 70]
assert tstConf._prefsWinSize == [70, 70]
assert tstConf.prefsWinSize == [70, 70]
assert tstConf.prefsWinSize == [70, 70]
tstConf.setPreferencesWinSize(700, 615)
# Main Pane Splitter
tstConf.setMainPanePos([200, 700])
assert tstConf.mainPanePos == [200, 700]
assert tstConf._mainPanePos == [200, 700]
tstConf.setMainPanePos([300, 800])
# View Pane Splitter
tstConf.setViewPanePos([400, 250])
assert tstConf.viewPanePos == [400, 250]
assert tstConf._viewPanePos == [400, 250]
tstConf.setViewPanePos([500, 150])
# Outline Pane Splitter
tstConf.setOutlinePanePos([400, 250])
assert tstConf.outlinePanePos == [400, 250]
assert tstConf._outlnPanePos == [400, 250]
tstConf.setOutlinePanePos([500, 150])
# Getters Only
# ============
assert tstConf.getTextWidth(False) == 700
assert tstConf.getTextWidth(True) == 800
assert tstConf.getTextMargin() == 40
assert tstConf.getTabWidth() == 40
@pytest.mark.base
+13 -13
View File
@@ -72,17 +72,16 @@ def testDlgPreferences_Main(qtbot, monkeypatch, nwGUI, tstPaths):
prefs.close()
# Check Fallback Values
with monkeypatch.context() as mp:
mp.setattr(CONFIG, "hasEnchant", False)
prefs = GuiPreferences(nwGUI)
prefs.show()
CONFIG.hasEnchant = False
prefs = GuiPreferences(nwGUI)
prefs.show()
# Check Spell Checking
spelling = [prefs.spellLanguage.itemData(i) for i in range(prefs.spellLanguage.count())]
assert len(spelling) == 1
assert spelling == [""]
# Check Spell Checking
spelling = [prefs.spellLanguage.itemData(i) for i in range(prefs.spellLanguage.count())]
assert len(spelling) == 1
assert spelling == [""]
prefs.close()
prefs.close()
# qtbot.stop()
@@ -138,13 +137,14 @@ def testDlgPreferences_Actions(qtbot, monkeypatch, nwGUI):
@pytest.mark.gui
def testDlgPreferences_Settings(qtbot, monkeypatch, nwGUI, tstPaths):
def testDlgPreferences_Settings(qtbot, monkeypatch, nwGUI, fncPath, tstPaths):
"""Test the preferences dialog settings."""
spelling = [("en", "English [en]"), ("de", "Deutch [de]")]
languages = [("en_GB", "British English"), ("en_US", "US English")]
monkeypatch.setattr(SHARED._spelling, "listDictionaries", lambda: spelling)
monkeypatch.setattr(CONFIG, "listLanguages", lambda *a: languages)
(fncPath / "nw_en_US.qm").touch()
(fncPath / "project_en_US.json").touch()
CONFIG._nwLangPath = fncPath
prefs = GuiPreferences(nwGUI)
with qtbot.waitExposed(prefs):
@@ -88,7 +88,12 @@ def testDlgProjSettings_SettingsPage(qtbot, monkeypatch, nwGUI, fncPath, projPat
"""Test the settings page of the dialog."""
languages = [("en", "English"), ("de", "German")]
monkeypatch.setattr(SHARED._spelling, "listDictionaries", lambda *a: languages)
monkeypatch.setattr(CONFIG, "listLanguages", lambda *a: languages)
(fncPath / "nw_en.qm").touch()
(fncPath / "nw_de.qm").touch()
(fncPath / "project_en.json").touch()
(fncPath / "project_de.json").touch()
CONFIG._nwLangPath = fncPath
# Create new project
buildTestProject(nwGUI, projPath)