Source code for PyHydroGeophysX.visualization.pyvista_compat

"""Shared PyVista / PyVistaQt setup used by the 3D viewers.

Factored out of the Mesh 3D module so the inversion model viewer can reuse the
same VTK shim and the same offscreen guard.
"""

from __future__ import annotations

import os
import sys
import types
from typing import Any, Optional, Tuple


[docs] def ensure_vtk_matplotlib_shim() -> None: """Stub the optional ``vtkmodules.vtkRenderingMatplotlib`` module when absent. Some VTK builds (conda-forge ``vtk-base``) omit it, yet pyvista imports it unconditionally for a side effect not needed for mesh display. """ if "vtkmodules.vtkRenderingMatplotlib" in sys.modules: return try: import vtkmodules.vtkRenderingMatplotlib # noqa: F401 - real module present except Exception: # noqa: BLE001 - missing optional submodule; provide a stub sys.modules["vtkmodules.vtkRenderingMatplotlib"] = types.ModuleType( "vtkmodules.vtkRenderingMatplotlib")
[docs] def try_import_pyvista() -> Tuple[bool, Optional[Any], Optional[Any], str]: """Return ``(ok, pyvista_module, QtInteractor, error)``. Disabled under the offscreen Qt platform (headless / --self-test), where constructing a live ``QtInteractor`` aborts the process at the VTK level. """ try: if os.environ.get("QT_QPA_PLATFORM", "").lower() == "offscreen": return False, None, None, "offscreen platform (interactive 3D viewer disabled)" os.environ.setdefault("QT_API", "pyside6") ensure_vtk_matplotlib_shim() import pyvista as pv from pyvistaqt import QtInteractor return True, pv, QtInteractor, "" except Exception as exc: # noqa: BLE001 return False, None, None, str(exc)