petal-qc 0.0.15__py3-none-any.whl → 0.0.17__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.
Files changed (32) hide show
  1. petal_qc/BTreport/CheckBTtests.py +92 -33
  2. petal_qc/BTreport/bustapeReport.py +2 -1
  3. petal_qc/__init__.py +7 -2
  4. petal_qc/{test/getPetalCoreTestSummary.py → getPetalCoreTestSummary.py} +36 -14
  5. petal_qc/metrology/PetalMetrology.py +0 -13
  6. petal_qc/metrology/compare_Cores.py +44 -0
  7. petal_qc/metrology/coreMetrology.py +0 -12
  8. petal_qc/metrology/do_Metrology.py +0 -13
  9. petal_qc/metrology/petal_flatness.py +0 -13
  10. petal_qc/metrology/readAVSdata.py +2 -0
  11. petal_qc/metrology/uploadPetalInformation.py +20 -20
  12. petal_qc/test/analyzeMetrologyTable.py +119 -0
  13. petal_qc/test/checkAVStests.py +2 -2
  14. petal_qc/test/checkCoreShipments.py +57 -0
  15. petal_qc/test/createMetrologyTable.py +87 -0
  16. petal_qc/test/getAVStests.py +21 -3
  17. petal_qc/test/prepareDESYfiles.py +2 -1
  18. petal_qc/test/test_Graphana.py +2 -1
  19. petal_qc/thermal/IRPetalParam.py +2 -0
  20. petal_qc/thermal/PipeFit.py +48 -19
  21. petal_qc/thermal/analyze_IRCore.py +34 -24
  22. petal_qc/thermal/contours.py +18 -12
  23. petal_qc/thermal/create_IRCore.py +40 -9
  24. petal_qc/thermal/create_core_report.py +8 -5
  25. petal_qc/thermal/show_IR_petal.py +1 -10
  26. petal_qc/utils/ArgParserUtils.py +41 -0
  27. petal_qc/utils/docx_utils.py +18 -6
  28. {petal_qc-0.0.15.dist-info → petal_qc-0.0.17.dist-info}/METADATA +2 -2
  29. {petal_qc-0.0.15.dist-info → petal_qc-0.0.17.dist-info}/RECORD +32 -28
  30. {petal_qc-0.0.15.dist-info → petal_qc-0.0.17.dist-info}/WHEEL +1 -1
  31. {petal_qc-0.0.15.dist-info → petal_qc-0.0.17.dist-info}/entry_points.txt +1 -0
  32. {petal_qc-0.0.15.dist-info → petal_qc-0.0.17.dist-info}/top_level.txt +0 -0
@@ -175,7 +175,8 @@ def create_golden_average(files, options):
175
175
  for i in range(2):
176
176
  ax[i].plot(R.results[i].path_length, R.results[i].path_temp, label="original")
177
177
  ax[i].plot(R.golden[i].path_length, R.golden[i].path_temp, label="golden")
178
- ax[i].legend()
178
+ if options.legend:
179
+ ax[i].legend()
179
180
 
180
181
  # Create the golden object
181
182
  golden = [Petal_IR_Analysis.AnalysisResult() for i in range(2)]
@@ -216,7 +217,7 @@ def get_golden_axis(R, golden):
216
217
  R.golden.append(G)
217
218
 
218
219
 
219
- def plot_profile_and_golden(golden, core, value):
220
+ def plot_profile_and_golden(golden, core, value, show_legend=True):
220
221
  """Plot petal core and golden average.
221
222
 
222
223
  Args:
@@ -270,7 +271,9 @@ def plot_profile_and_golden(golden, core, value):
270
271
  Tmean = np.mean(Y)
271
272
  Tband = factor*abs(Tmean)/3
272
273
 
273
- ax[0].legend(ncol=4, fontsize="x-small")
274
+ if show_legend:
275
+ ax[0].legend(ncol=4, fontsize="x-small")
276
+
274
277
  ax[0].set_title("T$_{prof}$ values")
275
278
  if value.find("temp") >= 0 or value.find("_avg") >= 0:
276
279
  ax[0].set_ylim(Tmean-Tband, Tmean+Tband)
@@ -282,14 +285,16 @@ def plot_profile_and_golden(golden, core, value):
282
285
  facecolor="yellow", alpha=0.25,
283
286
  label="Acceptance band")
284
287
 
285
- ax[1].legend(ncol=4, fontsize="x-small")
288
+ if show_legend:
289
+ ax[1].legend(ncol=4, fontsize="x-small")
290
+
286
291
  ax[1].set_title("T$_{prof}$ - Golden avg.")
287
292
  if value.find("temp") >= 0 or value.find("_avg") >= 0:
288
293
  ax[1].set_ylim(-Tband, Tband)
289
294
 
290
295
  return figures
291
296
 
292
- def show_golden_average(golden, results, value):
297
+ def show_golden_average(golden, results, value, show_legend=True):
293
298
  """Create golden average.
294
299
 
295
300
  Args:
@@ -343,7 +348,9 @@ def show_golden_average(golden, results, value):
343
348
  Tband = factor*abs(Tmean)/3
344
349
  ax[0].plot(gX, gY, '-', label="Golden", linewidth=4, alpha=0.4, color="black")
345
350
 
346
- ax[0].legend(ncol=4, fontsize="x-small")
351
+ if show_legend:
352
+ ax[0].legend(ncol=4, fontsize="x-small")
353
+
347
354
  ax[0].set_title("T$_{prof}$ values")
348
355
  if value.find("temp") >= 0 or value.find("_avg") >= 0:
349
356
  ax[0].set_ylim(Tmean-Tband, Tmean+Tband)
@@ -357,7 +364,9 @@ def show_golden_average(golden, results, value):
357
364
  facecolor="yellow", alpha=0.25,
358
365
  label="Acceptance band")
359
366
 
360
- ax[1].legend(ncol=4, fontsize="x-small")
367
+ if show_legend:
368
+ ax[1].legend(ncol=4, fontsize="x-small")
369
+
361
370
  ax[1].set_title("T$_{prof}$ - Golden avg.")
362
371
  if value.find("temp") >= 0 or value.find("_avg") >= 0:
363
372
  ax[1].set_ylim(-Tband, Tband)
@@ -369,7 +378,7 @@ def compare_golden(core, golden, value):
369
378
 
370
379
  Args:
371
380
  ----
372
- core (AnalusysResolt): The petal core
381
+ core (AnalisysResult): The petal core
373
382
  golden (AnalysisResult): The golden avrage
374
383
  value (str): The name of the variable to compare
375
384
 
@@ -396,11 +405,11 @@ def compare_golden(core, golden, value):
396
405
  indx = bisect.bisect_left(gX, x, lo=(indx-1 if indx>1 else 0))
397
406
  val = gY[indx]
398
407
  diff = abs(y-val)
399
- if diff > mxval:
400
- mxval = diff
401
408
 
402
- if diff>band:
409
+ delta = abs(diff-band)/band
410
+ if diff>band and delta>0.01:
403
411
  outsiders.append(x)
412
+ mxval = max(diff, mxval)
404
413
 
405
414
  rc = mxval < band
406
415
  return rc, mxval, outsiders
@@ -439,7 +448,7 @@ def analyze_petal_cores(files, golden, options):
439
448
  cores.append(core)
440
449
  out = [{}, {}]
441
450
  for iside in range(2):
442
- for val in ("path_temp", "sensor_avg", "sensor_std"):
451
+ for val in ("path_temp", "sensor_avg"):
443
452
  out[iside][val] = compare_golden(core.results[iside], golden[iside], val)
444
453
 
445
454
  dbOut = {
@@ -488,8 +497,8 @@ def analyze_petal_cores(files, golden, options):
488
497
  "properties": {"msg": "{} > {}".format(val[1], get_acceptance_band())}
489
498
  }
490
499
  )
491
- dbOut["passed"] = (len(dbOut["defects"]) == 0)
492
- dbOut["problems"] = (len(dbOut["comments"]) > 0)
500
+ dbOut["passed"] = len(dbOut["defects"]) == 0
501
+ dbOut["problems"] = len(dbOut["comments"]) > 0
493
502
 
494
503
  if options.out is None:
495
504
  ofile = "{}-Thermal.json".format(core.coreID)
@@ -518,10 +527,10 @@ def analyze_IRCore(options, show=True):
518
527
  with open(ofile, 'w') as fp:
519
528
  json.dump(golden, fp, indent=3, cls=IRCore.NumpyArrayEncoder)
520
529
 
521
- show_golden_average(golden, results, "path_temp")
522
- show_golden_average(golden, results, "path_spread")
523
- show_golden_average(golden, results, "sensor_avg")
524
- show_golden_average(golden, results, "sensor_std")
530
+ show_golden_average(golden, results, "path_temp", options.legend)
531
+ show_golden_average(golden, results, "path_spread", options.legend)
532
+ show_golden_average(golden, results, "sensor_avg", options.legend)
533
+ show_golden_average(golden, results, "sensor_std", options.legend)
525
534
 
526
535
  else:
527
536
  if options.golden is None:
@@ -556,17 +565,17 @@ def analyze_IRCore(options, show=True):
556
565
  else:
557
566
  document = None
558
567
 
559
- F = show_golden_average(golden, cores, "path_temp")
568
+ F = show_golden_average(golden, cores, "path_temp", options.legend)
560
569
  add_figures_to_doc(document, F, "Temperature along pipe")
561
- F = show_golden_average(golden, cores, "path_spread")
570
+ F = show_golden_average(golden, cores, "path_spread", options.legend)
562
571
  add_figures_to_doc(document, F, "Spread along pipe")
563
- F = show_golden_average(golden, cores, "sensor_avg")
572
+ F = show_golden_average(golden, cores, "sensor_avg", options.legend)
564
573
  add_figures_to_doc(document, F, "Sensor avg")
565
- F = show_golden_average(golden, cores, "sensor_std")
574
+ F = show_golden_average(golden, cores, "sensor_std", options.legend)
566
575
  add_figures_to_doc(document, F, "Sensor std")
567
576
 
568
577
  if document and not hasattr(options, "no_golden_doc"):
569
- ofile = utils.output_folder(options.folder, "Compare-to-Golden.docx")
578
+ ofile = utils.output_folder(options.folder, options.comparison)
570
579
  document.save(ofile)
571
580
 
572
581
  if show:
@@ -588,9 +597,10 @@ def main():
588
597
  parser.add_argument("--prefix", default="golden", help="Prefix for figures")
589
598
  parser.add_argument("--debug", action="store_true", default=False, help="Set to debug")
590
599
  parser.add_argument("--report", action="store_true", default=False, help="Set to produce plots for report")
591
-
600
+ parser.add_argument("--no-legend", dest="legend", action="store_false", default=True, help="Do not show the legend in plots.")
592
601
  parser.add_argument("--out", default=None, help="File to store Golden.")
593
602
  parser.add_argument("--folder", default=None, help="Folder to store output files. Superseeds folder in --out")
603
+ parser.add_argument("--comparison", default="Compare-to-Golden.docx", help="Path to comparison to golden of all input files.")
594
604
 
595
605
  options = parser.parse_args()
596
606
  if len(options.files) == 0:
@@ -10,7 +10,7 @@ import sys
10
10
  import matplotlib.path as mplPath
11
11
  import numpy as np
12
12
 
13
- from petal_qc.utils.Geometry import Point
13
+ from petal_qc.utils.Geometry import Point, remove_outliers_indx
14
14
 
15
15
 
16
16
  def pldist(point, start, end):
@@ -48,9 +48,9 @@ def closest_segment_point(P, A, B):
48
48
 
49
49
  t0 = np.dot(P-A, M)/np.dot(M, M)
50
50
  C = A + t0*M
51
- d = np.linalg.norm(P-C)
51
+ dist = np.linalg.norm(P-C)
52
52
 
53
- return d, C
53
+ return dist, C
54
54
 
55
55
 
56
56
  def find_closest(x0, y0, cont, return_index=False):
@@ -170,10 +170,10 @@ def contour_simplify(C, epsilon, return_mask=False):
170
170
 
171
171
  for i in range(index + 1, last_index):
172
172
  if indices[i - global_start_index]:
173
- d = pldist(C[i], C[start_index], C[last_index])
174
- if d > dmax:
173
+ dist = pldist(C[i], C[start_index], C[last_index])
174
+ if dist > dmax:
175
175
  index = i
176
- dmax = d
176
+ dmax = dist
177
177
 
178
178
  if dmax > epsilon:
179
179
  stk.append([start_index, index])
@@ -259,7 +259,7 @@ def in_contour(x, y, C):
259
259
  return path.contains_point(x, y, C)
260
260
 
261
261
 
262
- def get_average_in_contour(img, C):
262
+ def get_average_in_contour(img, C, remove_outliers=None):
263
263
  """Gets average and std of points within contour.
264
264
 
265
265
  We are assuming here that coordinates are integers, ie,
@@ -269,6 +269,7 @@ def get_average_in_contour(img, C):
269
269
  ----
270
270
  img: The image
271
271
  C: The contour
272
+ remove_outliers: If an int,
272
273
 
273
274
  Returns
274
275
  -------
@@ -290,6 +291,11 @@ def get_average_in_contour(img, C):
290
291
  if path.contains_point([ix, iy]):
291
292
  values.append(img[iy, ix])
292
293
 
294
+ values = np.array(values)
295
+ if remove_outliers is not None and isinstance(remove_outliers, (int, float)):
296
+ indx = remove_outliers_indx(values, remove_outliers)[0]
297
+ return np.mean(values[indx]), np.std(values[indx])
298
+
293
299
  return np.mean(values), np.std(values)
294
300
 
295
301
 
@@ -360,16 +366,16 @@ def contour_eval(C, x):
360
366
 
361
367
 
362
368
  if __name__ == "__main__":
363
- C = np.loadtxt("long_contour.csv")
369
+ cntr = np.loadtxt("long_contour.csv")
364
370
 
365
- CM0 = contour_CM(C)
366
- d0, pt0 = find_closest_point(CM0[0], CM0[1], C)
371
+ CM0 = contour_CM(cntr)
372
+ d0, pt0 = find_closest_point(CM0[0], CM0[1], cntr)
367
373
 
368
- Cs = contour_simplify(C, 1.)
374
+ Cs = contour_simplify(cntr, 1.)
369
375
  CMs = contour_CM(Cs)
370
376
  ds, pts = find_closest_point(CM0[0], CM0[1], Cs)
371
377
  d = np.linalg.norm(pt0-pts)
372
- print("no. of points {}".format(len(C)))
378
+ print("no. of points {}".format(len(cntr)))
373
379
  print("no. of points {}".format(len(Cs)))
374
380
  print(d0)
375
381
  print(ds)
@@ -22,12 +22,14 @@ from petal_qc.thermal import IRCore
22
22
  from petal_qc.thermal import IRPetal
23
23
  from petal_qc.thermal import Petal_IR_Analysis
24
24
  from petal_qc.thermal import PipeFit
25
+ from petal_qc.thermal.PetalColorMaps import HighContrast
25
26
  from petal_qc.thermal.IRDataGetter import IRDataGetter
26
27
  from petal_qc.thermal.IRPetalParam import IRPetalParam
27
28
  from petal_qc.utils.readGraphana import ReadGraphana
28
29
  from petal_qc.utils.utils import output_folder
29
30
 
30
31
 
32
+
31
33
  def get_db_date(timestamp=None):
32
34
  """Convert a date string into the expected DB format.
33
35
 
@@ -82,11 +84,16 @@ def get_inlet_temp(irbf, param):
82
84
  getter = IRDataGetter.factory(param.institute, param)
83
85
 
84
86
  # TODO: get the server from thhe options
85
- server = os.getenv("GRAFANA_SERVER")
87
+ server = None
88
+ if param.graphana is not None:
89
+ server = param.graphana
90
+ else:
91
+ server = os.getenv("GRAFANA_SERVER")
92
+
86
93
  if server is None:
87
94
  DB = ReadGraphana()
88
95
  else:
89
- print("Connecting to Graphana serfer {}".format(server))
96
+ print("Connecting to Graphana server {}".format(server))
90
97
  DB = ReadGraphana(server)
91
98
 
92
99
  frames = getter.get_analysis_frame(irbf)
@@ -166,30 +173,52 @@ def create_IR_core(options):
166
173
  ordered_pipes = [None, None]
167
174
  pipe_order = [0, 0]
168
175
  all_3d_points = IRPetal.get_all_3d_points()
176
+ core_images = IRPetal.get_last_images()
169
177
  for i in range(2):
170
178
  pipe_type = PipeFit.PipeFit.guess_pipe_type(pipes[i])
171
179
  pipe_order[i] = pipe_type
180
+ if options.save_pipes:
181
+ prfx = options.alias if len(options.alias)>0 else "pipe"
182
+ ofile = output_folder(options.folder, "{}_pipe_{}.txt".format(prfx, pipe_type))
183
+ np.savetxt(ofile, pipes[i])
184
+
172
185
  PF = PipeFit.PipeFit(pipe_type)
173
186
  R = PF.fit_ex(pipes[i], factor=getter.factor)
174
187
  if options.debug or options.report:
188
+ _X = all_3d_points[i][:, 0]
189
+ _Y = all_3d_points[i][:, 1]
190
+ _Z = all_3d_points[i][:, 2]
191
+
175
192
  fig, _ = PF.plot(show_fig=False)
176
193
  __figures__["fit_{}".format(i)] = fig
177
194
 
195
+
196
+ shape = core_images[i].shape
197
+ fig_size = [6.4, 0]
198
+ factor = fig_size[0]/shape[1]
199
+ fig_size[1] = shape[0] * factor
200
+ fig, ax = plt.subplots(1, 1, tight_layout=True, figsize=fig_size)
201
+ ax.imshow(core_images[i], origin='lower', cmap=HighContrast.reversed())
202
+ ax.plot(_X, _Y, 'o-', linewidth=1, markersize=10)
203
+ for s in PF.sensors:
204
+ o = PF.transform_inv(s, R)
205
+ ax.plot(o[:,0], o[:, 1], linewidth=2, color="black")
206
+
207
+ __figures__["sensors_{}".format(pipe_type)] = fig
208
+
178
209
  fig = plt.figure(tight_layout=True, figsize=(7, 6))
179
210
  fig.subplots_adjust(left=0.0, right=1.)
180
211
 
181
- ax = fig.add_subplot(1, 1, 1, projection='3d')
182
- ax.view_init(elev=90, azim=-90)
183
- _X = all_3d_points[i][:, 0]
184
- _Y = all_3d_points[i][:, 1]
185
- _Z = all_3d_points[i][:, 2]
186
- sct = ax.scatter(_X, _Y, _Z, c=_Z, marker='o', cmap=plt.cm.jet)
187
- fig.colorbar(sct, shrink=0.75, aspect=5)
212
+ ax = fig.add_subplot(1, 1, 1)
213
+ sct = ax.scatter(_X, _Y, c=_Z, marker='o', cmap=plt.cm.jet)
214
+ fig.colorbar(sct, pad=0.01, aspect=10)
188
215
  __figures__["pipe_path_{}".format(i)] = fig
189
216
 
190
217
  transforms[pipe_type] = R
191
218
  fitter[pipe_type] = PF
192
219
 
220
+
221
+
193
222
  # Reorder points in pipe contour so that first point corresponds to
194
223
  # the U-shape pipe minimum.
195
224
  pipes[i] = IRPetal.reorder_pipe_points(pipes[i], pipe_type, R)
@@ -261,6 +290,8 @@ def main():
261
290
  parser.add_argument("--alias", default="", help="Alias")
262
291
  parser.add_argument("--SN", default="", help="serial number")
263
292
  parser.add_argument("--folder", default=None, help="Folder to store output files. Superseeds folder in --out")
293
+ parser.add_argument("--no-legend", dest="legend", action="store_false", default=True, help="Do not show the legend in plots.")
294
+ parser.add_argument("--save_pipes", default=False, action="store_true", help="SAve pipe path. Output is alias_pipe-i.txt")
264
295
 
265
296
  IRPetalParam.add_parameters(parser)
266
297
 
@@ -44,7 +44,7 @@ def create_report(options):
44
44
 
45
45
  if options.golden is None:
46
46
  return core
47
-
47
+
48
48
  goldenFile = Path(options.golden).expanduser().resolve()
49
49
  if not goldenFile.exists():
50
50
  goldenFile = utils.output_folder(options.folder, options.golden)
@@ -76,13 +76,14 @@ def create_report(options):
76
76
  document.add_heading('Original image', level=1)
77
77
  document.add_picture(figures["original"], True, 14, caption="Original Thermal image.")
78
78
 
79
+ document.add_heading('Sensor Position', level=1)
80
+ document.add_picture([figures["sensors_0"], figures["sensors_1"]], True, 7.5, caption="Side 0 (left) and Side 1 (right) sensors.")
81
+
79
82
  document.add_heading('Result of Pipe Fit', level=1)
80
- document.add_picture(figures["fit_0"], True, 10, caption="Side 0 fit.")
81
- document.add_picture(figures["fit_1"], True, 10, caption="Side 1 fit.")
83
+ document.add_picture([figures["fit_0"],figures["fit_1"]], True, 7.5, caption="Side 0 fit (left) and Side 1 fit (right)")
82
84
 
83
85
  document.add_heading('Pipe Path', level=1)
84
- document.add_picture(figures["pipe_path_0"], True, 10, caption="Side 0 pipe temp.")
85
- document.add_picture(figures["pipe_path_1"], True, 10, caption="Side 1 pipe temp.")
86
+ document.add_picture([figures["pipe_path_0"], figures["pipe_path_1"]], True, 7.5, caption="Side 0 and 1 pipe temp (left, right).")
86
87
 
87
88
  options.add_attachments = True
88
89
  options.create_golden = False
@@ -151,6 +152,8 @@ def main():
151
152
  parser.add_argument("--folder", default=None, help="Folder to store output files. Superseeds folder in --out")
152
153
  parser.add_argument("--add_attachments", action="store_true", default=False, help="If true add the attachments section os DB file.")
153
154
  parser.add_argument("--golden", default=None, help="The golden to compare width")
155
+ parser.add_argument("--no-legend", dest="legend", action="store_false", default=True, help="Do not show the legend in plots.")
156
+ parser.add_argument("--save_pipes", default=False, action="store_true", help="SAve pipe path. Output is alias_pipe-i.txt")
154
157
 
155
158
 
156
159
  IRPetalParam.add_parameters(parser)
@@ -24,21 +24,12 @@ from petal_qc.thermal import contours
24
24
  from petal_qc.thermal import IRBFile
25
25
  from petal_qc.thermal import IRPetal
26
26
  from petal_qc.thermal import PipeFit
27
- from petal_qc.thermal.Petal_IR_Analysis import AnalysisResult
28
27
  from petal_qc.thermal.Petal_IR_Analysis import show_2D_image
29
28
  from petal_qc.thermal.PetalColorMaps import HighContrast
30
29
 
31
30
  import petal_qc.utils.Progress as Progress
32
31
  import petal_qc.utils.utils as utils
33
-
34
-
35
- class CommaSeparatedListAction(Action):
36
- """Create a list from the comma sepparated numbers at imput."""
37
-
38
- def __call__(self, parser, namespace, values, option_string=None):
39
- """The actual action."""
40
- setattr(namespace, self.dest, list(map(int, values.split(','))))
41
-
32
+ from petal_qc.utils.ArgParserUtils import CommaSeparatedListAction
42
33
 
43
34
  def get_min_max(values, step=1.0):
44
35
  """Return min and max.
@@ -0,0 +1,41 @@
1
+ #!/usr/bin/env python3
2
+ """A number of utilities for argument parser."""
3
+
4
+ from argparse import Action
5
+
6
+ class CommaSeparatedListAction(Action):
7
+ """Create a list from the comma sepparated numbers at imput."""
8
+
9
+ def __call__(self, parser, namespace, values, option_string=None):
10
+ """The actual action."""
11
+ setattr(namespace, self.dest, list(map(int, values.split(','))))
12
+
13
+
14
+ class RangeListAction(Action):
15
+ """Create a list from a range expresion at input.
16
+
17
+ The list is made with numbers or ranges (ch1:ch2 or ch1:ch2:step)
18
+ """
19
+
20
+ def __call__(self, parser, namespace, values, option_string=None):
21
+ """The actual action."""
22
+ value = []
23
+ for V in values.split(','):
24
+ try:
25
+ value.append(int(V))
26
+ except ValueError:
27
+ if ':' not in V:
28
+ continue
29
+
30
+ items = V.split(':')
31
+ if len(items)==1:
32
+ continue
33
+
34
+ ival = list(map(int, items))
35
+ ival[1] += 1
36
+ for x in range(*ival):
37
+ value.append(int(x))
38
+
39
+
40
+ setattr(namespace, self.dest, value)
41
+
@@ -96,13 +96,13 @@ class Document(object):
96
96
  """Add page numbers."""
97
97
  add_page_number(self.doc.sections[0].footer.paragraphs[0])
98
98
 
99
- def add_picture(self, fig, center=True, size=10, caption=None):
99
+ def add_picture(self, fig_list, center=True, size=10, caption=None):
100
100
  """Add a picture in the document.
101
101
 
102
102
  Args:
103
103
  ----
104
104
  doc: the document
105
- fig : The matplotlib figure
105
+ fig : The matplotlib figure or list of figures.
106
106
  center (bool, optional): If picture will be centerd. Defaults to True.
107
107
  size (int, optional): Size of picture in cm. Defaults to 10.
108
108
  caption (str, optional): The text of the caption. Defaults to None.
@@ -112,14 +112,26 @@ class Document(object):
112
112
  Index of Figure if caption is True, otherwise -1.
113
113
 
114
114
  """
115
- png_file = tempfile.NamedTemporaryFile(suffix=".png", delete=False)
116
- fig.savefig(png_file, dpi=300)
117
- png_file.close()
115
+
116
+ if not isinstance(fig_list, (list, tuple)):
117
+ fig_list = [fig_list]
118
+
118
119
  P = self.add_paragraph()
119
120
  if center:
120
121
  P.alignment = WD_ALIGN_PARAGRAPH.CENTER
121
122
 
122
- P.add_run().add_picture(png_file.name, width=Cm(size))
123
+ R = P.add_run()
124
+ for fig in fig_list:
125
+ png_file = tempfile.NamedTemporaryFile(suffix=".png", delete=False)
126
+ fig.savefig(png_file, dpi=300)
127
+ png_file.close()
128
+
129
+ R.add_text("")
130
+ R.add_picture(png_file.name, width=Cm(size))
131
+
132
+ if len(fig_list)>0:
133
+ R.add_text(" ")
134
+
123
135
  rc = -1
124
136
  if caption:
125
137
  P = self.add_paragraph()
@@ -1,6 +1,6 @@
1
- Metadata-Version: 2.1
1
+ Metadata-Version: 2.2
2
2
  Name: petal_qc
3
- Version: 0.0.15
3
+ Version: 0.0.17
4
4
  Summary: A collection of scripts for Petal CORE QC.
5
5
  Author-email: Carlos Lacasta <carlos.lacasta@cern.ch>
6
6
  Project-URL: Homepage, https://gitlab.cern.ch/atlas-itk/sw/db/itk-pdb-gtk-gui-utils
@@ -1,43 +1,46 @@
1
1
  petal_qc/PetalReceptionTests.py,sha256=cSrq4PUjdV7T16ARonhsnXWPBBRuvliTKlZwEPfgRVY,10832
2
- petal_qc/__init__.py,sha256=vWXzH1nq_4LPfkOPhVjMfsxaexYA1nBMrVTx8Y9FSyY,1491
2
+ petal_qc/__init__.py,sha256=kbjhVay5LvvbmD75vF-UppbK464u5DleMndzmQfOsfI,1595
3
3
  petal_qc/dashBoard.py,sha256=U_UHNMca3H2ogD4a0Vpe4ZVUKEv2-xmGZQEZ9_aH0E4,4034
4
- petal_qc/BTreport/CheckBTtests.py,sha256=CxR8lcawwhdzkBs8jZCXI6TSGPOsOEigpAND0D1O0cs,8178
4
+ petal_qc/getPetalCoreTestSummary.py,sha256=hTv4A8gcEkvCZLcy9ZkpwOevksz6LfK1Rb1-4ENlC7I,3706
5
+ petal_qc/BTreport/CheckBTtests.py,sha256=CoKTnW_7gbL42rVaBy9FnH1SEYifmgg1P5Iy253vDFk,9855
5
6
  petal_qc/BTreport/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
6
- petal_qc/BTreport/bustapeReport.py,sha256=c5VERxPm6BOgW_yN9O_bEPmCYpuwZ_Yt_I2sMVAp0-I,6895
7
+ petal_qc/BTreport/bustapeReport.py,sha256=M0EZQEh8G-65p6-gCOyZ0WlvnRbzQHXPwAWta9ZExnQ,6907
7
8
  petal_qc/metrology/Cluster.py,sha256=UtZ5q1EFb8f3qC0hEYBbhRg2pPbW_28aJX2EEMu00Ho,2105
8
9
  petal_qc/metrology/DataFile.py,sha256=PbFqy3-WSj69epV5EjhHc1GKhA8I74FmJYOXUjN0V20,1367
9
- petal_qc/metrology/PetalMetrology.py,sha256=YxzS-awU4PWdCYdJH754BrSOEilHf9gsyS7fcGzWV04,12781
10
+ petal_qc/metrology/PetalMetrology.py,sha256=ZEJnkR2vjNmbH7SChPtSsC1YNKgFwfa9YkHc1XNleK8,12333
10
11
  petal_qc/metrology/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
11
12
  petal_qc/metrology/all2csv.py,sha256=KTgEGaediylwkGN7gyWyQqUjU0f9FOa3xF4z1W38EcU,1569
12
13
  petal_qc/metrology/analyze_locking_points.py,sha256=83f8nNgmXWClQnIG1plu3YYuxNmeEeTu8VKJE9izw70,20531
13
14
  petal_qc/metrology/cold_noise.py,sha256=PuTaQ73WrQCJdE9ezS4UFmA3atwCuvM0ZsUOYu1ZIBw,3106
14
- petal_qc/metrology/compare_Cores.py,sha256=w4BZpXoDwX9N0FMQ2_1xcpnTELbdvQyRPvvdkJc1E0M,8207
15
+ petal_qc/metrology/compare_Cores.py,sha256=dP0i_C_VrM4s3i0RrI2g4ZcjRmgIHlAgodhGS87YYgw,9458
15
16
  petal_qc/metrology/comparisonTable.py,sha256=6Zmh-x0ahs28ZJQuHMrIiRcblUmTN1_-1otFSRNMPds,1743
16
17
  petal_qc/metrology/convert_mitutoyo.py,sha256=HdXQzFL5y7r8qXDzti91VItDQ-y6D9rEAYknn4yHwBs,5449
17
18
  petal_qc/metrology/convert_smartscope.py,sha256=0vAEYn7ec4qTnLfjphj1QA6tK3vZsXyF6nYYj3jE5Yc,6174
18
- petal_qc/metrology/coreMetrology.py,sha256=2BHc-h2xaFB3IK6VW_t96_swLiCf04EW7CeHq7hEKe4,13869
19
+ petal_qc/metrology/coreMetrology.py,sha256=rGzCyPqlfsnh2XUUDiykQFlRt3kkFkrQqVOhOJUNhyU,13427
19
20
  petal_qc/metrology/data2csv.py,sha256=2ttMSmfGLPIaOqZGima2dH6sdnSRAFTHlEbSOfW5ebA,1809
20
- petal_qc/metrology/do_Metrology.py,sha256=-2CicDzlMDo_7swiswF98RjcHjWtBhLbgnwXO_zTt9Q,4793
21
+ petal_qc/metrology/do_Metrology.py,sha256=czsEqw7FaCtE_1FezKYy4uaChezJ89urlO4rT4BUzkQ,4351
21
22
  petal_qc/metrology/flatness4nigel.py,sha256=SUHwn6pCEUWQV_62-_9-VKrmUdL4gVQcSA3aTtYq958,4071
22
23
  petal_qc/metrology/gtkutils.py,sha256=1pOTxiE2EZR9zNNNT5cOetga_4NG9DzLaqQPI4c1EzE,3372
23
- petal_qc/metrology/petal_flatness.py,sha256=JpgWlaxeLFsCZHquSUD3axCNvwtB5LOZ1wQHPUVUwc0,11052
24
- petal_qc/metrology/readAVSdata.py,sha256=m5RAY3g3l6bKpaSD_HtpPEipbiHqjGQD-dDOmC9wlE8,25503
24
+ petal_qc/metrology/petal_flatness.py,sha256=KksOFO_ZrKM4nUDHRC-3mSm1tp5C7wkE_6f9ZiH9B70,10610
25
+ petal_qc/metrology/readAVSdata.py,sha256=6GRUac9b3iOoVoGfWr6rsNj1smsw9aT0tu5wuNuumAE,25615
25
26
  petal_qc/metrology/show_data_file.py,sha256=yZPcmMy-1EWWySiBBx0hNB3tPVh19bTr0PDaXSyIF4c,4057
26
27
  petal_qc/metrology/testSummary.py,sha256=0BhcEd1BPz2Mbonzi8nyZOzNSzpUqowBFNl5cVutqsk,994
27
28
  petal_qc/metrology/test_paralelism.py,sha256=_j__OdUwdXWM494_9HpGPuPHixMwwVphCcvHEfzWi_k,1981
28
- petal_qc/metrology/uploadPetalInformation.py,sha256=7JXTNRaThXlWLKwPAC6v9N2jFK1nmG5AkGJqEryMyRE,26769
29
- petal_qc/test/checkAVStests.py,sha256=TQ6EscfqL65sNC6QX5FElakYShnuMvqvKYhroXjZD0Q,4815
29
+ petal_qc/metrology/uploadPetalInformation.py,sha256=K2hHXmoQ-qi5HLTmFNn5jVsZDDXX88psGV-XIRgx1kA,26728
30
+ petal_qc/test/analyzeMetrologyTable.py,sha256=_ipKV8-rXgLca5Bu3ATLZjGR5koFN4-qwpj88rgf-x0,3098
31
+ petal_qc/test/checkAVStests.py,sha256=0xAJLazfkgfQ0ouc17fivaj69OXTiS9sali0DhH-jTs,4814
32
+ petal_qc/test/checkCoreShipments.py,sha256=d9W_uE0tMdfJGRuiiTOGyIW60SIj08QKWjd3Y8aVBi8,1554
30
33
  petal_qc/test/compare_golden.py,sha256=lG1rtYLw_PwKWrLk0VVdbnRhi7Ytu78q7PGWcYptM_8,1171
31
34
  petal_qc/test/createMetrologyFile.py,sha256=3fmHj8AlT_739sGRrKgpe_ZbGW2NUDAc6w0t7dEXWMo,2387
35
+ petal_qc/test/createMetrologyTable.py,sha256=Dh9Mwab5geyojigVCS5mKba1EJU-4K1-ELDMZTDw4Dg,2687
32
36
  petal_qc/test/desyModuleBow.py,sha256=4RgDIVEMqzlGUVqKCjji95_JzfXtcgjK4kefKrVH9eY,3602
33
37
  petal_qc/test/findRawData.py,sha256=8wqvPILjfZZ0CKkDhOa_tcsYMwNwcKOLyaEoWfISBQY,2872
34
38
  petal_qc/test/getAVSjson.py,sha256=o8AYtyr7Vnp-enznmQ-NNiivZipmxtoVrmsfnRCl0X4,977
35
- petal_qc/test/getAVStests.py,sha256=BMP_u7wbgSSu1bYtjDiSBWVGNOmKPJtMhG_9t9GQxB4,9516
36
- petal_qc/test/getPetalCoreTestSummary.py,sha256=8eX-UPuNjARAZSaEZpNveqHP1WBFmcJnno3B36v6wpU,3159
39
+ petal_qc/test/getAVStests.py,sha256=GNqEpncUQdvo-qSf46ltGVeezSnHB2BQsKjApS6xomY,10285
37
40
  petal_qc/test/listPetalCoreComponents.py,sha256=7U9wokRkgeZdYZKeZdAadA32BlhVK6okInuh94hmj24,2502
38
- petal_qc/test/prepareDESYfiles.py,sha256=g1qSdmddk7Ope71-TvY5oztcZJ1vRqiX5UvNtZAW5TE,4034
41
+ petal_qc/test/prepareDESYfiles.py,sha256=uRir2fv0oGqB6hKnIqRltDW-oLz1tR2SDvVkMVxCfKI,4106
39
42
  petal_qc/test/reportFromJSon.py,sha256=3YTuWeeVtw5pITloLlwEYbx84f6k9XC_jTBK53I4mLM,1456
40
- petal_qc/test/test_Graphana.py,sha256=fXcqHzgrfZGjSF-WoMLl96G97XjXVnynHYC-5rKw_-c,1032
43
+ petal_qc/test/test_Graphana.py,sha256=4wADxS_ObG9n4vsCvD1GwPQnx8bFUiUOS6ZwK83wTl8,1082
41
44
  petal_qc/test/test_coreThermal.py,sha256=YRPK3DGG7Tz66K4Kka3euXgUDzW_JlIqSYicMBhb96E,1516
42
45
  petal_qc/thermal/CSVImage.py,sha256=Vt2kYmUsZWkQvxcF8fDda3HO1Rb29kPQHnEoHFCqWYo,2038
43
46
  petal_qc/thermal/DESYdata.py,sha256=YAwxhnmA89uH1vZ_BjDo0VLATTGRngoBSFzYfLSJbZU,1904
@@ -46,30 +49,31 @@ petal_qc/thermal/IRBFile.py,sha256=_no8iUyuSQ41j34o3LVzUCjMYoviwjz02tsWvFsTUzA,2
46
49
  petal_qc/thermal/IRCore.py,sha256=sidf7HtrzEUcllv0E_o1Hks-2_2dl4Og_LWcwgPNRcE,3062
47
50
  petal_qc/thermal/IRDataGetter.py,sha256=S-Xaizrop_xQ2pgkvuw_HdKbrsDD84KThwgTfjRg0bQ,11579
48
51
  petal_qc/thermal/IRPetal.py,sha256=hVOD0VAKTA2xvNXbZ-TXAYHNlihNWsUkI2i9IEwQhZk,40887
49
- petal_qc/thermal/IRPetalParam.py,sha256=E4uZvk7Ne5TqoY8UHIbMmgB87vIxmYhTgISvs9ZgCt8,3674
52
+ petal_qc/thermal/IRPetalParam.py,sha256=_d0mIxM1laVK5cnM5v7X1L0SQ5dUeXB8kpBySHjfiLI,3817
50
53
  petal_qc/thermal/PetalColorMaps.py,sha256=6CvJHzRdojLHu3BROYSekHw8g_BJ1lJ_edyhovTIydU,3831
51
54
  petal_qc/thermal/Petal_IR_Analysis.py,sha256=ALIER9fLn2R26IMhPVzEDL6tlK7XNbCtRtH0y6kTaEU,3950
52
- petal_qc/thermal/PipeFit.py,sha256=MNQYk9NivBsDze6CVwE1cFdJjrqqbn8FK19436nFMVY,17575
55
+ petal_qc/thermal/PipeFit.py,sha256=8nEjpZC1mWh4-bhXzwXfjO8WkC_6hFYX0XXPjTHwNUw,18345
53
56
  petal_qc/thermal/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
54
- petal_qc/thermal/analyze_IRCore.py,sha256=HahnXkBRdeLlPt1BKSrj3UP6aDSHqDNbao_wxU-DlTg,20485
55
- petal_qc/thermal/contours.py,sha256=ampCKm4byZYKb_4eJFjIkdFIl2bqVXD2mV13d2XUWlw,8244
57
+ petal_qc/thermal/analyze_IRCore.py,sha256=-MsKGJR-5pJV93ipLau0FHQeconLhMPDuLQIT9LMWsU,21115
58
+ petal_qc/thermal/contours.py,sha256=Bx4ghZhgZ4ya1rr4CZvjpqZd9M924Vms1oEGrgllWG4,8591
56
59
  petal_qc/thermal/coreThermal.py,sha256=cLH7lOd6EF6y03LVaQUovlNs_Dcx9DCD1Erdw8aNrA0,16227
57
- petal_qc/thermal/create_IRCore.py,sha256=b1ja1VBELqadyWnugYlMp7eNfaLC_zhL8Q6slwOK0Y8,8219
58
- petal_qc/thermal/create_core_report.py,sha256=MsB-Knr2iiHReyInLEd825KSzwG7VuAHSM_2MmPlW3g,6019
60
+ petal_qc/thermal/create_IRCore.py,sha256=KUiRu8CUFUP0cUgtUCFkGPDePoylFqkV_GxzIVRJjZs,9441
61
+ petal_qc/thermal/create_core_report.py,sha256=v1GMt9U57pAYm3m91T3a7cFfN5xvpFY4vsfuBrtOYuU,6394
59
62
  petal_qc/thermal/pipe_back.npz,sha256=yooZuVYtHU541HcV6Gh_5B0BqdYAVEvYAuVvMMSY7Jc,3632
60
63
  petal_qc/thermal/pipe_front.npz,sha256=DuwruG9C2Z1rLigqWMApY4Orsf1SGUQGKy0Yan8Bk8A,3697
61
64
  petal_qc/thermal/pipe_read.py,sha256=HrAtEbf8pMhJDETzkevodiTbuprIOh4yHv6PzpRoz7Q,5040
62
- petal_qc/thermal/show_IR_petal.py,sha256=vKb8wm9Y7erAdCb93ODREv2qfSexNMfJpV-67wfOhBw,13159
65
+ petal_qc/thermal/show_IR_petal.py,sha256=f4QZ68K0y7QpTpjou09XCqasoF93VxZLZ6vCQoOYiSM,12875
66
+ petal_qc/utils/ArgParserUtils.py,sha256=AuWA8SrJNnL_rWo_38N1hSrmjSpuBn7muOv9Xkw1jl4,1166
63
67
  petal_qc/utils/Geometry.py,sha256=NSz64lKNEh9ny5ZGRQ4abA1zPiJNJcGnTenTGZNNB8o,19865
64
68
  petal_qc/utils/Progress.py,sha256=gCti4n2xfCcOTlAff5GchabGE5BCwavvDZYYKdbEsXU,4064
65
69
  petal_qc/utils/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
66
70
  petal_qc/utils/all_files.py,sha256=4ja_DkbTYPY3gUPBAZq0p7KB9lnXZx-OCnpTHg9tm4I,1044
67
- petal_qc/utils/docx_utils.py,sha256=Eye16PF8W0mPBVdQvgFKWxPYV7-hzBgANPDZtUEjzf8,5805
71
+ petal_qc/utils/docx_utils.py,sha256=zVmSKHDVE8cUwbXxqyPtgS0z62VCFya1DWklOpO1rCQ,6067
68
72
  petal_qc/utils/fit_utils.py,sha256=3KUGWpBMV-bVDkQHWBigXot8chOpjAVBJ5H5b5dbdjk,5349
69
73
  petal_qc/utils/readGraphana.py,sha256=YVOztJC3q3P7F0I9Ggeiu6Mv9rZLKgj3clkLCU7k4i4,1918
70
74
  petal_qc/utils/utils.py,sha256=CqCsNIcEg6FQb3DN70tmqeLVLlQqsRfDzhfGevlnfBc,4035
71
- petal_qc-0.0.15.dist-info/METADATA,sha256=ghjcP3iMvHzI7sozmhikxxlR1zLXrvk5iACOWcrEEUc,953
72
- petal_qc-0.0.15.dist-info/WHEEL,sha256=PZUExdf71Ui_so67QXpySuHtCi3-J3wvF4ORK6k_S8U,91
73
- petal_qc-0.0.15.dist-info/entry_points.txt,sha256=1DtsI43PHWiGxvmhRhUhL4G1-XYBRyfqKgNMMTiqeJA,452
74
- petal_qc-0.0.15.dist-info/top_level.txt,sha256=CCo1Xe6kLS79PruhsB6bk2CuL9VFtNdNpgJjYUs4jk4,9
75
- petal_qc-0.0.15.dist-info/RECORD,,
75
+ petal_qc-0.0.17.dist-info/METADATA,sha256=VS3V_j4SivhcaUTZuVMJ0Cy222gFzVxtnMSo6uYczmg,953
76
+ petal_qc-0.0.17.dist-info/WHEEL,sha256=jB7zZ3N9hIM9adW7qlTAyycLYW9npaWKLRzaoVcLKcM,91
77
+ petal_qc-0.0.17.dist-info/entry_points.txt,sha256=YPrZOsRBRsiKNDvsnbug0-Khj7DcN_Sdpq-tB_XjykI,505
78
+ petal_qc-0.0.17.dist-info/top_level.txt,sha256=CCo1Xe6kLS79PruhsB6bk2CuL9VFtNdNpgJjYUs4jk4,9
79
+ petal_qc-0.0.17.dist-info/RECORD,,
@@ -1,5 +1,5 @@
1
1
  Wheel-Version: 1.0
2
- Generator: setuptools (75.6.0)
2
+ Generator: setuptools (75.8.2)
3
3
  Root-Is-Purelib: true
4
4
  Tag: py3-none-any
5
5
 
@@ -6,6 +6,7 @@ coreMetrologyTTY = petal_qc:coreMetrologyTTY
6
6
  coreThermal = petal_qc:coreThermal
7
7
  createCoreThermalReport = petal_qc:createCoreThermalReport
8
8
  doMetrology = petal_qc:doMetrology
9
+ petalCoreTestSummary = petal_qc:petalCoreTestSummary
9
10
  petalReceptionTests = petal_qc:petalReceptionTests
10
11
  petalqc_dashBoard = petal_qc:dashBoard
11
12
  uploadPetalInformation = petal_qc:uploadPetalInformation