Re-implement basic novel view functionality
This commit is contained in:
@@ -123,7 +123,7 @@ class Index:
|
|||||||
def _generateNovelModel(self, tHandle: str) -> None:
|
def _generateNovelModel(self, tHandle: str) -> None:
|
||||||
"""Generate a novel model for a specific handle."""
|
"""Generate a novel model for a specific handle."""
|
||||||
if (item := SHARED.project.tree[tHandle]) and item.isRootType() and item.isNovelLike():
|
if (item := SHARED.project.tree[tHandle]) and item.isRootType() and item.isNovelLike():
|
||||||
model = NovelModel(item)
|
model = NovelModel()
|
||||||
for handle in SHARED.project.tree.subTree(tHandle):
|
for handle in SHARED.project.tree.subTree(tHandle):
|
||||||
if node := self._itemIndex[handle]:
|
if node := self._itemIndex[handle]:
|
||||||
model.append(node)
|
model.append(node)
|
||||||
|
|||||||
@@ -31,37 +31,45 @@ from PyQt6.QtGui import QIcon, QPixmap
|
|||||||
from novelwriter import SHARED
|
from novelwriter import SHARED
|
||||||
from novelwriter.constants import nwStyles
|
from novelwriter.constants import nwStyles
|
||||||
from novelwriter.core.indexdata import IndexNode
|
from novelwriter.core.indexdata import IndexNode
|
||||||
from novelwriter.core.item import NWItem
|
|
||||||
from novelwriter.types import QtAlignRight
|
from novelwriter.types import QtAlignRight
|
||||||
|
|
||||||
logger = logging.getLogger(__name__)
|
logger = logging.getLogger(__name__)
|
||||||
|
|
||||||
C_FACTOR = 0x0100
|
C_FACTOR = 0x0100
|
||||||
|
|
||||||
C_TITLE_TEXT = 0x0000 | Qt.ItemDataRole.DisplayRole
|
R_TEXT = Qt.ItemDataRole.DisplayRole
|
||||||
C_TITLE_ICON = 0x0000 | Qt.ItemDataRole.DecorationRole
|
R_ICON = Qt.ItemDataRole.DecorationRole
|
||||||
C_COUNT_TEXT = 0x0100 | Qt.ItemDataRole.DisplayRole
|
R_ALIGN = Qt.ItemDataRole.TextAlignmentRole
|
||||||
C_COUNT_ALIGN = 0x0100 | Qt.ItemDataRole.TextAlignmentRole
|
R_TIP = Qt.ItemDataRole.ToolTipRole
|
||||||
C_EXTRA_TEXT = 0x0200 | Qt.ItemDataRole.DisplayRole
|
|
||||||
C_EXTRA_TIP = 0x0200 | Qt.ItemDataRole.ToolTipRole
|
|
||||||
C_MORE_ICON = 0x0300 | Qt.ItemDataRole.DecorationRole
|
|
||||||
|
|
||||||
T_NodeData = str | QIcon | QPixmap | Qt.AlignmentFlag | None
|
T_NodeData = str | QIcon | QPixmap | Qt.AlignmentFlag | None
|
||||||
|
|
||||||
|
|
||||||
class NovelModel(QAbstractTableModel):
|
class NovelModel(QAbstractTableModel):
|
||||||
|
|
||||||
def __init__(self, rootItem: NWItem) -> None:
|
__slots__ = ("_meta", "_rows", "_more", "_columns")
|
||||||
|
|
||||||
|
def __init__(self) -> None:
|
||||||
super().__init__()
|
super().__init__()
|
||||||
self._root = rootItem
|
self._meta: list[tuple[str, str]] = []
|
||||||
self._rows: list[tuple[str, str, dict]] = []
|
self._rows: list[dict[int, T_NodeData]] = []
|
||||||
self._more = SHARED.theme.getIcon("more_arrow")
|
self._more = SHARED.theme.getIcon("more_arrow")
|
||||||
|
self._columns = 3
|
||||||
return
|
return
|
||||||
|
|
||||||
def __del__(self) -> None: # pragma: no cover
|
def __del__(self) -> None: # pragma: no cover
|
||||||
logger.debug("Delete: NovelModel")
|
logger.debug("Delete: NovelModel")
|
||||||
return
|
return
|
||||||
|
|
||||||
|
##
|
||||||
|
# Setters
|
||||||
|
##
|
||||||
|
|
||||||
|
def setExtraColumn(self, state: bool) -> None:
|
||||||
|
"""Set extra data column settings."""
|
||||||
|
self._columns = 4 if state else 3
|
||||||
|
return
|
||||||
|
|
||||||
##
|
##
|
||||||
# Model Interface
|
# Model Interface
|
||||||
##
|
##
|
||||||
@@ -72,29 +80,42 @@ class NovelModel(QAbstractTableModel):
|
|||||||
|
|
||||||
def columnCount(self, index: QModelIndex) -> int:
|
def columnCount(self, index: QModelIndex) -> int:
|
||||||
"""Return the number of columns for an entry."""
|
"""Return the number of columns for an entry."""
|
||||||
return 4
|
return self._columns
|
||||||
|
|
||||||
def data(self, index: QModelIndex, role: Qt.ItemDataRole) -> T_NodeData:
|
def data(self, index: QModelIndex, role: Qt.ItemDataRole) -> T_NodeData:
|
||||||
"""Return display data for a node."""
|
"""Return display data for a node."""
|
||||||
if index.isValid() and (row := index.row()) < len(self._rows):
|
if index.isValid() and (row := index.row()) < len(self._rows):
|
||||||
return self._rows[row][2].get(C_FACTOR*index.column() | role)
|
return self._rows[row].get(C_FACTOR*index.column() | role)
|
||||||
return None
|
return None
|
||||||
|
|
||||||
|
def keys(self, index: QModelIndex) -> tuple[str | None, str | None]:
|
||||||
|
"""Return display data for a node."""
|
||||||
|
if index.isValid() and (row := index.row()) < len(self._rows):
|
||||||
|
return self._meta[row]
|
||||||
|
return None, None
|
||||||
|
|
||||||
##
|
##
|
||||||
# Data Methods
|
# Data Methods
|
||||||
##
|
##
|
||||||
|
|
||||||
|
def clear(self) -> None:
|
||||||
|
"""Clear the model."""
|
||||||
|
self._rows.clear()
|
||||||
|
return
|
||||||
|
|
||||||
def append(self, node: IndexNode) -> None:
|
def append(self, node: IndexNode) -> None:
|
||||||
"""Append a node to the model."""
|
"""Append a node to the model."""
|
||||||
handle = node.handle
|
handle = node.handle
|
||||||
for key, head in node.items():
|
for key, head in node.items():
|
||||||
if key != "T0000":
|
if key != "T0000":
|
||||||
iLevel = nwStyles.H_LEVEL.get(head.level, 0)
|
iLevel = nwStyles.H_LEVEL.get(head.level, 0)
|
||||||
|
more = self._columns - 1
|
||||||
data = {}
|
data = {}
|
||||||
data[C_TITLE_TEXT] = head.title
|
data[C_FACTOR*0 | R_TEXT] = head.title
|
||||||
data[C_TITLE_ICON] = SHARED.theme.getHeaderDecoration(iLevel)
|
data[C_FACTOR*0 | R_ICON] = SHARED.theme.getHeaderDecoration(iLevel)
|
||||||
data[C_COUNT_TEXT] = f"{head.mainCount:n}"
|
data[C_FACTOR*1 | R_TEXT] = f"{head.mainCount:n}"
|
||||||
data[C_COUNT_ALIGN] = QtAlignRight
|
data[C_FACTOR*1 | R_ALIGN] = QtAlignRight
|
||||||
data[C_MORE_ICON] = self._more
|
data[C_FACTOR*more | R_ICON] = self._more
|
||||||
self._rows.append((handle, key, data))
|
self._meta.append((handle, key))
|
||||||
|
self._rows.append(data)
|
||||||
return
|
return
|
||||||
|
|||||||
@@ -30,15 +30,15 @@ from __future__ import annotations
|
|||||||
from enum import Enum
|
from enum import Enum
|
||||||
from typing import TYPE_CHECKING
|
from typing import TYPE_CHECKING
|
||||||
|
|
||||||
from PyQt6.QtCore import QSize, Qt, pyqtSignal, pyqtSlot
|
from PyQt6.QtCore import QModelIndex, QSize, Qt, pyqtSignal, pyqtSlot
|
||||||
from PyQt6.QtGui import QMouseEvent, QWheelEvent
|
from PyQt6.QtGui import QMouseEvent, QWheelEvent
|
||||||
from PyQt6.QtWidgets import (
|
from PyQt6.QtWidgets import (
|
||||||
QApplication, QComboBox, QDialog, QDoubleSpinBox, QLabel, QSpinBox,
|
QApplication, QComboBox, QDialog, QDoubleSpinBox, QLabel, QSpinBox,
|
||||||
QToolButton, QWidget
|
QToolButton, QTreeView, QWidget
|
||||||
)
|
)
|
||||||
|
|
||||||
from novelwriter import CONFIG, SHARED
|
from novelwriter import CONFIG, SHARED
|
||||||
from novelwriter.types import QtMouseLeft
|
from novelwriter.types import QtMouseLeft, QtMouseMiddle
|
||||||
|
|
||||||
if TYPE_CHECKING: # pragma: no cover
|
if TYPE_CHECKING: # pragma: no cover
|
||||||
from novelwriter.guimain import GuiMain
|
from novelwriter.guimain import GuiMain
|
||||||
@@ -99,6 +99,17 @@ class NNonBlockingDialog(NDialog):
|
|||||||
return
|
return
|
||||||
|
|
||||||
|
|
||||||
|
class NTreeView(QTreeView):
|
||||||
|
|
||||||
|
middleClicked = pyqtSignal(QModelIndex)
|
||||||
|
|
||||||
|
def mousePressEvent(self, event: QMouseEvent | None) -> None:
|
||||||
|
"""Emit a signal on mouse middle click."""
|
||||||
|
if event and event.button() == QtMouseMiddle:
|
||||||
|
self.middleClicked.emit(self.indexAt(event.pos()))
|
||||||
|
return super().mousePressEvent(event)
|
||||||
|
|
||||||
|
|
||||||
class NComboBox(QComboBox):
|
class NComboBox(QComboBox):
|
||||||
|
|
||||||
def __init__(self, parent: QWidget | None = None) -> None:
|
def __init__(self, parent: QWidget | None = None) -> None:
|
||||||
|
|||||||
@@ -29,17 +29,15 @@ import logging
|
|||||||
|
|
||||||
from enum import Enum
|
from enum import Enum
|
||||||
|
|
||||||
from PyQt6.QtCore import pyqtSignal, pyqtSlot
|
from PyQt6.QtCore import QModelIndex, pyqtSignal, pyqtSlot
|
||||||
from PyQt6.QtGui import QActionGroup, QFont, QPalette
|
from PyQt6.QtGui import QActionGroup, QFont, QPalette
|
||||||
from PyQt6.QtWidgets import (
|
from PyQt6.QtWidgets import QAbstractItemView, QFrame, QHBoxLayout, QMenu, QVBoxLayout, QWidget
|
||||||
QFrame, QHBoxLayout, QMenu, QTreeView, QTreeWidgetItem, QVBoxLayout,
|
|
||||||
QWidget
|
|
||||||
)
|
|
||||||
|
|
||||||
from novelwriter import CONFIG, SHARED
|
from novelwriter import CONFIG, SHARED
|
||||||
from novelwriter.common import qtAddAction, qtAddMenu, qtLambda
|
from novelwriter.common import qtAddAction, qtAddMenu, qtLambda
|
||||||
from novelwriter.enum import nwChange, nwItemClass
|
from novelwriter.core.novelmodel import NovelModel
|
||||||
from novelwriter.extensions.modified import NIconToolButton
|
from novelwriter.enum import nwChange, nwDocMode, nwItemClass
|
||||||
|
from novelwriter.extensions.modified import NIconToolButton, NTreeView
|
||||||
from novelwriter.extensions.novelselector import NovelSelector
|
from novelwriter.extensions.novelselector import NovelSelector
|
||||||
from novelwriter.gui.theme import STYLES_MIN_TOOLBUTTON
|
from novelwriter.gui.theme import STYLES_MIN_TOOLBUTTON
|
||||||
from novelwriter.types import (
|
from novelwriter.types import (
|
||||||
@@ -93,7 +91,6 @@ class GuiNovelView(QWidget):
|
|||||||
def updateTheme(self) -> None:
|
def updateTheme(self) -> None:
|
||||||
"""Update theme elements."""
|
"""Update theme elements."""
|
||||||
self.novelBar.updateTheme()
|
self.novelBar.updateTheme()
|
||||||
self.novelTree.updateTheme()
|
|
||||||
self.refreshTree()
|
self.refreshTree()
|
||||||
return
|
return
|
||||||
|
|
||||||
@@ -104,7 +101,7 @@ class GuiNovelView(QWidget):
|
|||||||
|
|
||||||
def clearNovelView(self) -> None:
|
def clearNovelView(self) -> None:
|
||||||
"""Clear project-related GUI content."""
|
"""Clear project-related GUI content."""
|
||||||
self.novelTree.clearContent()
|
# self.novelTree.clearContent()
|
||||||
self.novelBar.clearContent()
|
self.novelBar.clearContent()
|
||||||
self.novelBar.setEnabled(False)
|
self.novelBar.setEnabled(False)
|
||||||
return
|
return
|
||||||
@@ -351,7 +348,7 @@ class GuiNovelToolBar(QWidget):
|
|||||||
return
|
return
|
||||||
|
|
||||||
|
|
||||||
class GuiNovelTree(QTreeView):
|
class GuiNovelTree(NTreeView):
|
||||||
|
|
||||||
C_DATA = 0
|
C_DATA = 0
|
||||||
C_TITLE = 0
|
C_TITLE = 0
|
||||||
@@ -372,68 +369,36 @@ class GuiNovelTree(QTreeView):
|
|||||||
self.novelView = novelView
|
self.novelView = novelView
|
||||||
|
|
||||||
# Internal Variables
|
# Internal Variables
|
||||||
self._lastBuild = 0
|
# self._lastBuild = 0
|
||||||
self._lastCol = NovelTreeColumn.POV
|
# self._lastCol = NovelTreeColumn.POV
|
||||||
self._lastColSize = 0.25
|
# self._lastColSize = 0.25
|
||||||
self._actHandle = None
|
# self._actHandle = None
|
||||||
self._treeMap: dict[str, QTreeWidgetItem] = {}
|
# self._treeMap: dict[str, QTreeWidgetItem] = {}
|
||||||
|
|
||||||
# Cached Strings
|
# Cached Strings
|
||||||
# self._povLabel = trConst(nwLabels.KEY_NAME[nwKeyWords.POV_KEY])
|
# self._povLabel = trConst(nwLabels.KEY_NAME[nwKeyWords.POV_KEY])
|
||||||
# self._focLabel = trConst(nwLabels.KEY_NAME[nwKeyWords.FOCUS_KEY])
|
# self._focLabel = trConst(nwLabels.KEY_NAME[nwKeyWords.FOCUS_KEY])
|
||||||
# self._pltLabel = trConst(nwLabels.KEY_NAME[nwKeyWords.PLOT_KEY])
|
# self._pltLabel = trConst(nwLabels.KEY_NAME[nwKeyWords.PLOT_KEY])
|
||||||
|
|
||||||
# Build GUI
|
|
||||||
# =========
|
|
||||||
|
|
||||||
# iPx = SHARED.theme.baseIconHeight
|
|
||||||
|
|
||||||
self.setIconSize(SHARED.theme.baseIconSize)
|
self.setIconSize(SHARED.theme.baseIconSize)
|
||||||
self.setFrameStyle(QFrame.Shape.NoFrame)
|
self.setFrameStyle(QFrame.Shape.NoFrame)
|
||||||
self.setUniformRowHeights(True)
|
self.setUniformRowHeights(True)
|
||||||
self.setAllColumnsShowFocus(True)
|
self.setAllColumnsShowFocus(True)
|
||||||
self.setHeaderHidden(True)
|
self.setHeaderHidden(True)
|
||||||
self.setIndentation(2)
|
self.setIndentation(2)
|
||||||
|
self.setDragEnabled(False)
|
||||||
|
|
||||||
# self.setIconSize(iSz)
|
# Set selection options
|
||||||
# self.setFrameStyle(QFrame.Shape.NoFrame)
|
self.setSelectionBehavior(QAbstractItemView.SelectionBehavior.SelectRows)
|
||||||
# self.setUniformRowHeights(True)
|
self.setSelectionMode(QAbstractItemView.SelectionMode.SingleSelection)
|
||||||
# self.setAllColumnsShowFocus(True)
|
|
||||||
# self.setHeaderHidden(True)
|
|
||||||
# self.setIndentation(2)
|
|
||||||
# self.setColumnCount(4)
|
|
||||||
# self.setSelectionBehavior(QAbstractItemView.SelectionBehavior.SelectRows)
|
|
||||||
# self.setSelectionMode(QAbstractItemView.SelectionMode.SingleSelection)
|
|
||||||
# self.setExpandsOnDoubleClick(False)
|
|
||||||
# self.setDragEnabled(False)
|
|
||||||
|
|
||||||
# Lock the column sizes
|
|
||||||
# if header := self.header():
|
|
||||||
# header.setStretchLastSection(False)
|
|
||||||
# header.setMinimumSectionSize(iPx + 6)
|
|
||||||
# header.setSectionResizeMode(self.C_TITLE, QtHeaderStretch)
|
|
||||||
# header.setSectionResizeMode(self.C_WORDS, QtHeaderToContents)
|
|
||||||
# header.setSectionResizeMode(self.C_EXTRA, QtHeaderToContents)
|
|
||||||
# header.setSectionResizeMode(self.C_MORE, QtHeaderToContents)
|
|
||||||
|
|
||||||
# Pre-Generate Tree Formatting
|
|
||||||
# fH1 = self.font()
|
|
||||||
# fH1.setBold(True)
|
|
||||||
# fH1.setUnderline(True)
|
|
||||||
|
|
||||||
# fH2 = self.font()
|
|
||||||
# fH2.setBold(True)
|
|
||||||
|
|
||||||
# self._hFonts = [self.font(), fH1, fH2, self.font(), self.font()]
|
|
||||||
|
|
||||||
# Connect signals
|
# Connect signals
|
||||||
# self.clicked.connect(self._treeItemClicked)
|
self.clicked.connect(self._onSingleClick)
|
||||||
# self.itemDoubleClicked.connect(self._treeDoubleClick)
|
self.doubleClicked.connect(self._onDoubleClick)
|
||||||
# self.itemSelectionChanged.connect(self._treeSelectionChange)
|
self.middleClicked.connect(self._onMiddleClick)
|
||||||
|
|
||||||
# Set custom settings
|
# Set custom settings
|
||||||
self.initSettings()
|
self.initSettings()
|
||||||
# self.updateTheme()
|
|
||||||
|
|
||||||
logger.debug("Ready: GuiNovelTree")
|
logger.debug("Ready: GuiNovelTree")
|
||||||
|
|
||||||
@@ -441,25 +406,87 @@ class GuiNovelTree(QTreeView):
|
|||||||
|
|
||||||
def initSettings(self) -> None:
|
def initSettings(self) -> None:
|
||||||
"""Set or update tree widget settings."""
|
"""Set or update tree widget settings."""
|
||||||
# Scroll bars
|
|
||||||
if CONFIG.hideVScroll:
|
if CONFIG.hideVScroll:
|
||||||
self.setVerticalScrollBarPolicy(QtScrollAlwaysOff)
|
self.setVerticalScrollBarPolicy(QtScrollAlwaysOff)
|
||||||
else:
|
else:
|
||||||
self.setVerticalScrollBarPolicy(QtScrollAsNeeded)
|
self.setVerticalScrollBarPolicy(QtScrollAsNeeded)
|
||||||
|
|
||||||
if CONFIG.hideHScroll:
|
if CONFIG.hideHScroll:
|
||||||
self.setHorizontalScrollBarPolicy(QtScrollAlwaysOff)
|
self.setHorizontalScrollBarPolicy(QtScrollAlwaysOff)
|
||||||
else:
|
else:
|
||||||
self.setHorizontalScrollBarPolicy(QtScrollAsNeeded)
|
self.setHorizontalScrollBarPolicy(QtScrollAsNeeded)
|
||||||
|
|
||||||
return
|
return
|
||||||
|
|
||||||
def updateTheme(self) -> None:
|
##
|
||||||
"""Update theme elements."""
|
# Getters
|
||||||
# iPx = SHARED.theme.baseIconHeight
|
##
|
||||||
# self._pMore = SHARED.theme.getPixmap("more_arrow", (iPx, iPx))
|
|
||||||
|
def getSelectedHandle(self) -> tuple[str | None, str | None]:
|
||||||
|
"""Get the currently selected or active handle. If multiple
|
||||||
|
items are selected, return the first.
|
||||||
|
"""
|
||||||
|
if model := self._getModel():
|
||||||
|
return model.keys(self.currentIndex())
|
||||||
|
return None, None
|
||||||
|
|
||||||
|
##
|
||||||
|
# Class Methods
|
||||||
|
##
|
||||||
|
|
||||||
|
def resizeColumsn(self) -> None:
|
||||||
|
"""Set the correct column sizes."""
|
||||||
|
if (header := self.header()) and (model := self._getModel()):
|
||||||
|
header.setStretchLastSection(False)
|
||||||
|
header.setMinimumSectionSize(SHARED.theme.baseIconHeight + 6)
|
||||||
|
header.setSectionResizeMode(0, QtHeaderStretch)
|
||||||
|
for i in range(1, model.columnCount(QModelIndex())):
|
||||||
|
header.setSectionResizeMode(i, QtHeaderToContents)
|
||||||
return
|
return
|
||||||
|
|
||||||
|
##
|
||||||
|
# Private Slots
|
||||||
|
##
|
||||||
|
|
||||||
|
@pyqtSlot(QModelIndex)
|
||||||
|
def _onSingleClick(self, index: QModelIndex) -> None:
|
||||||
|
"""The user single-clicked an index."""
|
||||||
|
if (model := self._getModel()) and (keys := model.keys(index)) and (tHandle := keys[0]):
|
||||||
|
self.novelView.selectedItemChanged.emit(tHandle)
|
||||||
|
return
|
||||||
|
|
||||||
|
@pyqtSlot(QModelIndex)
|
||||||
|
def _onDoubleClick(self, index: QModelIndex) -> None:
|
||||||
|
"""The user double-clicked an index."""
|
||||||
|
if (
|
||||||
|
(model := self._getModel()) and (keys := model.keys(index))
|
||||||
|
and (tHandle := keys[0]) and (sTitle := keys[1])
|
||||||
|
):
|
||||||
|
self.novelView.openDocumentRequest.emit(tHandle, nwDocMode.EDIT, sTitle or "", False)
|
||||||
|
return
|
||||||
|
|
||||||
|
@pyqtSlot(QModelIndex)
|
||||||
|
def _onMiddleClick(self, index: QModelIndex) -> None:
|
||||||
|
"""The user middle-clicked an index."""
|
||||||
|
if (
|
||||||
|
(model := self._getModel()) and (keys := model.keys(index))
|
||||||
|
and (tHandle := keys[0]) and (sTitle := keys[1])
|
||||||
|
):
|
||||||
|
self.novelView.openDocumentRequest.emit(tHandle, nwDocMode.VIEW, sTitle or "", False)
|
||||||
|
return
|
||||||
|
|
||||||
|
##
|
||||||
|
# Internal Functions
|
||||||
|
##
|
||||||
|
|
||||||
|
def _getModel(self) -> NovelModel | None:
|
||||||
|
"""Return the model, if it exists."""
|
||||||
|
if isinstance(model := self.model(), NovelModel):
|
||||||
|
return model
|
||||||
|
return None
|
||||||
|
|
||||||
|
##
|
||||||
|
# Old Code
|
||||||
|
##
|
||||||
|
|
||||||
##
|
##
|
||||||
# Properties
|
# Properties
|
||||||
##
|
##
|
||||||
@@ -476,23 +503,12 @@ class GuiNovelTree(QTreeView):
|
|||||||
# Class Methods
|
# Class Methods
|
||||||
##
|
##
|
||||||
|
|
||||||
def clearContent(self) -> None:
|
# def clearContent(self) -> None:
|
||||||
"""Clear the GUI content and the related maps."""
|
# """Clear the GUI content and the related maps."""
|
||||||
# self.clear()
|
# self.clear()
|
||||||
# self._treeMap = {}
|
# self._treeMap = {}
|
||||||
# self._lastBuild = 0
|
# self._lastBuild = 0
|
||||||
return
|
# return
|
||||||
|
|
||||||
def resizeColumsn(self) -> None:
|
|
||||||
"""Set the correct column sizes."""
|
|
||||||
if header := self.header():
|
|
||||||
header.setStretchLastSection(False)
|
|
||||||
header.setMinimumSectionSize(SHARED.theme.baseIconHeight + 6)
|
|
||||||
header.setSectionResizeMode(self.C_TITLE, QtHeaderStretch)
|
|
||||||
header.setSectionResizeMode(self.C_WORDS, QtHeaderToContents)
|
|
||||||
header.setSectionResizeMode(self.C_EXTRA, QtHeaderToContents)
|
|
||||||
header.setSectionResizeMode(self.C_MORE, QtHeaderToContents)
|
|
||||||
return
|
|
||||||
|
|
||||||
# def refreshTree(self, rootHandle: str | None = None, overRide: bool = False) -> None:
|
# def refreshTree(self, rootHandle: str | None = None, overRide: bool = False) -> None:
|
||||||
# """Refresh the tree if it has been changed."""
|
# """Refresh the tree if it has been changed."""
|
||||||
@@ -526,18 +542,6 @@ class GuiNovelTree(QTreeView):
|
|||||||
# return
|
# return
|
||||||
# return
|
# return
|
||||||
|
|
||||||
def getSelectedHandle(self) -> tuple[str | None, str | None]:
|
|
||||||
"""Get the currently selected or active handle. If multiple
|
|
||||||
items are selected, return the first.
|
|
||||||
"""
|
|
||||||
# selList = self.selectedItems()
|
|
||||||
# trItem = selList[0] if selList else self.currentItem()
|
|
||||||
# if isinstance(trItem, QTreeWidgetItem):
|
|
||||||
# tHandle = trItem.data(self.C_DATA, self.D_HANDLE)
|
|
||||||
# sTitle = trItem.data(self.C_DATA, self.D_TITLE)
|
|
||||||
# return tHandle, sTitle
|
|
||||||
return None, None
|
|
||||||
|
|
||||||
# def setLastColType(self, colType: NovelTreeColumn, doRefresh: bool = True) -> None:
|
# def setLastColType(self, colType: NovelTreeColumn, doRefresh: bool = True) -> None:
|
||||||
# """Change the content type of the last column and rebuild."""
|
# """Change the content type of the last column and rebuild."""
|
||||||
# if self._lastCol != colType:
|
# if self._lastCol != colType:
|
||||||
@@ -575,9 +579,9 @@ class GuiNovelTree(QTreeView):
|
|||||||
# self._actHandle = tHandle or None
|
# self._actHandle = tHandle or None
|
||||||
# return
|
# return
|
||||||
|
|
||||||
# ##
|
##
|
||||||
# # Events
|
# Events
|
||||||
# ##
|
##
|
||||||
|
|
||||||
# def mousePressEvent(self, event: QMouseEvent) -> None:
|
# def mousePressEvent(self, event: QMouseEvent) -> None:
|
||||||
# """Overload mousePressEvent to clear selection if clicking the
|
# """Overload mousePressEvent to clear selection if clicking the
|
||||||
|
|||||||
@@ -1022,7 +1022,7 @@ class GuiProjectTree(QTreeView):
|
|||||||
return [i for i in self.selectedIndexes() if i.column() == 0]
|
return [i for i in self.selectedIndexes() if i.column() == 0]
|
||||||
|
|
||||||
def _getModel(self) -> ProjectModel | None:
|
def _getModel(self) -> ProjectModel | None:
|
||||||
"""Return a project node corresponding to a model index."""
|
"""Return the model, if it exists."""
|
||||||
if isinstance(model := self.model(), ProjectModel):
|
if isinstance(model := self.model(), ProjectModel):
|
||||||
return model
|
return model
|
||||||
return None
|
return None
|
||||||
|
|||||||
Reference in New Issue
Block a user