Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix issues with novel tree last column #1355

Merged
merged 4 commits into from
Feb 10, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
75 changes: 43 additions & 32 deletions i18n/nw_base.ts
Original file line number Diff line number Diff line change
Expand Up @@ -757,114 +757,114 @@
<context>
<name>GuiDocEditFooter</name>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2924" />
<location filename="../novelwriter/gui/doceditor.py" line="2931" />
<source>Status</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="3073" />
<location filename="../novelwriter/gui/doceditor.py" line="3080" />
<source>Line: {0} ({1})</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="3102" />
<location filename="../novelwriter/gui/doceditor.py" line="3109" />
<source>Words: {0} ({1})</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="3107" />
<location filename="../novelwriter/gui/doceditor.py" line="3114" />
<source>Document size is {0} bytes</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="3119" />
<location filename="../novelwriter/gui/doceditor.py" line="3126" />
<source>Words: {0} selected</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="3122" />
<location filename="../novelwriter/gui/doceditor.py" line="3129" />
<source>Character count: {0}</source>
<translation type="unfinished" />
</message>
</context>
<context>
<name>GuiDocEditHeader</name>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2694" />
<location filename="../novelwriter/gui/doceditor.py" line="2701" />
<source>Edit document label</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2703" />
<location filename="../novelwriter/gui/doceditor.py" line="2710" />
<source>Search document</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2712" />
<location filename="../novelwriter/gui/doceditor.py" line="2719" />
<source>Toggle Focus Mode</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2721" />
<location filename="../novelwriter/gui/doceditor.py" line="2728" />
<source>Close the document</source>
<translation type="unfinished" />
</message>
</context>
<context>
<name>GuiDocEditSearch</name>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2287" />
<location filename="../novelwriter/gui/doceditor.py" line="2274" />
<location filename="../novelwriter/gui/doceditor.py" line="2294" />
<location filename="../novelwriter/gui/doceditor.py" line="2281" />
<source>Search</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2279" />
<location filename="../novelwriter/gui/doceditor.py" line="2286" />
<source>Replace</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2295" />
<location filename="../novelwriter/gui/doceditor.py" line="2302" />
<source>Case Sensitive</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2301" />
<location filename="../novelwriter/gui/doceditor.py" line="2308" />
<source>Whole Words Only</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2307" />
<location filename="../novelwriter/gui/doceditor.py" line="2314" />
<source>RegEx Mode</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2313" />
<location filename="../novelwriter/gui/doceditor.py" line="2320" />
<source>Loop Search</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2319" />
<location filename="../novelwriter/gui/doceditor.py" line="2326" />
<source>Search Next File</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2327" />
<location filename="../novelwriter/gui/doceditor.py" line="2334" />
<source>Preserve Case</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2335" />
<location filename="../novelwriter/gui/doceditor.py" line="2342" />
<source>Close Search</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2351" />
<location filename="../novelwriter/gui/doceditor.py" line="2358" />
<source>Find in current document</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/doceditor.py" line="2356" />
<location filename="../novelwriter/gui/doceditor.py" line="2363" />
<source>Find and replace in current document</source>
<translation type="unfinished" />
</message>
Expand Down Expand Up @@ -2050,55 +2050,66 @@
<context>
<name>GuiNovelToolBar</name>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="207" />
<location filename="../novelwriter/gui/noveltree.py" line="216" />
<source>Outline of {0}</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="215" />
<location filename="../novelwriter/gui/noveltree.py" line="224" />
<source>Novel Root</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="221" />
<location filename="../novelwriter/gui/noveltree.py" line="230" />
<source>Refresh</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="228" />
<location filename="../novelwriter/gui/noveltree.py" line="237" />
<source>Last Column</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="231" />
<location filename="../novelwriter/gui/noveltree.py" line="240" />
<source>Hidden</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="232" />
<location filename="../novelwriter/gui/noveltree.py" line="241" />
<source>Point of View Character</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="233" />
<location filename="../novelwriter/gui/noveltree.py" line="242" />
<source>Focus Character</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="234" />
<location filename="../novelwriter/gui/noveltree.py" line="243" />
<source>Novel Plot</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="237" />
<location filename="../novelwriter/gui/noveltree.py" line="361" />
<location filename="../novelwriter/gui/noveltree.py" line="246" />
<source>Column Size</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="250" />
<source>More Options</source>
<translation type="unfinished" />
</message>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="361" />
<source>Maximum column size in %</source>
<translation type="unfinished" />
</message>
</context>
<context>
<name>GuiNovelTree</name>
<message>
<location filename="../novelwriter/gui/noveltree.py" line="778" />
<location filename="../novelwriter/gui/noveltree.py" line="815" />
<source>No meta data</source>
<translation type="unfinished" />
</message>
Expand Down
2 changes: 1 addition & 1 deletion novelwriter/core/options.py
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@
"widthCol3", "widthCol4", "wordsPerPage", "countFrom", "clearDouble",
},
"GuiWordList": {"winWidth", "winHeight"},
"GuiNovelView": {"lastCol"},
"GuiNovelView": {"lastCol", "lastColSize"},
}


Expand Down
57 changes: 47 additions & 10 deletions novelwriter/gui/noveltree.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,12 +34,13 @@
from PyQt5.QtGui import QFont, QPalette
from PyQt5.QtCore import Qt, QSize, pyqtSlot, pyqtSignal
from PyQt5.QtWidgets import (
QAbstractItemView, QActionGroup, QFrame, QHBoxLayout, QHeaderView, QMenu,
QSizePolicy, QToolButton, QToolTip, QTreeWidget, QTreeWidgetItem,
QVBoxLayout, QWidget
QAbstractItemView, QActionGroup, QFrame, QHBoxLayout, QHeaderView,
QInputDialog, QMenu, QSizePolicy, QToolButton, QToolTip, QTreeWidget,
QTreeWidgetItem, QVBoxLayout, QWidget
)

from novelwriter.enum import nwDocMode, nwItemClass, nwOutline
from novelwriter.common import minmax
from novelwriter.constants import nwHeaders, nwKeyWords, nwLabels, trConst
from novelwriter.gui.components import NovelSelector

Expand Down Expand Up @@ -126,20 +127,28 @@ def openProjectTasks(self):
lastCol = self.theProject.options.getEnum(
"GuiNovelView", "lastCol", NovelTreeColumn, NovelTreeColumn.HIDDEN
)
lastColSize = self.theProject.options.getInt(
"GuiNovelView", "lastColSize", 25
)

self.clearProject()

self.novelBar.buildNovelRootMenu()
self.novelBar.setLastColType(lastCol, doRefresh=False)
self.novelBar.setCurrentRoot(lastNovel)
self.novelBar.setEnabled(True)

self.novelTree.setLastColSize(lastColSize)

return

def closeProjectTasks(self):
"""Run closing project tasks.
"""
lastColType = self.novelTree.lastColType
lastColSize = self.novelTree.lastColSize
self.theProject.options.setValue("GuiNovelView", "lastCol", lastColType)
self.theProject.options.setValue("GuiNovelView", "lastColSize", lastColSize)
return

def setTreeFocus(self):
Expand Down Expand Up @@ -233,6 +242,10 @@ def __init__(self, novelView):
self._addLastColAction(NovelTreeColumn.FOCUS, self.tr("Focus Character"))
self._addLastColAction(NovelTreeColumn.PLOT, self.tr("Novel Plot"))

self.mLastCol.addSeparator()
self.aLastColSize = self.mLastCol.addAction(self.tr("Column Size"))
self.aLastColSize.triggered.connect(self._selectLastColumnSize)

self.tbMore = QToolButton(self)
self.tbMore.setToolTip(self.tr("More Options"))
self.tbMore.setIconSize(QSize(iPx, iPx))
Expand Down Expand Up @@ -339,6 +352,19 @@ def _refreshNovelTree(self):
self.novelView.novelTree.refreshTree(rootHandle=rootHandle, overRide=True)
return

@pyqtSlot()
def _selectLastColumnSize(self):
"""Set the maximum width for the last column.
"""
oldSize = self.novelView.novelTree.lastColSize
newSize, isOk = QInputDialog.getInt(
self, self.tr("Column Size"), self.tr("Maximum column size in %"), oldSize, 15, 75, 5
)
if isOk:
self.novelView.novelTree.setLastColSize(newSize)
self._refreshNovelTree()
return

##
# Internal Functions
##
Expand Down Expand Up @@ -379,10 +405,11 @@ def __init__(self, novelView):
self.theProject = novelView.mainGui.theProject

# Internal Variables
self._treeMap = {}
self._lastBuild = 0
self._lastCol = NovelTreeColumn.POV
self._actHandle = None
self._treeMap = {}
self._lastBuild = 0
self._lastCol = NovelTreeColumn.POV
self._lastColSize = 0.25
self._actHandle = None

# Cached Strings
self._povLabel = trConst(nwLabels.KEY_NAME[nwKeyWords.POV_KEY])
Expand Down Expand Up @@ -470,6 +497,10 @@ def updateTheme(self):
def lastColType(self):
return self._lastCol

@property
def lastColSize(self):
return int(self._lastColSize * 100)

##
# Class Methods
##
Expand Down Expand Up @@ -552,6 +583,12 @@ def setLastColType(self, colType, doRefresh=True):
self.refreshTree(rootHandle=lastNovel, overRide=True)
return

def setLastColSize(self, colSize):
"""Set the column size in integer values between 15 and 75.
"""
self._lastColSize = minmax(colSize, 15, 75)/100.0
return

def setActiveHandle(self, tHandle):
"""Highlight the rows associated with a given handle.
"""
Expand Down Expand Up @@ -619,7 +656,7 @@ def resizeEvent(self, event):
newW = event.size().width()
oldW = event.oldSize().width()
if newW != oldW:
eliW = int(0.25 * newW)
eliW = int(self._lastColSize * newW)
fMetric = self.fontMetrics()
for i in range(self.topLevelItemCount()):
trItem = self.topLevelItem(i)
Expand Down Expand Up @@ -709,7 +746,7 @@ def _updateTreeItemValues(self, trItem, idxItem, tHandle, sTitle):
trItem.setData(self.C_MORE, Qt.DecorationRole, self._pMore)

# Custom column
mW = int(0.25 * self.viewport().width())
mW = int(self._lastColSize * self.viewport().width())
lastText, toolTip = self._getLastColumnText(tHandle, sTitle)
elideText = self.fontMetrics().elidedText(lastText, Qt.ElideRight, mW)
trItem.setText(self.C_EXTRA, elideText)
Expand Down Expand Up @@ -741,7 +778,7 @@ def _getLastColumnText(self, tHandle, sTitle):

if refData:
toolText = ", ".join(refData)
return refData[0], f"{refName}: {toolText}"
return toolText, f"{refName}: {toolText}"

return "", ""

Expand Down
9 changes: 8 additions & 1 deletion tests/test_gui/test_gui_noveltree.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@

from PyQt5.QtGui import QFocusEvent
from PyQt5.QtCore import Qt, QEvent
from PyQt5.QtWidgets import QToolTip
from PyQt5.QtWidgets import QInputDialog, QToolTip

from novelwriter.enum import nwWidget, nwItemType
from novelwriter.gui.noveltree import NovelTreeColumn
Expand Down Expand Up @@ -82,6 +82,8 @@ def testGuiNovelTree_TreeItems(qtbot, monkeypatch, nwGUI, projPath, mockRnd):
# Populate Tree
# =============

novelView.setTreeFocus()

nwGUI.projStack.setCurrentIndex(nwGUI.idxNovelView)
nwGUI.rebuildIndex()
novelTree._populateTree(rootHandle=None)
Expand Down Expand Up @@ -172,6 +174,11 @@ def testGuiNovelTree_TreeItems(qtbot, monkeypatch, nwGUI, projPath, mockRnd):
spSize = nwGUI.splitMain.sizes()
nwGUI.splitMain.setSizes([spSize[0] + 10, spSize[1] - 10])

# Resize the last column
with monkeypatch.context() as mp:
mp.setattr(QInputDialog, "getInt", lambda *a, **k: (40, True))
novelBar._selectLastColumnSize()

# Item Meta
# =========

Expand Down