# Copyright 2025–2026 European Union
# Author: Bulgheroni Antonio (antonio.bulgheroni@ec.europa.eu)
# SPDX-License-Identifier: EUPL-1.2
"""
Matplotlib canvas widgets for Qt applications.
This module provides specialized canvas widgets that integrate Matplotlib
figures with Qt for displaying TIFF images and intensity profiles.
"""
from typing import Optional
import matplotlib.pyplot as plt
from matplotlib.backends.backend_qt import NavigationToolbar2QT
from matplotlib.backends.backend_qtagg import FigureCanvasQTAgg
from PySide6.QtCore import QEvent
from PySide6.QtGui import QCursor, Qt
from PySide6.QtWidgets import QToolButton, QWidget
[docs]
class MPLCanvas(FigureCanvasQTAgg):
pass
[docs]
class TiffCanvas(MPLCanvas):
"""
Canvas for displaying TIFF images with a colorbar.
This class creates a Matplotlib figure with two axes - one for the image
and one for the corresponding colorbar.
:param parent: The parent widget
:type parent: QWidget or None
:param width: Width of the figure in inches
:type width: float
:param height: Height of the figure in inches
:type height: float
:param dpi: Resolution in dots per inch
:type dpi: int
"""
def __init__(self, parent: Optional[QWidget] = None, width: float = 8, height: float = 6, dpi: int = 100) -> None:
"""Initialize the TIFF canvas with image and colorbar axes."""
self.fig, self.axes = plt.subplots(1, 2, width_ratios=[19, 1], figsize=(width, height), dpi=dpi)
self.im_axes, self.cb_axes = self.axes
setattr(self.im_axes, 'radioviz_name', 'im_axes')
setattr(self.cb_axes, 'radioviz_name', 'cb_axes')
super().__init__(self.fig) # type: ignore[no-untyped-call]
self.setParent(parent)
self.point_selection_active = False
self.setMouseTracking(True)
def enterEvent(self, event: QEvent) -> None:
if self.point_selection_active:
self.setCursor(QCursor(Qt.CursorShape.CrossCursor))
super().enterEvent(event) # type: ignore[no-untyped-call]
def leaveEvent(self, event: QEvent) -> None:
if self.point_selection_active:
self.setCursor(QCursor(Qt.CursorShape.ArrowCursor))
super().leaveEvent(event) # type: ignore[no-untyped-call]
[docs]
class SimpleCanvas(MPLCanvas):
"""
Canvas for displaying intensity profiles.
This class creates a Matplotlib figure with a single axis for
plotting intensity profiles or similar data.
:param parent: The parent widget
:type parent: QWidget or None
:param width: Width of the figure in inches
:type width: float
:param height: Height of the figure in inches
:type height: float
:param dpi: Resolution in dots per inch
:type dpi: int
"""
def __init__(self, parent: Optional[QWidget] = None, width: float = 5, height: float = 4, dpi: int = 100) -> None:
"""Initialize the profile canvas with one single axis"""
self.fig, self.ax = plt.subplots(figsize=(width, height), dpi=dpi)
setattr(self.ax, 'radioviz_name', 'main_axis')
super().__init__(self.fig) # type: ignore[no-untyped-call]
self.setParent(parent)