pyvale 2025.4.1__py3-none-any.whl → 2025.5.1__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of pyvale might be problematic. Click here for more details.
- pyvale/__init__.py +18 -3
- pyvale/analyticmeshgen.py +1 -0
- pyvale/analyticsimdatafactory.py +18 -13
- pyvale/analyticsimdatagenerator.py +105 -72
- pyvale/blendercalibrationdata.py +15 -0
- pyvale/blenderlightdata.py +26 -0
- pyvale/blendermaterialdata.py +15 -0
- pyvale/blenderrenderdata.py +30 -0
- pyvale/blenderscene.py +488 -0
- pyvale/blendertools.py +420 -0
- pyvale/camera.py +6 -5
- pyvale/cameradata.py +25 -7
- pyvale/cameradata2d.py +6 -4
- pyvale/camerastereo.py +217 -0
- pyvale/cameratools.py +206 -11
- pyvale/cython/rastercyth.py +6 -2
- pyvale/data/cal_target.tiff +0 -0
- pyvale/dataset.py +73 -14
- pyvale/errorcalculator.py +8 -10
- pyvale/errordriftcalc.py +10 -9
- pyvale/errorintegrator.py +19 -21
- pyvale/errorrand.py +33 -39
- pyvale/errorsyscalib.py +134 -0
- pyvale/errorsysdep.py +19 -22
- pyvale/errorsysfield.py +49 -41
- pyvale/errorsysindep.py +79 -175
- pyvale/examples/basics/ex1_1_basicscalars_therm2d.py +131 -0
- pyvale/examples/basics/ex1_2_sensormodel_therm2d.py +158 -0
- pyvale/examples/basics/ex1_3_customsens_therm3d.py +216 -0
- pyvale/examples/basics/ex1_4_basicerrors_therm3d.py +153 -0
- pyvale/examples/basics/ex1_5_fielderrs_therm3d.py +168 -0
- pyvale/examples/basics/ex1_6_caliberrs_therm2d.py +133 -0
- pyvale/examples/basics/ex1_7_spatavg_therm2d.py +123 -0
- pyvale/examples/basics/ex2_1_basicvectors_disp2d.py +112 -0
- pyvale/examples/basics/ex2_2_vectorsens_disp2d.py +111 -0
- pyvale/examples/basics/ex2_3_sensangle_disp2d.py +139 -0
- pyvale/examples/basics/ex2_4_chainfielderrs_disp2d.py +196 -0
- pyvale/examples/basics/ex2_5_vectorfields3d_disp3d.py +109 -0
- pyvale/examples/basics/ex3_1_basictensors_strain2d.py +114 -0
- pyvale/examples/basics/ex3_2_tensorsens2d_strain2d.py +111 -0
- pyvale/examples/basics/ex3_3_tensorsens3d_strain3d.py +182 -0
- pyvale/examples/basics/ex4_1_expsim2d_thermmech2d.py +171 -0
- pyvale/examples/basics/ex4_2_expsim3d_thermmech3d.py +252 -0
- pyvale/examples/{analyticdatagen → genanalyticdata}/ex1_1_scalarvisualisation.py +6 -9
- pyvale/examples/{analyticdatagen → genanalyticdata}/ex1_2_scalarcasebuild.py +8 -11
- pyvale/examples/{analyticdatagen → genanalyticdata}/ex2_1_analyticsensors.py +9 -12
- pyvale/examples/imagedef2d/ex_imagedef2d_todisk.py +8 -15
- pyvale/examples/renderblender/ex1_1_blenderscene.py +121 -0
- pyvale/examples/renderblender/ex1_2_blenderdeformed.py +119 -0
- pyvale/examples/renderblender/ex2_1_stereoscene.py +128 -0
- pyvale/examples/renderblender/ex2_2_stereodeformed.py +131 -0
- pyvale/examples/renderblender/ex3_1_blendercalibration.py +120 -0
- pyvale/examples/{rasterisation → renderrasterisation}/ex_rastenp.py +3 -2
- pyvale/examples/{rasterisation → renderrasterisation}/ex_rastercyth_oneframe.py +2 -2
- pyvale/examples/{rasterisation → renderrasterisation}/ex_rastercyth_static_cypara.py +3 -8
- pyvale/examples/{rasterisation → renderrasterisation}/ex_rastercyth_static_pypara.py +6 -7
- pyvale/examples/{ex1_4_thermal2d.py → visualisation/ex1_1_plot_traces.py} +32 -16
- pyvale/examples/{features/ex_animation_tools_3dmonoblock.py → visualisation/ex2_1_animate_sim.py} +37 -31
- pyvale/experimentsimulator.py +107 -30
- pyvale/field.py +2 -9
- pyvale/fieldconverter.py +98 -22
- pyvale/fieldsampler.py +2 -2
- pyvale/fieldscalar.py +10 -10
- pyvale/fieldtensor.py +15 -17
- pyvale/fieldtransform.py +7 -2
- pyvale/fieldvector.py +6 -7
- pyvale/generatorsrandom.py +25 -47
- pyvale/imagedef2d.py +6 -2
- pyvale/integratorfactory.py +2 -2
- pyvale/integratorquadrature.py +50 -24
- pyvale/integratorrectangle.py +85 -7
- pyvale/integratorspatial.py +4 -4
- pyvale/integratortype.py +3 -3
- pyvale/output.py +17 -0
- pyvale/pyvaleexceptions.py +11 -0
- pyvale/raster.py +6 -5
- pyvale/rastercy.py +6 -4
- pyvale/rasternp.py +6 -4
- pyvale/rendermesh.py +6 -2
- pyvale/sensorarray.py +2 -2
- pyvale/sensorarrayfactory.py +52 -65
- pyvale/sensorarraypoint.py +29 -30
- pyvale/sensordata.py +2 -2
- pyvale/sensordescriptor.py +138 -25
- pyvale/sensortools.py +3 -3
- pyvale/simtools.py +67 -0
- pyvale/visualexpplotter.py +99 -57
- pyvale/visualimagedef.py +11 -7
- pyvale/visualimages.py +6 -4
- pyvale/visualopts.py +372 -58
- pyvale/visualsimanimator.py +42 -13
- pyvale/visualsimsensors.py +318 -0
- pyvale/visualtools.py +69 -13
- pyvale/visualtraceplotter.py +52 -165
- {pyvale-2025.4.1.dist-info → pyvale-2025.5.1.dist-info}/METADATA +17 -14
- pyvale-2025.5.1.dist-info/RECORD +172 -0
- {pyvale-2025.4.1.dist-info → pyvale-2025.5.1.dist-info}/WHEEL +1 -1
- pyvale/examples/analyticdatagen/__init__.py +0 -5
- pyvale/examples/ex1_1_thermal2d.py +0 -86
- pyvale/examples/ex1_2_thermal2d.py +0 -108
- pyvale/examples/ex1_3_thermal2d.py +0 -110
- pyvale/examples/ex1_5_thermal2d.py +0 -102
- pyvale/examples/ex2_1_thermal3d .py +0 -84
- pyvale/examples/ex2_2_thermal3d.py +0 -51
- pyvale/examples/ex2_3_thermal3d.py +0 -106
- pyvale/examples/ex3_1_displacement2d.py +0 -44
- pyvale/examples/ex3_2_displacement2d.py +0 -76
- pyvale/examples/ex3_3_displacement2d.py +0 -101
- pyvale/examples/ex3_4_displacement2d.py +0 -102
- pyvale/examples/ex4_1_strain2d.py +0 -54
- pyvale/examples/ex4_2_strain2d.py +0 -76
- pyvale/examples/ex4_3_strain2d.py +0 -97
- pyvale/examples/ex5_1_multiphysics2d.py +0 -75
- pyvale/examples/ex6_1_multiphysics2d_expsim.py +0 -115
- pyvale/examples/ex6_2_multiphysics3d_expsim.py +0 -160
- pyvale/examples/features/__init__.py +0 -5
- pyvale/examples/features/ex_area_avg.py +0 -89
- pyvale/examples/features/ex_calibration_error.py +0 -108
- pyvale/examples/features/ex_chain_field_errs.py +0 -141
- pyvale/examples/features/ex_field_errs.py +0 -78
- pyvale/examples/features/ex_sensor_single_angle_batch.py +0 -110
- pyvale/optimcheckfuncs.py +0 -153
- pyvale/visualsimplotter.py +0 -182
- pyvale-2025.4.1.dist-info/RECORD +0 -163
- {pyvale-2025.4.1.dist-info → pyvale-2025.5.1.dist-info}/licenses/LICENSE +0 -0
- {pyvale-2025.4.1.dist-info → pyvale-2025.5.1.dist-info}/top_level.txt +0 -0
pyvale/visualtraceplotter.py
CHANGED
|
@@ -1,36 +1,59 @@
|
|
|
1
|
-
#
|
|
1
|
+
# ==============================================================================
|
|
2
2
|
# pyvale: the python validation engine
|
|
3
3
|
# License: MIT
|
|
4
4
|
# Copyright (C) 2025 The Computer Aided Validation Team
|
|
5
|
-
#
|
|
5
|
+
# ==============================================================================
|
|
6
6
|
|
|
7
7
|
from typing import Any
|
|
8
|
-
|
|
9
8
|
import numpy as np
|
|
10
9
|
import matplotlib.pyplot as plt
|
|
11
10
|
from pyvale.sensorarraypoint import SensorArrayPoint
|
|
12
11
|
from pyvale.visualopts import (PlotOptsGeneral,
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
from pyvale.experimentsimulator import ExperimentSimulator
|
|
12
|
+
TraceOptsSensor)
|
|
13
|
+
|
|
16
14
|
|
|
17
|
-
#TODO: Docstrings
|
|
18
15
|
|
|
16
|
+
# TODO: this should probably take an ISensorarray
|
|
19
17
|
def plot_time_traces(sensor_array: SensorArrayPoint,
|
|
20
|
-
component: str,
|
|
18
|
+
component: str | None = None,
|
|
21
19
|
trace_opts: TraceOptsSensor | None = None,
|
|
22
20
|
plot_opts: PlotOptsGeneral | None = None
|
|
23
21
|
) -> tuple[Any,Any]:
|
|
24
|
-
|
|
22
|
+
"""Plots time traces for the truth and virtual experiments of the sensors
|
|
23
|
+
in the given sensor array.
|
|
24
|
+
|
|
25
|
+
Parameters
|
|
26
|
+
----------
|
|
27
|
+
sensor_array : SensorArrayPoint
|
|
28
|
+
_description
|
|
29
|
+
component : str | None
|
|
30
|
+
String key for the field component to plot, by default None. If None
|
|
31
|
+
then the first component in the measurement array is plotted
|
|
32
|
+
trace_opts : TraceOptsSensor | None, optional
|
|
33
|
+
Dataclass containing specific options for controlling the plot
|
|
34
|
+
appearance, by default None. If None the default options are used.
|
|
35
|
+
plot_opts : PlotOptsGeneral | None, optional
|
|
36
|
+
Dataclass containing general options for formatting plots and
|
|
37
|
+
visualisations, by default None. If None the default options are used.
|
|
38
|
+
|
|
39
|
+
Returns
|
|
40
|
+
-------
|
|
41
|
+
tuple[Any,Any]
|
|
42
|
+
A tuple containing a handle to the matplotlib figure and axis objects:
|
|
43
|
+
(fig,ax).
|
|
44
|
+
"""
|
|
25
45
|
#---------------------------------------------------------------------------
|
|
26
|
-
field = sensor_array.
|
|
27
|
-
comp_ind = sensor_array.field.get_component_index(component)
|
|
46
|
+
field = sensor_array._field
|
|
28
47
|
samp_time = sensor_array.get_sample_times()
|
|
29
48
|
measurements = sensor_array.get_measurements()
|
|
30
|
-
|
|
31
|
-
descriptor = sensor_array.
|
|
49
|
+
num_sens = sensor_array._sensor_data.positions.shape[0]
|
|
50
|
+
descriptor = sensor_array._descriptor
|
|
32
51
|
sensors_perturbed = sensor_array.get_sensor_data_perturbed()
|
|
33
52
|
|
|
53
|
+
comp_ind = 0
|
|
54
|
+
if component is not None:
|
|
55
|
+
comp_ind = sensor_array._field.get_component_index(component)
|
|
56
|
+
|
|
34
57
|
#---------------------------------------------------------------------------
|
|
35
58
|
if plot_opts is None:
|
|
36
59
|
plot_opts = PlotOptsGeneral()
|
|
@@ -39,23 +62,23 @@ def plot_time_traces(sensor_array: SensorArrayPoint,
|
|
|
39
62
|
trace_opts = TraceOptsSensor()
|
|
40
63
|
|
|
41
64
|
if trace_opts.sensors_to_plot is None:
|
|
42
|
-
sensors_to_plot = range(
|
|
65
|
+
sensors_to_plot = range(num_sens)
|
|
43
66
|
else:
|
|
44
67
|
sensors_to_plot = trace_opts.sensors_to_plot
|
|
45
68
|
|
|
46
69
|
#---------------------------------------------------------------------------
|
|
47
70
|
# Figure canvas setup
|
|
48
71
|
fig, ax = plt.subplots(figsize=plot_opts.single_fig_size_landscape,
|
|
49
|
-
layout=
|
|
72
|
+
layout="constrained")
|
|
50
73
|
fig.set_dpi(plot_opts.resolution)
|
|
51
74
|
|
|
52
75
|
#---------------------------------------------------------------------------
|
|
53
76
|
# Plot simulation and truth lines
|
|
54
77
|
if trace_opts.sim_line is not None:
|
|
55
78
|
sim_time = field.get_time_steps()
|
|
56
|
-
sim_vals = field.sample_field(sensor_array.
|
|
79
|
+
sim_vals = field.sample_field(sensor_array._sensor_data.positions,
|
|
57
80
|
None,
|
|
58
|
-
sensor_array.
|
|
81
|
+
sensor_array._sensor_data.angles)
|
|
59
82
|
|
|
60
83
|
for ii,ss in enumerate(sensors_to_plot):
|
|
61
84
|
ax.plot(sim_time,
|
|
@@ -63,7 +86,7 @@ def plot_time_traces(sensor_array: SensorArrayPoint,
|
|
|
63
86
|
trace_opts.sim_line,
|
|
64
87
|
lw=plot_opts.lw,
|
|
65
88
|
ms=plot_opts.ms,
|
|
66
|
-
color=plot_opts.colors[ii % plot_opts.
|
|
89
|
+
color=plot_opts.colors[ii % plot_opts.colors_num])
|
|
67
90
|
|
|
68
91
|
if trace_opts.truth_line is not None:
|
|
69
92
|
truth = sensor_array.get_truth()
|
|
@@ -73,22 +96,25 @@ def plot_time_traces(sensor_array: SensorArrayPoint,
|
|
|
73
96
|
trace_opts.truth_line,
|
|
74
97
|
lw=plot_opts.lw,
|
|
75
98
|
ms=plot_opts.ms,
|
|
76
|
-
color=plot_opts.colors[ii % plot_opts.
|
|
99
|
+
color=plot_opts.colors[ii % plot_opts.colors_num])
|
|
77
100
|
|
|
78
|
-
sensor_tags = descriptor.create_sensor_tags(
|
|
101
|
+
sensor_tags = descriptor.create_sensor_tags(num_sens)
|
|
102
|
+
lines = []
|
|
79
103
|
for ii,ss in enumerate(sensors_to_plot):
|
|
80
104
|
sensor_time = samp_time
|
|
81
105
|
if sensors_perturbed is not None:
|
|
82
106
|
if sensors_perturbed.sample_times is not None:
|
|
83
107
|
sensor_time = sensors_perturbed.sample_times
|
|
84
108
|
|
|
85
|
-
ax.plot(sensor_time,
|
|
109
|
+
line, = ax.plot(sensor_time,
|
|
86
110
|
measurements[ss,comp_ind,:],
|
|
87
111
|
trace_opts.meas_line,
|
|
88
112
|
label=sensor_tags[ss],
|
|
89
113
|
lw=plot_opts.lw,
|
|
90
114
|
ms=plot_opts.ms,
|
|
91
|
-
color=plot_opts.colors[ii % plot_opts.
|
|
115
|
+
color=plot_opts.colors[ii % plot_opts.colors_num])
|
|
116
|
+
|
|
117
|
+
lines.append(line)
|
|
92
118
|
|
|
93
119
|
#---------------------------------------------------------------------------
|
|
94
120
|
# Axis / legend labels and options
|
|
@@ -104,152 +130,13 @@ def plot_time_traces(sensor_array: SensorArrayPoint,
|
|
|
104
130
|
else:
|
|
105
131
|
ax.set_xlim(trace_opts.time_min_max)
|
|
106
132
|
|
|
107
|
-
if trace_opts.
|
|
108
|
-
ax.legend(
|
|
133
|
+
if trace_opts.legend_loc is not None:
|
|
134
|
+
ax.legend(handles=lines,
|
|
135
|
+
prop={"size":plot_opts.font_leg_size},
|
|
136
|
+
loc=trace_opts.legend_loc)
|
|
109
137
|
|
|
110
138
|
plt.grid(True)
|
|
111
139
|
plt.draw()
|
|
112
140
|
|
|
113
141
|
return (fig,ax)
|
|
114
142
|
|
|
115
|
-
|
|
116
|
-
def plot_exp_traces(exp_sim: ExperimentSimulator,
|
|
117
|
-
component: str,
|
|
118
|
-
sens_array_num: int,
|
|
119
|
-
sim_num: int,
|
|
120
|
-
trace_opts: TraceOptsExperiment | None = None,
|
|
121
|
-
plot_opts: PlotOptsGeneral | None = None) -> tuple[Any,Any]:
|
|
122
|
-
#---------------------------------------------------------------------------
|
|
123
|
-
n_sensors = exp_sim.sensor_arrays[sens_array_num].sensor_data.positions.shape[0]
|
|
124
|
-
descriptor = exp_sim.sensor_arrays[sens_array_num].descriptor
|
|
125
|
-
comp_ind = exp_sim.sensor_arrays[sens_array_num].field.get_component_index(component)
|
|
126
|
-
samp_time = exp_sim.sensor_arrays[sens_array_num].get_sample_times()
|
|
127
|
-
num_sens = exp_sim.sensor_arrays[sens_array_num].get_measurement_shape()[0]
|
|
128
|
-
|
|
129
|
-
#---------------------------------------------------------------------------
|
|
130
|
-
if trace_opts is None:
|
|
131
|
-
trace_opts = TraceOptsExperiment()
|
|
132
|
-
|
|
133
|
-
if plot_opts is None:
|
|
134
|
-
plot_opts = PlotOptsGeneral()
|
|
135
|
-
|
|
136
|
-
#---------------------------------------------------------------------------
|
|
137
|
-
exp_data = exp_sim.get_data()
|
|
138
|
-
exp_stats = exp_sim.get_stats()
|
|
139
|
-
|
|
140
|
-
if trace_opts.sensors_to_plot is None:
|
|
141
|
-
sensors_to_plot = range(num_sens)
|
|
142
|
-
else:
|
|
143
|
-
sensors_to_plot = trace_opts.sensors_to_plot
|
|
144
|
-
|
|
145
|
-
#---------------------------------------------------------------------------
|
|
146
|
-
# Figure canvas setup
|
|
147
|
-
fig, ax = plt.subplots(figsize=plot_opts.single_fig_size_landscape,
|
|
148
|
-
layout='constrained')
|
|
149
|
-
fig.set_dpi(plot_opts.resolution)
|
|
150
|
-
|
|
151
|
-
#---------------------------------------------------------------------------
|
|
152
|
-
# Plot all simulated experimental points
|
|
153
|
-
if trace_opts.plot_all_exp_points:
|
|
154
|
-
for ii,ss in enumerate(sensors_to_plot):
|
|
155
|
-
for ee in range(exp_sim.num_exp_per_sim):
|
|
156
|
-
ax.plot(samp_time,
|
|
157
|
-
exp_data[sens_array_num][sim_num,ee,ss,comp_ind,:],
|
|
158
|
-
"+",
|
|
159
|
-
lw=plot_opts.lw,
|
|
160
|
-
ms=plot_opts.ms,
|
|
161
|
-
color=plot_opts.colors[ii % plot_opts.n_colors])
|
|
162
|
-
|
|
163
|
-
#---------------------------------------------------------------------------
|
|
164
|
-
sensor_tags = descriptor.create_sensor_tags(n_sensors)
|
|
165
|
-
for ii,ss in enumerate(sensors_to_plot):
|
|
166
|
-
if trace_opts.centre == "median":
|
|
167
|
-
ax.plot(samp_time,
|
|
168
|
-
exp_stats[sens_array_num].median[sim_num,ss,comp_ind,:],
|
|
169
|
-
trace_opts.exp_mean_line,
|
|
170
|
-
label=sensor_tags[ss],
|
|
171
|
-
lw=plot_opts.lw,
|
|
172
|
-
ms=plot_opts.ms,
|
|
173
|
-
color=plot_opts.colors[ii % plot_opts.n_colors])
|
|
174
|
-
else:
|
|
175
|
-
ax.plot(samp_time,
|
|
176
|
-
exp_stats[sens_array_num].mean[sim_num,ss,comp_ind,:],
|
|
177
|
-
trace_opts.exp_mean_line,
|
|
178
|
-
label=sensor_tags[ss],
|
|
179
|
-
lw=plot_opts.lw,
|
|
180
|
-
ms=plot_opts.ms,
|
|
181
|
-
color=plot_opts.colors[ii % plot_opts.n_colors])
|
|
182
|
-
|
|
183
|
-
if trace_opts is not None:
|
|
184
|
-
upper = np.zeros_like(exp_stats[sens_array_num].min)
|
|
185
|
-
lower = np.zeros_like(exp_stats[sens_array_num].min)
|
|
186
|
-
|
|
187
|
-
if trace_opts.fill_between == 'max':
|
|
188
|
-
upper = exp_stats[sens_array_num].min
|
|
189
|
-
lower = exp_stats[sens_array_num].max
|
|
190
|
-
|
|
191
|
-
elif trace_opts.fill_between == 'quartile':
|
|
192
|
-
upper = exp_stats[sens_array_num].q25
|
|
193
|
-
lower = exp_stats[sens_array_num].q75
|
|
194
|
-
|
|
195
|
-
elif trace_opts.fill_between == '2std':
|
|
196
|
-
upper = exp_stats[sens_array_num].mean + \
|
|
197
|
-
2*exp_stats[sens_array_num].std
|
|
198
|
-
lower = exp_stats[sens_array_num].mean - \
|
|
199
|
-
2*exp_stats[sens_array_num].std
|
|
200
|
-
|
|
201
|
-
elif trace_opts.fill_between == '3std':
|
|
202
|
-
upper = exp_stats[sens_array_num].mean + \
|
|
203
|
-
3*exp_stats[sens_array_num].std
|
|
204
|
-
lower = exp_stats[sens_array_num].mean - \
|
|
205
|
-
3*exp_stats[sens_array_num].std
|
|
206
|
-
|
|
207
|
-
ax.fill_between(samp_time,
|
|
208
|
-
upper[sim_num,ss,comp_ind,:],
|
|
209
|
-
lower[sim_num,ss,comp_ind,:],
|
|
210
|
-
color=plot_opts.colors[ii % plot_opts.n_colors],
|
|
211
|
-
alpha=0.2)
|
|
212
|
-
|
|
213
|
-
#---------------------------------------------------------------------------
|
|
214
|
-
# Plot simulation and truth line
|
|
215
|
-
if trace_opts.sim_line is not None:
|
|
216
|
-
sim_time = exp_sim.sensor_arrays[sens_array_num].field.get_time_steps()
|
|
217
|
-
sim_vals = exp_sim.sensor_arrays[sens_array_num].field.sample_field(
|
|
218
|
-
exp_sim.sensor_arrays[sens_array_num].positions)
|
|
219
|
-
|
|
220
|
-
for ss in sensors_to_plot:
|
|
221
|
-
ax.plot(sim_time,
|
|
222
|
-
sim_vals[ss,comp_ind,:],
|
|
223
|
-
trace_opts.sim_line,
|
|
224
|
-
lw=plot_opts.lw,
|
|
225
|
-
ms=plot_opts.ms)
|
|
226
|
-
|
|
227
|
-
if trace_opts.truth_line is not None:
|
|
228
|
-
truth = exp_sim.sensor_arrays[sens_array_num].get_truth()
|
|
229
|
-
for ss in sensors_to_plot:
|
|
230
|
-
ax.plot(samp_time,
|
|
231
|
-
truth[ss,comp_ind,:],
|
|
232
|
-
trace_opts.truth_line,
|
|
233
|
-
lw=plot_opts.lw,
|
|
234
|
-
ms=plot_opts.ms,
|
|
235
|
-
color=plot_opts.colors[ii % plot_opts.n_colors])
|
|
236
|
-
|
|
237
|
-
#---------------------------------------------------------------------------
|
|
238
|
-
# Axis / legend labels and options
|
|
239
|
-
ax.set_xlabel(trace_opts.time_label,
|
|
240
|
-
fontsize=plot_opts.font_ax_size, fontname=plot_opts.font_name)
|
|
241
|
-
ax.set_ylabel(descriptor.create_label(comp_ind),
|
|
242
|
-
fontsize=plot_opts.font_ax_size, fontname=plot_opts.font_name)
|
|
243
|
-
|
|
244
|
-
if trace_opts.time_min_max is None:
|
|
245
|
-
ax.set_xlim((np.min(samp_time),np.max(samp_time))) # type: ignore
|
|
246
|
-
else:
|
|
247
|
-
ax.set_xlim(trace_opts.time_min_max)
|
|
248
|
-
|
|
249
|
-
if trace_opts.legend:
|
|
250
|
-
ax.legend(prop={"size":plot_opts.font_leg_size},loc='best')
|
|
251
|
-
|
|
252
|
-
plt.grid(True)
|
|
253
|
-
plt.draw()
|
|
254
|
-
|
|
255
|
-
return (fig,ax)
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: pyvale
|
|
3
|
-
Version: 2025.
|
|
3
|
+
Version: 2025.5.1
|
|
4
4
|
Summary: An all-in-one package for sensor simulation, sensor uncertainty quantification, sensor placement optimisation and simulation calibration or validation.
|
|
5
5
|
Author-email: "scepticalrabbit et al." <thescepticalrabbit@gmail.com>
|
|
6
6
|
License: MIT License
|
|
@@ -44,15 +44,19 @@ Requires-Dist: numba>=0.59.1
|
|
|
44
44
|
Requires-Dist: pymoo>=0.6.1.3
|
|
45
45
|
Requires-Dist: Cython>=3.0.0
|
|
46
46
|
Requires-Dist: bpy>=4.2.0
|
|
47
|
+
Requires-Dist: pyyaml>=6.0.2
|
|
48
|
+
Requires-Dist: pytest>=8.3.5
|
|
47
49
|
Dynamic: license-file
|
|
48
50
|
|
|
49
51
|
# pyvale
|
|
50
52
|
The python validation engine (`pyvale`): An all-in-one package for sensor simulation, sensor uncertainty quantification, sensor placement optimisation and simulation calibration/validation. Used to simulate experimental data from an input multi-physics simulation by explicitly modelling sensors with realistic uncertainties. Useful for experimental design, sensor placement optimisation, testing simulation validation metrics and virtually testing digital shadows/twins.
|
|
51
53
|
|
|
52
54
|
## Quick Demo: Simulating Point Sensors
|
|
53
|
-
Here we demonstrate how `pyvale` can be used to simulate thermocouples and strain gauges applied to a [MOOSE](https://mooseframework.inl.gov/index.html) thermo-mechanical simulation of a fusion divertor armour heatsink. The figures below show visualisations of the virtual thermocouple and strain gauge locations on the simualtion mesh as well as time traces for each sensor over a series of simulated experiments.
|
|
55
|
+
Here we demonstrate how `pyvale` can be used to simulate thermocouples and strain gauges applied to a [MOOSE](https://mooseframework.inl.gov/index.html) thermo-mechanical simulation of a fusion divertor armour heatsink. The figures below show visualisations of the virtual thermocouple and strain gauge locations on the simualtion mesh as well as time traces for each sensor over a series of simulated experiments.
|
|
54
56
|
|
|
55
|
-
|
|
57
|
+
The code to run the simulated experiments and produce the output shown here comes from [this example](https://computer-aided-validation-laboratory.github.io/pyvale/examples/point/ex4_2.html). You can find more examples and details of `pyvale` python API in the `pyvale` [documentation](https://computer-aided-validation-laboratory.github.io/pyvale/index.html).
|
|
58
|
+
|
|
59
|
+
|||
|
|
56
60
|
|--|--|
|
|
57
61
|
|*Visualisation of the thermcouple locations.*|*Visualisation of the strain gauge locations.*|
|
|
58
62
|
|
|
@@ -118,21 +122,20 @@ pip install -e .
|
|
|
118
122
|
pip install -e ./dependencies/mooseherder
|
|
119
123
|
```
|
|
120
124
|
|
|
121
|
-
### MOOSE
|
|
125
|
+
### Running Physics Simulations with MOOSE
|
|
122
126
|
`pyvale` come pre-packaged with example `moose` physics simulation outputs (as *.e exodus files) to demonstrate its functionality. If you need to run additional simulation cases we recommend `proteus` (https://github.com/aurora-multiphysics/proteus) which has build scripts for common linux distributions.
|
|
123
127
|
|
|
124
|
-
## Getting Started
|
|
125
|
-
The examples folder in "pyvale/examples" includes a sequence of examples of increasing complexity that demonstrate the functionality of `pyvale`.
|
|
126
|
-
|
|
127
128
|
## Contributors
|
|
128
129
|
The Computer Aided Validation Team at UKAEA:
|
|
129
|
-
- Lloyd Fletcher (ScepticalRabbit), UK Atomic Energy Authority
|
|
130
|
-
-
|
|
131
|
-
-
|
|
132
|
-
- Lorna Sibson (lornasibson), UK Atomic Energy Authority
|
|
133
|
-
-
|
|
134
|
-
-
|
|
135
|
-
-
|
|
130
|
+
- Lloyd Fletcher ([ScepticalRabbit](https://github.com/ScepticalRabbit)), UK Atomic Energy Authority
|
|
131
|
+
- Joel Hirst ([JoelPhys](https://github.com/JoelPhys)), UK Atomic Energy Authority
|
|
132
|
+
- John Charlton ([coolmule0](https://github.com/coolmule0)), UK Atomic Energy Authority
|
|
133
|
+
- Lorna Sibson ([lornasibson](https://github.com/lornasibson)), UK Atomic Energy Authority
|
|
134
|
+
- Megan Sampson ([meganasampson](https://github.com/meganasampson)), UK Atomic Energy Authority
|
|
135
|
+
- Michael Atkinson ([mikesmic](https://github.com/mikesmic)), UK Atomic Energy Authority
|
|
136
|
+
- Adel Tayeb ([3adelTayeb](https://github.com/3adelTayeb)), UK Atomic Energy Authority
|
|
137
|
+
- Alex Marsh ([alexmarsh2](https://github.com/alexmarsh2)), UK Atomic Energy Authority
|
|
138
|
+
- Rory Spencer ([fusmatrs](https://github.com/orgs/Computer-Aided-Validation-Laboratory/people/fusmatrs)), UK Atomic Energy Authority
|
|
136
139
|
|
|
137
140
|
|
|
138
141
|
|
|
@@ -0,0 +1,172 @@
|
|
|
1
|
+
pyvale/__init__.py,sha256=61KOsSmlV9ojm_naGhl4NirlLkhGKeUn6jdbnmHs6Rg,2820
|
|
2
|
+
pyvale/analyticmeshgen.py,sha256=tMh8Fo7iJqjaMfhLu2gBLyD4L2SRGaXjCB3w3cVO7KE,3424
|
|
3
|
+
pyvale/analyticsimdatafactory.py,sha256=WWk1XfigI0q17rTQwZClRvumEGEwHLpameBOXvWHsT4,2703
|
|
4
|
+
pyvale/analyticsimdatagenerator.py,sha256=H_Ro3L8uih2Ipv63ckPN3LmvUaebysCvtJAz1b8Iefs,12424
|
|
5
|
+
pyvale/blendercalibrationdata.py,sha256=N2ntMuYRuic7uDyM7IgOW8VRk75l0zYjvWWtkMiAUGo,487
|
|
6
|
+
pyvale/blenderlightdata.py,sha256=syeXDH6ggVsUJpkw9yIoDJROBRoQGLQjE5wkLEd6Ifg,734
|
|
7
|
+
pyvale/blendermaterialdata.py,sha256=igb5cZwRq5VVC-9dd-I66hT4Jh2idjxjVgVa6F9YV7k,508
|
|
8
|
+
pyvale/blenderrenderdata.py,sha256=8WWuPpUch53QgEwDwjY1-KAGmh-SyUfr2Alg2DYf2PA,889
|
|
9
|
+
pyvale/blenderscene.py,sha256=-S0vCukWavzr8ITtujwzw78RYYzU9AzVj_lHv_1wof8,21262
|
|
10
|
+
pyvale/blendertools.py,sha256=FBcYb0F5m3WXVAGYFy0fu1Uajko7O8g5lqHADWqXG6w,17120
|
|
11
|
+
pyvale/camera.py,sha256=leH2fd3FbvidZ5v7rf04CMPGT_ozIVQkSIKuvFHRGsw,5331
|
|
12
|
+
pyvale/cameradata.py,sha256=ogGlrUqA7uB8JNdLMkpDBTHbGORYqahro21auyS5U1w,1918
|
|
13
|
+
pyvale/cameradata2d.py,sha256=O3imDz8BUer6Wxo82KzCQrVLIBDL5RLy8aNoQoKG4b0,2736
|
|
14
|
+
pyvale/camerastereo.py,sha256=_icc2BvdYnExL9vkuf2adXyejUh2oDFsv6QeKdJ2M3s,9905
|
|
15
|
+
pyvale/cameratools.py,sha256=xGim_-SPvOIWvvAjSspT-7VF8gAGyO56IWteVD-fTxI,20318
|
|
16
|
+
pyvale/dataset.py,sha256=F9X3rPhOwaAXoJxc-MaNiIf0gNTN0JnHvklT6_lGOTw,12360
|
|
17
|
+
pyvale/errorcalculator.py,sha256=lvxY-NCnC_oHw7OWh9N0D8IzcE2NvWprVrRBKXzWdsY,3418
|
|
18
|
+
pyvale/errordriftcalc.py,sha256=T8kqVlVz4GEMOL7WTyv1G7gCJKkulZPHyc5KrVufWAo,4428
|
|
19
|
+
pyvale/errorintegrator.py,sha256=mR8hA1dmylWd-jEHT8HkZFdXOxTGwC2OTKk0uBfdiro,13802
|
|
20
|
+
pyvale/errorrand.py,sha256=YRaEEjMpEyFtk8o8I7P8R0d-0CNONXWSnIomjXHc4sM,22192
|
|
21
|
+
pyvale/errorsyscalib.py,sha256=bcea3iHwCWY-fqo9hqkFsPX12Ym0sOXjzGVW1VNtiUc,5582
|
|
22
|
+
pyvale/errorsysdep.py,sha256=nE4mAnfAK1146_Z5cuEkLvoadXdGw-Tm5IPSb6ydLXE,11571
|
|
23
|
+
pyvale/errorsysfield.py,sha256=h7zgGETj_YQZQE-SdmL4oas0iSUqESBTRZnvUXHtPxY,17077
|
|
24
|
+
pyvale/errorsysindep.py,sha256=vbRjDoXvqQd4b6B2upcFUm_THTJjw1LtnDmLJWIK2VE,29631
|
|
25
|
+
pyvale/experimentsimulator.py,sha256=hDnyo8tV5SEKjSC0zUZIOQFtEK4UWzOyV0C7mfVoFHo,6898
|
|
26
|
+
pyvale/field.py,sha256=C2cfN9L53wk1bXYht_hO1UoUc9Vew-wzAmm5Hj12VvA,4532
|
|
27
|
+
pyvale/fieldconverter.py,sha256=f2FbFd_GMhR7W5r8VvuzGVAFwwCA58ZM-a61Zl_vu0Q,12610
|
|
28
|
+
pyvale/fieldsampler.py,sha256=-ukU3tAMtgk6FAehHPWH-ctE9Mh37mRWenQzZ5UDH1Q,4443
|
|
29
|
+
pyvale/fieldscalar.py,sha256=LrBb__lejqOGmkkI1q3fyKpbEiwgpx7Xf5fzB-JFlb8,5914
|
|
30
|
+
pyvale/fieldtensor.py,sha256=Ssa0R9UOG8C7DUkgUkFLLX-nHFjxxBjFwEXu5UhVFwg,8146
|
|
31
|
+
pyvale/fieldtransform.py,sha256=dzhHw6SlgdKEUbsy6Uh_8dp0sgx-dTH2TtjO7zSslos,17994
|
|
32
|
+
pyvale/fieldvector.py,sha256=VtodQyCTBPoe8L9bdJczoDl42q26qzvaj-lKinYMBT4,7926
|
|
33
|
+
pyvale/generatorsrandom.py,sha256=Ly4a2CUVj9JgWNwNykXBh6mEJEdaKgH0t24bgyUn800,16604
|
|
34
|
+
pyvale/imagedef2d.py,sha256=jqjW3mQqz62mxz-gypypA_5QhnMpHevvedpngEhl0e8,25117
|
|
35
|
+
pyvale/integratorfactory.py,sha256=c4YfUuntnPFiXZGKmRrOIKlgtWjLSY5RNeLvv84eLEU,9620
|
|
36
|
+
pyvale/integratorquadrature.py,sha256=0lVMH7NmVNVTuLHQRjp9gOSBpTDd8VFCxlfl8CyufZs,9035
|
|
37
|
+
pyvale/integratorrectangle.py,sha256=MaJ5ygSL1H7tDwhzFV86t_MuT21ZeM5b8_WH460Ke3o,6695
|
|
38
|
+
pyvale/integratorspatial.py,sha256=yN05AONJuy0Ued3pDlmSGo5Yu8NwSLBlSIO-9UV5zxk,3195
|
|
39
|
+
pyvale/integratortype.py,sha256=jfxdyhgOeowWLkb_ab-OB5G67PmnW-Q_mFENBJ7V9l8,1305
|
|
40
|
+
pyvale/output.py,sha256=OsAKbXMuSZT1yr_EKsslQsKQano7ge9H_8g9ep4AVt0,504
|
|
41
|
+
pyvale/pyvaleexceptions.py,sha256=vhXGitvM72L6Iezho14waCOqDGGCPjbW1n7V-r-xCeY,349
|
|
42
|
+
pyvale/raster.py,sha256=Z8YowjBPb8p4_c3xGu-CH0DT6Z5uajjTB8xuOZmDj6M,788
|
|
43
|
+
pyvale/rastercy.py,sha256=ty-sHAE_OJWEf0P-TJIRmTrRiCTzmDWmHrN11ka_lRk,2881
|
|
44
|
+
pyvale/rasternp.py,sha256=9EVae-M4-jtqr0vfkHQCshpeTO9NKQb0ASOYuGRY9Hc,25993
|
|
45
|
+
pyvale/rendermesh.py,sha256=xa5AqbRIqvpVRoi603zKF4JadvojhEIrapG1jZJYdIA,5414
|
|
46
|
+
pyvale/sensorarray.py,sha256=HC7DOSQtC1q5XE4hNr0KeWufd7z1qk3HoK_AMw9YRJk,7019
|
|
47
|
+
pyvale/sensorarrayfactory.py,sha256=3QCpwD_OpoQezoLT35WSzlnqojBoP9cbyLpBecvjUdg,7939
|
|
48
|
+
pyvale/sensorarraypoint.py,sha256=d42O0SRQcK6qVxSx4Zhu-nJNZis1F2ncXPL6xq7fiTU,11214
|
|
49
|
+
pyvale/sensordata.py,sha256=LFuROk6CcnDI1-0cSx83mk4sgrt4HnwswLItA8LsLVE,2764
|
|
50
|
+
pyvale/sensordescriptor.py,sha256=6-quSWdSMjp7qwcSJULEiOhICyI0TH-tJTH68qbW7dY,7073
|
|
51
|
+
pyvale/sensortools.py,sha256=2JDpUDG-18dtXRzEViqg9fdCmAhqrde6H9I5MpP_fC4,5731
|
|
52
|
+
pyvale/simtools.py,sha256=i9XKHRdw0yymSLydYqV4DBSWgZZS5ea_gmp3m1ny22I,2280
|
|
53
|
+
pyvale/visualexpplotter.py,sha256=tJGXbLr_lZDf8GVsqqkq5T4AoefjLxpo08wYCRwLiO4,7891
|
|
54
|
+
pyvale/visualimagedef.py,sha256=xlcT51guewx2AlWZlZ70RcfqgcghtO_E51kmM2G0xWM,2823
|
|
55
|
+
pyvale/visualimages.py,sha256=6u0FheaBdSLXYUBGOCTf-Zf7ylAYgY0HKXXj_PH0aIQ,2849
|
|
56
|
+
pyvale/visualopts.py,sha256=1jYi6qKWGcMSwKnFTcBtLdv-GRUJ-pnS3DOq5sr-J-U,14928
|
|
57
|
+
pyvale/visualsimanimator.py,sha256=ZhQyxaab82tAN3sVeIUs-Pg-3WggwsF3k-HS9e4MNFk,4456
|
|
58
|
+
pyvale/visualsimsensors.py,sha256=hINsI73NQvHunJ3lUZX-F0RrN_u6gzF0tMHZwsxHr34,12405
|
|
59
|
+
pyvale/visualtools.py,sha256=9nDMZHXv0N7HBl0vOL9QLeHlayYl6ng4dx2-5i2TJjw,4816
|
|
60
|
+
pyvale/visualtraceplotter.py,sha256=y-GjToF5U2VIGO-YwR_tKi_vMUO3ayhaohaWrWNUFgQ,5487
|
|
61
|
+
pyvale/cython/rastercyth.py,sha256=ji6XpRUk-POdwI0Oh1PdFBUCnY4RMiZEO77MyXTM6d0,24479
|
|
62
|
+
pyvale/data/__init__.py,sha256=h1zJBQZxFSPPUksp_ErTC1uTQLdSmoc-ry3D_naPKYE,271
|
|
63
|
+
pyvale/data/cal_target.tiff,sha256=4dbDIm7h7gYDJOhWOZXO-rs162ZLqxb1bdrbTykMEMk,4718962
|
|
64
|
+
pyvale/data/case00_HEX20_out.e,sha256=wTdEWvGyQBhP1D1bIy5YZKu7I_QISWLEjl9K9VOOnbI,241172
|
|
65
|
+
pyvale/data/case00_HEX27_out.e,sha256=XF1nLiBQcCJuZ4bXi8FUG3hbj5hpnno4by_hdyTVm4I,316644
|
|
66
|
+
pyvale/data/case00_HEX8_out.e,sha256=V52yZoQ4egI6v6JVkmA8DUVX6Q0K3AEWG8U3BbGHzSg,148268
|
|
67
|
+
pyvale/data/case00_TET10_out.e,sha256=eoIiAiQ5yLgiH2S01eMQRyHWGLfplnIAk6MPPcqEoPs,214036
|
|
68
|
+
pyvale/data/case00_TET14_out.e,sha256=t9s7WCV6gUlZfNcaj9q4_U7Sct9v9F77NQ0KU596GGk,316996
|
|
69
|
+
pyvale/data/case00_TET4_out.e,sha256=coeIyrkviOfgpgYauenoXldWnYulKgteOts6FolKYBM,127868
|
|
70
|
+
pyvale/data/case13_out.e,sha256=cqgs7TbyDtrlV4AxXUzULa0Qu50gbp_3VeQkehNT82g,150820
|
|
71
|
+
pyvale/data/case16_out.e,sha256=hmkiJQo4phaAPiEa9mgjggcUMn_yY2h348DSqMIj0pA,11614464
|
|
72
|
+
pyvale/data/case17_out.e,sha256=C5Zx0Xx8_iZqypPFbcutGPQtO5VNQaJmqg9YxWi0FHc,6095004
|
|
73
|
+
pyvale/data/case18_1_out.e,sha256=4ITunHIxCBCekUPipSv8j7IKDlhlwTaHe1e3wTN4qLE,1470776
|
|
74
|
+
pyvale/data/case18_2_out.e,sha256=Uz8U1TMBSe1YkRE4nRFMQ38Y11UQo9wb1cIbTRPua1Y,1470776
|
|
75
|
+
pyvale/data/case18_3_out.e,sha256=8dTnKLQOSCL-gle-1shL68GBQPW1go05aDvjO6AawAg,1470776
|
|
76
|
+
pyvale/data/case25_out.e,sha256=LWnCKG7GDUvzCs7GI1h25dhIhq6_qJgXnkhiTmdynPw,93748
|
|
77
|
+
pyvale/data/case26_out.e,sha256=UAoxPN0K1bbk9R0r2hDehuQZVCPHcAV5NA1PckRyXDY,225744
|
|
78
|
+
pyvale/data/optspeckle_2464x2056px_spec5px_8bit_gblur1px.tiff,sha256=cRmbiTzxc8QJ_aO9dc7YT21lV1c9K7pH-L9uQZvUQ8M,5046422
|
|
79
|
+
pyvale/examples/__init__.py,sha256=h1zJBQZxFSPPUksp_ErTC1uTQLdSmoc-ry3D_naPKYE,271
|
|
80
|
+
pyvale/examples/basics/ex1_1_basicscalars_therm2d.py,sha256=j9g-rhWf4-gW2DwDr2ur-DOkgVYYx-rH01aAQ87Re5U,6146
|
|
81
|
+
pyvale/examples/basics/ex1_2_sensormodel_therm2d.py,sha256=HzoJjJ_Pq1ukIeT7nn1Ao7hcywnfxx3K9MImD74eLGw,7145
|
|
82
|
+
pyvale/examples/basics/ex1_3_customsens_therm3d.py,sha256=IfVtucEdaI-k1CsNwcboOCPmU0kM4tKIOQBoRDfw21M,9765
|
|
83
|
+
pyvale/examples/basics/ex1_4_basicerrors_therm3d.py,sha256=BdFijiIzsZwExNq1xQFm8ut-sr3m1cZoUaDd7Eljcf4,6811
|
|
84
|
+
pyvale/examples/basics/ex1_5_fielderrs_therm3d.py,sha256=xTYASxpj5hhvxVoZbcmnGQVOR5_XfM_D-Ei44HttUH4,7344
|
|
85
|
+
pyvale/examples/basics/ex1_6_caliberrs_therm2d.py,sha256=5Q2n0aqDzOUheYgchGHWBn-kVPPce8MaEIIl_qcIVQw,5209
|
|
86
|
+
pyvale/examples/basics/ex1_7_spatavg_therm2d.py,sha256=TbdBvL0SmsbbGfylwe-WSKSJmT8yoy-4I5c_fNk6KEg,5442
|
|
87
|
+
pyvale/examples/basics/ex2_1_basicvectors_disp2d.py,sha256=HVb-d-TPOCjLsNf16N6bIUG35FUkf4Jb9136XANgiNo,4934
|
|
88
|
+
pyvale/examples/basics/ex2_2_vectorsens_disp2d.py,sha256=xhyVYSBp8LuOuhrGhssaPwF_dyp3qUhg2ZXNMsM-grY,5107
|
|
89
|
+
pyvale/examples/basics/ex2_3_sensangle_disp2d.py,sha256=PuZs3cVeb9Nol_9c6WgyD8TyA8UMDjs78AwdG-vBJqc,5643
|
|
90
|
+
pyvale/examples/basics/ex2_4_chainfielderrs_disp2d.py,sha256=q6kMdly2b-SSUbeaTRq0w5RZyeSAcwgEWyPKdy4ttI8,8383
|
|
91
|
+
pyvale/examples/basics/ex2_5_vectorfields3d_disp3d.py,sha256=LzI9P4lCAfzuwuE4DdGuw10WnmfS6Qk8CusOiS-zPyI,4439
|
|
92
|
+
pyvale/examples/basics/ex3_1_basictensors_strain2d.py,sha256=1bfgLAFf8M2LwqxEhUqErdc3hrvlEyZU0jrxPhAP7Dg,5071
|
|
93
|
+
pyvale/examples/basics/ex3_2_tensorsens2d_strain2d.py,sha256=vH2Trr3VGWhdPJM_3TNdfDXsOk-kDowftphPsqVoep8,4802
|
|
94
|
+
pyvale/examples/basics/ex3_3_tensorsens3d_strain3d.py,sha256=0g0hxeIosc8RN7hN2v8qMpN23FOjUlKzjds7-K7M_Dw,8420
|
|
95
|
+
pyvale/examples/basics/ex4_1_expsim2d_thermmech2d.py,sha256=SgO_luAOmAY7ZBuMZpPPnIYHwJsaDfhxonnIPh3iwwo,7926
|
|
96
|
+
pyvale/examples/basics/ex4_2_expsim3d_thermmech3d.py,sha256=u81CMU9P9q5vgrnBP1MXo34V_zo3PoN5XAtpi8vzpSU,11163
|
|
97
|
+
pyvale/examples/genanalyticdata/ex1_1_scalarvisualisation.py,sha256=4AeQXlzKAgXA3SjXpKoj2Pi9WVHDPlWp2N3tNdYf4M0,938
|
|
98
|
+
pyvale/examples/genanalyticdata/ex1_2_scalarcasebuild.py,sha256=E5eWebp-TQBH-46KqW5JfNZgo7OHpt_D-Yx_bVCsLgk,1272
|
|
99
|
+
pyvale/examples/genanalyticdata/ex2_1_analyticsensors.py,sha256=-IoroBX6QKvlMUdnHWQLEF9JS56mvKmTk_7f9fpzqbQ,2845
|
|
100
|
+
pyvale/examples/imagedef2d/ex_imagedef2d_todisk.py,sha256=hTSeDsDkDywl1M4zYelKE_u8RmX2qR5zwSYVrOoxwxg,2613
|
|
101
|
+
pyvale/examples/renderblender/ex1_1_blenderscene.py,sha256=EN4hT5gS0wWfj-rthlw6UANCbnKZG_MAG2zJSZ66kcA,5023
|
|
102
|
+
pyvale/examples/renderblender/ex1_2_blenderdeformed.py,sha256=BeWLlwcVvzH79vZ8bZ8A_a6Cfk4SgQfz7sEcvELanCk,5074
|
|
103
|
+
pyvale/examples/renderblender/ex2_1_stereoscene.py,sha256=5PkiAm6C_Rz5MZvc0uJ76paB8nurh93hq8aqBU0Roro,5458
|
|
104
|
+
pyvale/examples/renderblender/ex2_2_stereodeformed.py,sha256=kPCCiTckNAB6taQLiflFWmmtV2fWQKcwmxQmCcf2jmI,5629
|
|
105
|
+
pyvale/examples/renderblender/ex3_1_blendercalibration.py,sha256=oXpVs7kTVsNgJU2ou1SOYOunDKheHaQnLU2vrMBfC7E,5258
|
|
106
|
+
pyvale/examples/renderrasterisation/ex_rastenp.py,sha256=nkw42wsiLmVhNJcZpEySPrnTntJ6f6mS4ov5iLIxsRA,4848
|
|
107
|
+
pyvale/examples/renderrasterisation/ex_rastercyth_oneframe.py,sha256=TpNMhpixM0OnUT4q2l2eoVqx53j9A-pYLoKIZ7yRKt4,7437
|
|
108
|
+
pyvale/examples/renderrasterisation/ex_rastercyth_static_cypara.py,sha256=oyZYzYmkEyNUYwTBSHgWcrG4lKml7NKDO1sdlpKk8wE,6674
|
|
109
|
+
pyvale/examples/renderrasterisation/ex_rastercyth_static_pypara.py,sha256=0n_LDEHspZ5zwWzf5tvpaLhXFxWy_nHXJarl0XaZF5I,6756
|
|
110
|
+
pyvale/examples/visualisation/ex1_1_plot_traces.py,sha256=Vx4ZWOxwncyUHtXAOOR1YqEUFon8gkaTZ1Ne_K6AfO0,3252
|
|
111
|
+
pyvale/examples/visualisation/ex2_1_animate_sim.py,sha256=OdQpu33z5QZYHYdZdsntBc8K8gXCNFVCylNqoQv5RvA,2985
|
|
112
|
+
pyvale/simcases/case00_HEX20.i,sha256=UiKSQOGgAQwS3cWLxSMVixmp-1RzpZS3nKxVaIgWWKg,5149
|
|
113
|
+
pyvale/simcases/case00_HEX27.i,sha256=MJ3jXHf8hDQP-Y3Ew9FU3EAnD-7E4l8C4QjdeAoRrFc,5149
|
|
114
|
+
pyvale/simcases/case00_HEX8.i,sha256=R4NiWVjoyG8_y6Hhh_I_QySYzbEQ70QuiD0I4auA4Bc,5159
|
|
115
|
+
pyvale/simcases/case00_TET10.i,sha256=ijpTfoLb7ucLdgLyV7LimdIEnB3lLfykM_QJxAs2B9Q,5149
|
|
116
|
+
pyvale/simcases/case00_TET14.i,sha256=PlMC60P6prgpqCOSWAgU5VZ_0g_2WTxtQUYbAM2EaWk,5149
|
|
117
|
+
pyvale/simcases/case00_TET4.i,sha256=Ot9VqNO0s2RVWVmGqLcFcZ0dg9E3Z00BhfYFsOQkiKE,5159
|
|
118
|
+
pyvale/simcases/case01.i,sha256=R6t_uui6DywA1m5HLt4EsdkGDzobpGrfxBrfIY-5YiI,2184
|
|
119
|
+
pyvale/simcases/case02.i,sha256=gOPdUDVDnMUgqevcRO7vT5HnXTY64a7rmugSgkUqQ0s,3406
|
|
120
|
+
pyvale/simcases/case03.i,sha256=6LkfehTSTXuJ390mdn6tYp2Tkgo15KVpGmFmBrHo-AA,2848
|
|
121
|
+
pyvale/simcases/case04.i,sha256=Ao5z2qey2eJrqW1TmCm6LZRDeTwPTOFtMNPocH4zQO4,3757
|
|
122
|
+
pyvale/simcases/case05.i,sha256=VO2D38xsUrZmEMuEJF6JzjF_InpGAdrf9y_5FhvvvDw,5959
|
|
123
|
+
pyvale/simcases/case06.i,sha256=DLMHzOp3Kgu4EIXSg58Ltz4NRVTPC-dZbJp-g-vY3Uo,7298
|
|
124
|
+
pyvale/simcases/case07.geo,sha256=DxJjqex1zlQewGEcr_JiwbHSDczhOi-34ogvwAFfx_Q,4442
|
|
125
|
+
pyvale/simcases/case07.i,sha256=73YrdZUAGCddorbBBxY-oK0tLOw12lISYR5xzzi3ddc,1921
|
|
126
|
+
pyvale/simcases/case08.geo,sha256=d9QEIzMRRXynWOAHx07i8RxTA-uvKNVvpMAEBVZamKs,4795
|
|
127
|
+
pyvale/simcases/case08.i,sha256=G4MqwcZWAaKcXD3toDNtaghbJ3rxiZHWvL-zT6n021Y,3253
|
|
128
|
+
pyvale/simcases/case09.geo,sha256=zW9w_MQlfdbzXat7XfttiAP5HKIo6aCnUBWyGd8SlQQ,6858
|
|
129
|
+
pyvale/simcases/case09.i,sha256=3tZCH7MtvjE4GPLO-Tsigm8kmvc_Ma8H9kZ2e5wb3uQ,1924
|
|
130
|
+
pyvale/simcases/case10.geo,sha256=y4RRENzZyfzUey-wNK3dr448_j7ta70EgxReoaKP2vY,6839
|
|
131
|
+
pyvale/simcases/case10.i,sha256=5X7xsgqiXAZDx-q5erxiWg1XOdGlmfD9UZ7i4Lqg-nk,6377
|
|
132
|
+
pyvale/simcases/case11.geo,sha256=HDEMxIpANKUrDEgBfokxDohEoVpWMcfAcKJ1Rr8RW8c,10429
|
|
133
|
+
pyvale/simcases/case11.i,sha256=f34kuvrDNKjqjiyV0BmCeH3ZDDJFUTtkKmorK4YbAhc,3093
|
|
134
|
+
pyvale/simcases/case12.geo,sha256=FQ-Ck1LBsqnV4HDdLbIP1U2cRot7dRBTIlQ1n6GnxgE,12477
|
|
135
|
+
pyvale/simcases/case12.i,sha256=N-lJnOenl_PQhhatkjMLhUGNNGKLV0QPjLiWU0QfXGo,7932
|
|
136
|
+
pyvale/simcases/case13.i,sha256=q1KLk_S9AC15-ZNV_PydIp2QZsf_EUE1sth6a3t8cG8,3308
|
|
137
|
+
pyvale/simcases/case14.i,sha256=-Yq-ecGcs153-t-fHNM4kWBR3d4_joxmM7WAnm4O57w,3502
|
|
138
|
+
pyvale/simcases/case15.geo,sha256=Sgat1JQJeBCaSlGEEJ1o_WSZMpLpDkbhIrTaUKDiRX4,10429
|
|
139
|
+
pyvale/simcases/case15.i,sha256=88TAhiFxU9jGKnxJu8Ne4pWnbh9pHKkzSs0e0IjfUDM,3187
|
|
140
|
+
pyvale/simcases/case16.geo,sha256=SHB_GMofxN6WYq8JZ1Ktm8B8F_0L7K5hu4-DHtm3CX4,12554
|
|
141
|
+
pyvale/simcases/case16.i,sha256=TJDlkIcdQz2JypfVDobYXg6N86rk03w-AUlIdWV1l7s,8758
|
|
142
|
+
pyvale/simcases/case17.geo,sha256=lBMnrWGnYYivRqOIg5hfExRVr_jRjs1Zd9-f_ugitwA,4442
|
|
143
|
+
pyvale/simcases/case17.i,sha256=G0o57umdzOkzWoroREpV1IH6DA8QM2zAhdemul6-Y7w,3056
|
|
144
|
+
pyvale/simcases/case18.i,sha256=W3Hu6wwWCwOzxwZFmEB2tMlQ1VeCrs-r8erdbFWrqd0,6292
|
|
145
|
+
pyvale/simcases/case18_1.i,sha256=W3Hu6wwWCwOzxwZFmEB2tMlQ1VeCrs-r8erdbFWrqd0,6292
|
|
146
|
+
pyvale/simcases/case18_2.i,sha256=9Y2F3FCrLUJ78cP95CUKvsdCWGkWQLZbcqQ_WbeWPVs,6292
|
|
147
|
+
pyvale/simcases/case18_3.i,sha256=0K1IDUiK1WSjWJOpJi7hvUqJApFD4Z0m9JkCkivAevM,6292
|
|
148
|
+
pyvale/simcases/case19.geo,sha256=nT1Hch8Llv96z3QAPYqzpzIlaV01xXf1sozuA-m0-7I,9102
|
|
149
|
+
pyvale/simcases/case19.i,sha256=jRDSAWaC-bTxCeFgSyj1gapbo6iqteySuPR5QhPLKqo,2191
|
|
150
|
+
pyvale/simcases/case20.geo,sha256=TKBX8JKDwXKyXfXCi6fmOzDV_7_1Kpfpne9yeute11o,9102
|
|
151
|
+
pyvale/simcases/case20.i,sha256=wAQGXJbY_VniZPG-PzeL5-Sk6_ZUiwuf8zRV3c8nEz0,6655
|
|
152
|
+
pyvale/simcases/case21.geo,sha256=AzFNKkQp7-a9PojtR4y0GNI6g12BLvTRvkHDglYPRFQ,2387
|
|
153
|
+
pyvale/simcases/case21.i,sha256=QjKU97PMsswLkaGkutC7gdJhGY8lRq5VEf5b-gRhT4E,3417
|
|
154
|
+
pyvale/simcases/case22.geo,sha256=3OHJhFTm9P_G6vIB9fqgcpeT1DQt5xq5tWxOsRhvj2A,2491
|
|
155
|
+
pyvale/simcases/case22.i,sha256=b3IeO0hs4IU0PJlS_MIkF1gtPkKYQXklfNs5rhy9KNc,3189
|
|
156
|
+
pyvale/simcases/case23.geo,sha256=53NyuNJrPBgUWRHhgz0zS2fCZ8lavn_flpnfLUO2GNY,5448
|
|
157
|
+
pyvale/simcases/case23.i,sha256=0sRJTmiieHxb4YBnYH5foJGteQZfn5Fo0Z3TkDuLSoQ,3188
|
|
158
|
+
pyvale/simcases/case24.geo,sha256=3qiwipPbwaOjmPySISOZycYKdXCSDFrQpccnXHWhiU0,2408
|
|
159
|
+
pyvale/simcases/case24.i,sha256=6scn1ujqyQ2FUHm30NNZPwTzXD9w7AEDkzbrncah-xQ,2950
|
|
160
|
+
pyvale/simcases/case25.geo,sha256=k33GLvsApxTbxDbnOGueA3rTIazqcgYQ5DP37kCAPA4,2492
|
|
161
|
+
pyvale/simcases/case25.i,sha256=8lArbbZOCJ4aLuJCaEO5FW1kzJI4JquOmbA-nVpNRRI,2994
|
|
162
|
+
pyvale/simcases/case26.geo,sha256=7Qj0siF2FqgElxcmtX_7UDp4tdX6scnJgKffpP6iRQY,5468
|
|
163
|
+
pyvale/simcases/case26.i,sha256=V-pS7MeAo9vl3QUDtu-i6MQyeftryxSj0r8n7t6hY0k,2992
|
|
164
|
+
pyvale/simcases/run_1case.py,sha256=QmmZcawWmfkmImciEqM-8NedwlzuIOgLT2Te3fVb574,1928
|
|
165
|
+
pyvale/simcases/run_all_cases.py,sha256=9b3JYcxC8PA2CR-htum7wCICwwnLNeC01xAhk0m6yxw,1903
|
|
166
|
+
pyvale/simcases/run_build_case.py,sha256=IlyZC_VU095ayi7nz57xSSboTeJB54y7nsQXpBTUXFM,1938
|
|
167
|
+
pyvale/simcases/run_example_cases.py,sha256=l5KOQvPMNRUkJMotaReG2nmrFtVBNWCwKVezNyRwKb0,1910
|
|
168
|
+
pyvale-2025.5.1.dist-info/licenses/LICENSE,sha256=h2qWsRIazuLLhALyUsCP6aE0DFcswL9SSSt9sgMzZi4,1099
|
|
169
|
+
pyvale-2025.5.1.dist-info/METADATA,sha256=c1scLLW0CF-y-OV3hLheymbxPJrQXoxkYnkoCjMfweE,7448
|
|
170
|
+
pyvale-2025.5.1.dist-info/WHEEL,sha256=Nw36Djuh_5VDukK0H78QzOX-_FQEo6V37m3nkm96gtU,91
|
|
171
|
+
pyvale-2025.5.1.dist-info/top_level.txt,sha256=u1d_f4iZ3b3_96Rb_zrs9hyrpC4yE5e1Lg6Ey_Wgr0c,7
|
|
172
|
+
pyvale-2025.5.1.dist-info/RECORD,,
|
|
@@ -1,5 +0,0 @@
|
|
|
1
|
-
#===============================================================================
|
|
2
|
-
# pyvale: the python validation engine
|
|
3
|
-
# License: MIT
|
|
4
|
-
# Copyright (C) 2025 The Computer Aided Validation Team
|
|
5
|
-
#===============================================================================
|
|
@@ -1,86 +0,0 @@
|
|
|
1
|
-
# ================================================================================
|
|
2
|
-
# pyvale: the python validation engine
|
|
3
|
-
# License: MIT
|
|
4
|
-
# Copyright (C) 2025 The Computer Aided Validation Team
|
|
5
|
-
# ================================================================================
|
|
6
|
-
|
|
7
|
-
from pathlib import Path
|
|
8
|
-
import matplotlib.pyplot as plt
|
|
9
|
-
import mooseherder as mh
|
|
10
|
-
import pyvale as pyv
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
def main() -> None:
|
|
14
|
-
"""pyvale example: point sensors on a 2D thermal simulation
|
|
15
|
-
----------------------------------------------------------------------------
|
|
16
|
-
- Quick start
|
|
17
|
-
- Basic sensor array construction using the sensor array factory
|
|
18
|
-
- Basic visualisation of sensor locations and sensor traces with the pyvale
|
|
19
|
-
wrapper for pyvista and matplotlib.
|
|
20
|
-
"""
|
|
21
|
-
|
|
22
|
-
data_path = pyv.DataSet.thermal_2d_path()
|
|
23
|
-
sim_data = mh.ExodusReader(data_path).read_all_sim_data()
|
|
24
|
-
field_key = "temperature"
|
|
25
|
-
# Scale to mm to make 3D visualisation scaling easier
|
|
26
|
-
sim_data.coords = sim_data.coords*1000.0 # type: ignore
|
|
27
|
-
|
|
28
|
-
n_sens = (3,2,1)
|
|
29
|
-
x_lims = (0.0,100.0)
|
|
30
|
-
y_lims = (0.0,50.0)
|
|
31
|
-
z_lims = (0.0,0.0)
|
|
32
|
-
sens_pos = pyv.create_sensor_pos_array(n_sens,x_lims,y_lims,z_lims)
|
|
33
|
-
sens_data = pyv.SensorData(positions=sens_pos)
|
|
34
|
-
|
|
35
|
-
tc_array = pyv.SensorArrayFactory \
|
|
36
|
-
.thermocouples_basic_errs(sim_data,
|
|
37
|
-
sens_data,
|
|
38
|
-
field_key,
|
|
39
|
-
spat_dims=2)
|
|
40
|
-
|
|
41
|
-
measurements = tc_array.get_measurements()
|
|
42
|
-
print(f"\nMeasurements for last sensor:\n{measurements[-1,0,:]}\n")
|
|
43
|
-
|
|
44
|
-
pv_plot = pyv.plot_point_sensors_on_sim(tc_array,field_key)
|
|
45
|
-
# Set this to "interactive" to get an interactive 3D plot of the simulation
|
|
46
|
-
# and labelled sensor locations, set to "save_fig" to create a vector
|
|
47
|
-
# graphic using a specified camera position.
|
|
48
|
-
pv_plot_mode = "interactive"
|
|
49
|
-
|
|
50
|
-
if pv_plot_mode == "interactive":
|
|
51
|
-
pv_plot.camera_position = [(-7.547, 59.753, 134.52),
|
|
52
|
-
(41.916, 25.303, 9.297),
|
|
53
|
-
(0.0810, 0.969, -0.234)]
|
|
54
|
-
pv_plot.show()
|
|
55
|
-
|
|
56
|
-
print(80*"=")
|
|
57
|
-
print("Camera positions = ")
|
|
58
|
-
print(pv_plot.camera_position)
|
|
59
|
-
print(80*"="+"\n")
|
|
60
|
-
|
|
61
|
-
if pv_plot_mode == "save_fig":
|
|
62
|
-
# Determined manually by moving camera and then dumping camera position
|
|
63
|
-
# to console after window close - see "interactive above"
|
|
64
|
-
pv_plot.camera_position = [(-7.547, 59.753, 134.52),
|
|
65
|
-
(41.916, 25.303, 9.297),
|
|
66
|
-
(0.0810, 0.969, -0.234)]
|
|
67
|
-
save_render = Path("src/examples/plate_thermal_2d_sim_view.svg")
|
|
68
|
-
pv_plot.save_graphic(save_render) # only for .svg .eps .ps .pdf .tex
|
|
69
|
-
pv_plot.screenshot(save_render.with_suffix(".png"))
|
|
70
|
-
|
|
71
|
-
# Set this to "interactive" to get a matplotlib.pyplot with the sensor
|
|
72
|
-
# traces plotted over time. Set to "save_fig" to save an image of the plot
|
|
73
|
-
# to file.
|
|
74
|
-
trace_plot_mode = "interactive"
|
|
75
|
-
|
|
76
|
-
(fig,_) = pyv.plot_time_traces(tc_array,field_key)
|
|
77
|
-
|
|
78
|
-
if trace_plot_mode == "interactive":
|
|
79
|
-
plt.show()
|
|
80
|
-
if trace_plot_mode == "save_fig":
|
|
81
|
-
save_traces = Path("src/examples/plate_thermal_2d_traces.png")
|
|
82
|
-
fig.savefig(save_traces, dpi=300, format="png", bbox_inches="tight")
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
if __name__ == "__main__":
|
|
86
|
-
main()
|