Public Access
147 lines
5.1 KiB
Python
147 lines
5.1 KiB
Python
# -*- coding: iso-8859-1 -*-
|
|
|
|
from .Resultable import Resultable
|
|
from .Drawable import Drawable
|
|
import numpy
|
|
import threading
|
|
|
|
#############################################################################
|
|
# #
|
|
# Name: Class Temp_Result #
|
|
# #
|
|
# Purpose: Specialised class of Resultable and Drawable #
|
|
# Contains recorded temperature data #
|
|
# #
|
|
#############################################################################
|
|
|
|
class TemperatureResult(Resultable, Drawable):
|
|
"""
|
|
Specialised class of Resultable and Drawable
|
|
Contains recorded temperature data.
|
|
|
|
Attributes:
|
|
x: List of timestamps in seconds.
|
|
y: List of temperature readings in Celsius.
|
|
setpoint: Optional list of setpoint temperatures in Celsius.
|
|
xlabel: Label for x-axis (default: "Time (s)").
|
|
ylabel: Label for y-axis (default: "Temperature (C)").
|
|
"""
|
|
def __init__(self, x = None, y = None, setpoint = None, desc = None, job_id = None, job_date = None):
|
|
Resultable.__init__(self)
|
|
Drawable.__init__(self)
|
|
|
|
# Set default labels
|
|
self.xlabel = "Time (s)"
|
|
self.ylabel = "Temperature (C)"
|
|
|
|
# Initialize data lists
|
|
self.x = [] if x is None else x
|
|
self.y = [] if y is None else y
|
|
self.setpoint = [] if setpoint is None else setpoint
|
|
|
|
# Set metadata if provided
|
|
if desc is not None:
|
|
self.description = desc
|
|
if job_id is not None:
|
|
self.job_id = job_id
|
|
if job_date is not None:
|
|
self.job_date = job_date
|
|
|
|
# Listener management for GUI updates
|
|
self.__listeners = []
|
|
self.__listener_lock = threading.Lock()
|
|
|
|
def get_number_of_channels(self):
|
|
"""Returns 1 for temperature data."""
|
|
return 1
|
|
|
|
def register_listener(self, listener):
|
|
"""Register a listener to be notified when data changes."""
|
|
with self.__listener_lock:
|
|
if listener not in self.__listeners:
|
|
self.__listeners.append(listener)
|
|
|
|
def unregister_listener(self, listener):
|
|
"""Unregister a listener."""
|
|
with self.__listener_lock:
|
|
if listener in self.__listeners:
|
|
self.__listeners.remove(listener)
|
|
|
|
def get_xdata(self):
|
|
"""Returns the x data (timestamps) as numpy array."""
|
|
if isinstance(self.x, numpy.ndarray):
|
|
return self.x
|
|
return numpy.array(self.x, dtype=float) if self.x else numpy.array([], dtype=float)
|
|
|
|
def get_ydata(self, channel=0):
|
|
"""Returns the y data (temperature readings) as numpy array."""
|
|
if channel == 0:
|
|
if isinstance(self.y, numpy.ndarray):
|
|
return self.y
|
|
return numpy.array(self.y, dtype=float) if self.y else numpy.array([], dtype=float)
|
|
return numpy.array([], dtype=float)
|
|
|
|
def __len__(self):
|
|
"""Returns the number of data points."""
|
|
return len(self.y) if self.y else 0
|
|
|
|
def uses_statistics(self):
|
|
"""Returns False as temperature data doesn't use statistics."""
|
|
return False
|
|
|
|
def ready_for_drawing_error(self):
|
|
"""Returns False as temperature data doesn't have error bars."""
|
|
return False
|
|
|
|
def get_yerr(self, channel=0):
|
|
"""Returns empty error data."""
|
|
return numpy.array([], dtype=float)
|
|
|
|
def get_errorplotdata(self):
|
|
"""Returns empty error plot data."""
|
|
return [[], [], []]
|
|
|
|
def get_lineplotdata(self):
|
|
"""Returns line plot data (not used for temperature)."""
|
|
return [[], []]
|
|
|
|
def get_xmin(self):
|
|
"""Returns minimum of x."""
|
|
xdata = self.get_xdata()
|
|
return xdata.min() if len(xdata) > 0 else 0
|
|
|
|
def get_xmax(self):
|
|
"""Returns maximum of x."""
|
|
xdata = self.get_xdata()
|
|
return xdata.max() if len(xdata) > 0 else 0
|
|
|
|
def get_ymin(self):
|
|
"""Returns minimum of y."""
|
|
ydata = self.get_ydata(0)
|
|
return ydata.min() if len(ydata) > 0 else 0
|
|
|
|
def get_ymax(self):
|
|
"""Returns maximum of y."""
|
|
ydata = self.get_ydata(0)
|
|
return ydata.max() if len(ydata) > 0 else 0
|
|
|
|
def get_xminpos(self):
|
|
"""Returns smallest positive value of x."""
|
|
xdata = self.get_xdata()
|
|
mask = xdata > 0
|
|
if numpy.any(mask):
|
|
return xdata[mask].min()
|
|
return 0
|
|
|
|
def get_yminpos(self):
|
|
"""Returns smallest positive value of y."""
|
|
ydata = self.get_ydata(0)
|
|
mask = ydata > 0
|
|
if numpy.any(mask):
|
|
return ydata[mask].min()
|
|
return 0
|
|
|
|
def __repr__(self):
|
|
"""String representation of the temperature result."""
|
|
return f"TemperatureResult(points={len(self)}, job_id={self.job_id})"
|