Newer
Older
import pandas as pd
import matplotlib.pyplot as plt
import numpy as np
import time
# Different exceptions can be thrown while plotting, depending on the backend.
# We catch them all locally and raise our own exception instead
class PlottingError(Exception):
"Raised when plotting fails"
pass
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
class MeasurementPlot:
def __init__(self, title=''):
self.fig, self.ax1 = plt.subplots(2, figsize=(12, 10))
self.fig.suptitle("Measurement "+title, color="red")
# First plot: Phase and magnitude
self.path_collection_phase = self.ax1[0].scatter([], [], c='red', marker='<', label='Phase')
self.magnitude_axis = self.ax1[0].twinx()
self.path_collection_mag = self.magnitude_axis.scatter([], [], c='#3120E0', marker='4', label='Magnitude')
self.equi_axis0 = self.ax1[0].twinx()
self.equi_axis0.spines['right'].set_position(('outward', 40))
self.path_collection_equi0 = self.equi_axis0.scatter([], [], c='black', marker=".", label='Equilibrium_Indicator')
self.ax1[0].set_xlabel("TIMESTAMP")
self.ax1[0].set_ylabel("PHASE", color='red')
self.magnitude_axis.set_ylabel("MAGNITUDE", color='#3120E0')
self.equi_axis0.set_ylabel("EQUILIBRIUM_INDICATOR", color='black')
# fix range to 0..31 with some extra margin for plotting
self.equi_axis0.set_ylim(-1, 32)
self.ax1[0].grid(True, linestyle=":")
all_path_collections = [self.path_collection_phase, self.path_collection_mag, self.path_collection_equi0]
labels = [pc.get_label() for pc in all_path_collections]
self.ax1[0].legend(all_path_collections, labels, loc='lower right')
# Second plot: Humidity and temperature
self.path_collection_temp = self.ax1[1].scatter([], [], c='blue', marker='p', label="Temperature")
self.humidity_axis = self.ax1[1].twinx()
self.path_collection_hum = self.humidity_axis.scatter([], [], c='green', marker="*", label="Humidity")
self.equi_axis1 = self.ax1[1].twinx()
self.equi_axis1.spines['right'].set_position(('outward', 40))
self.path_collection_equi1 = self.equi_axis1.scatter([], [], c='black', marker=".", label="Equilibrium_Indicator")
self.ax1[1].set_xlabel("TIMESTAMP")
self.ax1[1].set_ylabel("TEMPERATURE ", color='blue')
self.humidity_axis.set_ylabel("HUMIDITY", color='green')
self.equi_axis1.set_ylabel("EQUILIBRIUM_INDICATOR", color='black')
self.equi_axis1.set_ylim(-1, 32)
self.ax1[1].grid(True, linestyle=":")
all_path_collections = [self.path_collection_temp, self.path_collection_hum, self.path_collection_equi1]
labels = [pc.get_label() for pc in all_path_collections]
self.ax1[1].legend(all_path_collections, labels, loc='lower right')
def draw(self, data_frame, pdf_name=''):
timestamps = data_frame.TIMESTAMP
minimum, maximum = self.get_extended_min_max(timestamps)
self.ax1[0].set_xlim(minimum, maximum)
self.ax1[1].set_xlim(minimum, maximum)
phases = data_frame.S21_PHASE
minimum, maximum = self.get_extended_min_max(phases)
self.ax1[0].set_ylim(minimum, maximum)
self.path_collection_phase.set_offsets(np.c_[timestamps, phases])
magnitudes = data_frame.S21_MAGNITUDE
minimum, maximum = self.get_extended_min_max(magnitudes)
self.magnitude_axis.set_ylim(minimum, maximum)
self.path_collection_mag.set_offsets(np.c_[timestamps, magnitudes])
temperatures = data_frame.READBACK_TEMPERATURE
minimum, maximum = self.get_extended_min_max(temperatures)
self.ax1[1].set_ylim(minimum, maximum)
self.path_collection_temp.set_offsets(np.c_[timestamps, temperatures])
humidities = data_frame.READBACK_HUMIDITY
minimum, maximum = self.get_extended_min_max(humidities)
self.humidity_axis.set_ylim(minimum, maximum)
self.path_collection_hum.set_offsets(np.c_[timestamps, humidities])
self.path_collection_equi0.set_offsets(np.c_[timestamps, data_frame.EQUILIBRIUM_INDICATOR])
self.path_collection_equi1.set_offsets(np.c_[timestamps, data_frame.EQUILIBRIUM_INDICATOR])
if not pdf_name == '':
self.fig.savefig(pdf_name)
plt.show()
if plt.isinteractive():
try:
self.fig.canvas.draw()
self.fig.canvas.flush_events()
except Exception as e:
raise PlottingError from e
# add 5 % of the distance between min and max to the range
@staticmethod
def get_extended_min_max(array):
distance = array.max() - array.min()
if distance == 0.:
distance = 0.5
return array.min()-0.05*distance, array.max()+0.05*distance
if __name__ == '__main__':
m = MeasurementPlot()
plt.ion()
measurements = []
for i in range(20):
measurement = {
'TIMESTAMP': i,
'READBACK_TEMPERATURE': 25 - i,
'READBACK_HUMIDITY': 10 + 0.1*i,
'EQUILIBRIUM_INDICATOR': i % 4,
'S21_PHASE': 20 - 2*i,
'S21_MAGNITUDE': 0.3*i
}
measurements.append(measurement)
data_frame = pd.DataFrame(measurements)
m.draw(data_frame)
print(str(i))
time.sleep(0.3)
print('I am done. ')
plt.ioff()
m.draw(data_frame, 'the.pdf')