Files
Plugin_SN_Basis/ui/base_dockwidget.py
T

173 lines
5.7 KiB
Python
Raw Normal View History

"""
sn_basis/ui/base_dockwidget.py
Basis-Dockwidget für alle LNO-Module.
"""
from sn_basis.functions.qt_wrapper import QDockWidget, QTabWidget
from sn_basis.functions.message_wrapper import warning, error
2026-01-08 17:13:51 +01:00
from sn_basis.functions.qt_wrapper import (
QDockWidget,
QTabWidget,
QScrollArea,
FrameNoFrame,
2026-01-08 17:13:51 +01:00
Qt,
DockWidgetMovable,
DockWidgetFloatable,
DockWidgetClosable,
DockAreaLeft,
DockAreaRight,
)
def _inhalt(seite):
"""Tab-Instanz einer Reiterseite; liegt sie in einem Scroll-Bereich, dessen Inhalt."""
if isinstance(seite, QScrollArea):
return seite.widget()
return seite
def tabs_mit_scrollbereich(tab_widget) -> None:
"""Packt jeden Tab eines QTabWidget in einen mitwachsenden Scroll-Bereich (Basis #104).
Ohne Scroll-Bereich verlangt Qt für das Dock mindestens die Höhe des höchsten Tabs; ist
der Tab höher als der Bildschirm, schiebt QGIS seinen unteren Fensterrand aus dem Bild.
Tabs, die schon in einem Scroll-Bereich liegen, bleiben unverändert.
"""
if not callable(getattr(tab_widget, "count", None)) or not callable(getattr(tab_widget, "insertTab", None)):
return
aktuell = tab_widget.currentIndex()
for index in range(tab_widget.count()):
seite = tab_widget.widget(index)
if seite is None or isinstance(seite, QScrollArea):
continue
titel = tab_widget.tabText(index)
bereich = QScrollArea()
bereich.setWidgetResizable(True)
bereich.setFrameShape(FrameNoFrame)
tab_widget.removeTab(index)
bereich.setWidget(seite)
tab_widget.insertTab(index, bereich, titel)
tab_widget.setCurrentIndex(aktuell)
2025-11-17 11:29:04 +01:00
class BaseDockWidget(QDockWidget):
"""
Basis-Dockwidget für alle LNO-Module.
- Titel wird automatisch aus base_title + subtitle erzeugt
- Tabs werden dynamisch aus der Klassenvariable 'tabs' erzeugt
- Die zugehörige Toolbar-Action wird beim Schließen zurückgesetzt
- Jeder Tab liegt in einem Scroll-Bereich (``setWidget``), auch wenn ein Fachplugin
seine Tabs selbst aufbaut (Basis #104)
"""
2025-11-17 11:29:04 +01:00
base_title = "LNO Sachsen"
tabs = [] # Liste von Tab-Klassen
action = None # Referenz auf die Toolbar-Action
2025-11-17 11:29:04 +01:00
def __init__(self, parent=None, subtitle=""):
super().__init__(parent)
2026-01-08 17:13:51 +01:00
# -----------------------------------------------------
# Dock-Konfiguration (WICHTIG)
# -----------------------------------------------------
self.setFeatures(
DockWidgetMovable
| DockWidgetFloatable
| DockWidgetClosable
)
self.setAllowedAreas(
DockAreaLeft
| DockAreaRight
)
2025-11-17 11:29:04 +01:00
# -----------------------------------------------------
# Titel setzen
# -----------------------------------------------------
try:
title = (
self.base_title
if not subtitle
else f"{self.base_title} | {subtitle}"
)
self.setWindowTitle(title)
except Exception as e:
warning("Titel konnte nicht gesetzt werden", str(e))
2025-11-17 11:29:04 +01:00
# -----------------------------------------------------
# Tabs erzeugen
# -----------------------------------------------------
try:
tab_widget = QTabWidget()
for tab_class in self.tabs:
try:
tab_instance = tab_class()
tab_title = getattr(
tab_class,
"tab_title",
tab_class.__name__,
)
tab_widget.addTab(tab_instance, tab_title)
except Exception as e:
error(
"Tab konnte nicht geladen werden",
f"{tab_class}: {e}",
)
self.setWidget(tab_widget)
except Exception as e:
error(
"Tab-Widget konnte nicht initialisiert werden",
str(e),
)
# ---------------------------------------------------------
# Inhalt setzen
# ---------------------------------------------------------
def setWidget(self, widget):
"""Wie ``QDockWidget.setWidget``; die Tabs eines QTabWidget bekommen je einen Scroll-Bereich."""
if widget is not None:
try:
tabs_mit_scrollbereich(widget)
except Exception as e:
warning("Scroll-Bereich konnte nicht angelegt werden", str(e))
super().setWidget(widget)
# ---------------------------------------------------------
# Dock schließen
# ---------------------------------------------------------
2025-11-17 12:23:04 +01:00
def closeEvent(self, event):
"""
Wird aufgerufen, wenn das Dock geschlossen wird.
Setzt die zugehörige Toolbar-Action zurück.
"""
2026-04-20 13:28:00 +02:00
try:
tab_widget = self.widget()
if tab_widget and hasattr(tab_widget, "count") and hasattr(tab_widget, "widget"):
for index in range(tab_widget.count()):
tab = _inhalt(tab_widget.widget(index))
2026-04-20 13:28:00 +02:00
cleanup = getattr(tab, "cleanup", None)
if callable(cleanup):
try:
cleanup()
except Exception:
pass
except Exception:
pass
try:
if self.action:
self.action.setChecked(False)
except Exception as e:
warning(
"Toolbar-Status konnte nicht zurückgesetzt werden",
str(e),
)
2025-11-17 12:23:04 +01:00
super().closeEvent(event)