source: trunk/MagicSoft/Mars/mjobs/MJCalibration.cc@ 4638

Last change on this file since 4638 was 4638, checked in by gaug, 20 years ago
*** empty log message ***
File size: 57.8 KB
Line 
1/* ======================================================================== *\
2!
3! *
4! * This file is part of MARS, the MAGIC Analysis and Reconstruction
5! * Software. It is distributed to you in the hope that it can be a useful
6! * and timesaving tool in analysing Data of imaging Cerenkov telescopes.
7! * It is distributed WITHOUT ANY WARRANTY.
8! *
9! * Permission to use, copy, modify and distribute this software and its
10! * documentation for any purpose is hereby granted without fee,
11! * provided that the above copyright notice appear in all copies and
12! * that both that copyright notice and this permission notice appear
13! * in supporting documentation. It is provided "as is" without express
14! * or implied warranty.
15! *
16!
17!
18! Author(s): Thomas Bretz, 1/2004 <mailto:tbretz@astro.uni-wuerzburg.de>
19! Markus Gaug, 02/2004 <mailto:markus@ifae.es>
20!
21! Copyright: MAGIC Software Development, 2000-2004
22!
23!
24\* ======================================================================== */
25/////////////////////////////////////////////////////////////////////////////
26//
27// MJCalibration
28//
29// Do one calibration loop over serious of runs with the same pulser
30// colour and the same intensity. The following containers (rectangular) and
31// tasks (ellipses) are called to produce an MCalibrationChargeCam and to
32// update the MCalibrationQECam: (MCalibrate is not called from this class)
33//
34//Begin_Html
35/*
36<img src="images/CalibClasses.gif">
37*/
38//End_Html
39//
40// Different signal extractors can be set with the command SetExtractor()
41// Only extractors deriving from MExtractor can be set, default is MExtractSlidingWindow
42//
43// Different arrival time extractors can be set with the command SetTimeExtractor()
44// Only extractors deriving from MExtractTime can be set, default is MExtractTimeSpline
45//
46// At the end of the eventloop, plots and results are displayed, depending on
47// the flags set (see DisplayResult())
48//
49// If the flag SetFullDisplay() is set, all MHCameras will be displayed.
50// if the flag SetDataCheckDisplay() is set, only the most important ones are displayed
51// Otherwise, (default: SetNormalDisplay()), a good selection of plots is given
52//
53// If the flag SetDataCheck() is set, the calibration is used as in the data check at
54// La Palma, which mean especially running on raw data files.
55//
56// The absolute light calibration devices Blind Pixel and PIN Diode can be switched on
57// and off with the commands:
58//
59// - SetUseBlindPixel(Bool_t )
60// - SetUsePINDiode(Bool_t )
61//
62// See also: MHCalibrationChargePix, MHCalibrationChargeCam, MHGausEvents
63// MHCalibrationChargeBlindPix, MHCalibrationChargePINDiode
64// MCalibrationChargePix, MCalibrationChargeCam, MCalibrationChargeCalc
65// MCalibrationChargeBlindPix, MCalibrationChargePINDiode,
66// MCalibrationQECam, MBadPixelsPix, MBadPixelsCam
67//
68// If the flag RelTimeCalibration() is set, a calibration of the relative arrival
69// times is also performed. The following containers (rectangular) and
70// tasks (ellipses) are called to produce an MCalibrationRelTimeCam used by
71// MCalibrateTime to correct timing offset between pixels: (MCalibrateTime is not
72// called from this class)
73//
74//Begin_Html
75/*
76<img src="images/RelTimeClasses.gif">
77*/
78//End_Html
79//
80// Different arrival time extractors can be set directly with the command SetTimeExtractor(MExtractor *)
81//
82// See also: MHCalibrationRelTimePix, MHCalibrationRelTimeCam, MHGausEvents
83// MCalibrationRelTimePix, MCalibrationRelTimeCam
84// MBadPixelsPix, MBadPixelsCam
85//
86/////////////////////////////////////////////////////////////////////////////
87#include "MJCalibration.h"
88
89#include <TEnv.h>
90#include <TFile.h>
91#include <TStyle.h>
92#include <TCanvas.h>
93#include <TSystem.h>
94#include <TLine.h>
95#include <TLatex.h>
96#include <TLegend.h>
97#include <TPaveText.h>
98
99#include "MLog.h"
100#include "MLogManip.h"
101
102#include "MRunIter.h"
103#include "MSequence.h"
104#include "MParList.h"
105#include "MTaskList.h"
106#include "MEvtLoop.h"
107
108#include "MHCamera.h"
109#include "MGeomCam.h"
110
111#include "MPedestalCam.h"
112#include "MCalibrationCam.h"
113#include "MCalibrationQECam.h"
114#include "MCalibrationQEPix.h"
115#include "MCalibrationChargeCam.h"
116#include "MCalibrationChargePix.h"
117#include "MCalibrationChargePINDiode.h"
118#include "MCalibrationChargeBlindPix.h"
119#include "MCalibrationChargeBlindCam.h"
120#include "MCalibrationChargeBlindPix.h"
121#include "MCalibrationChargeCalc.h"
122
123#include "MHGausEvents.h"
124#include "MHCalibrationCam.h"
125#include "MHCalibrationChargeCam.h"
126#include "MHCalibrationChargeBlindCam.h"
127#include "MHCalibrationChargePINDiode.h"
128#include "MHCalibrationRelTimeCam.h"
129#include "MCalibrationRelTimeCam.h"
130#include "MCalibrationRelTimeCalc.h"
131
132#include "MReadMarsFile.h"
133#include "MRawFileRead.h"
134#include "MGeomApply.h"
135#include "MTaskEnv.h"
136#include "MBadPixelsMerge.h"
137#include "MBadPixelsCam.h"
138#include "MExtractTime.h"
139#include "MExtractor.h"
140#include "MExtractPINDiode.h"
141#include "MExtractBlindPixel.h"
142#include "MExtractSlidingWindow.h"
143#include "MExtractTimeFastSpline.h"
144#include "MFCosmics.h"
145#include "MContinue.h"
146#include "MFillH.h"
147
148#include "MArrivalTimeCam.h"
149
150#include "MStatusDisplay.h"
151
152ClassImp(MJCalibration);
153
154using namespace std;
155
156const Int_t MJCalibration::gkIFAEBoxInaugurationRun = 20113;
157const Int_t MJCalibration::gkSecondBlindPixelInstallation = 31693;
158const Int_t MJCalibration::gkThirdBlindPixelInstallation = 99999;
159
160const Double_t MJCalibration::fgConvFADC2PheMin = 0.;
161const Double_t MJCalibration::fgConvFADC2PheMax = 1.5;
162const Double_t MJCalibration::fgConvFADC2PhotMin = 0.;
163const Double_t MJCalibration::fgConvFADC2PhotMax = 10.;
164const Double_t MJCalibration::fgQEMin = 0.;
165const Double_t MJCalibration::fgQEMax = 0.3;
166
167const Float_t MJCalibration::fgRefConvFADC2PheInner = 0.14;
168const Float_t MJCalibration::fgRefConvFADC2PheOuter = 0.45;
169const Float_t MJCalibration::fgRefConvFADC2PhotInner = 0.8;
170const Float_t MJCalibration::fgRefConvFADC2PhotOuter = 3.8;
171const Float_t MJCalibration::fgRefQEInner = 0.18;
172const Float_t MJCalibration::fgRefQEOuter = 0.12;
173// --------------------------------------------------------------------------
174//
175// Default constructor.
176//
177// - Sets fRuns to 0, fExtractor to NULL, fTimeExtractor to NULL, fColor to kNONE,
178// fDisplay to kNormalDisplay, fRelTime to kFALSE, fDataCheck to kFALSE,
179// - SetUseBlindPixel()
180// - SetUsePINDiode()
181//
182MJCalibration::MJCalibration(const char *name, const char *title)
183 : fEnv(0), fRuns(0), fSequence(0), fExtractor(NULL), fTimeExtractor(NULL),
184 fColor(MCalibrationCam::kNONE), fDisplayType(kNormalDisplay),
185 fRelTimes(kFALSE), fDataCheck(kFALSE), fDebug(kFALSE)
186{
187
188 fName = name ? name : "MJCalibration";
189 fTitle = title ? title : "Tool to create the calibration constants for one calibration run";
190
191 SetUseBlindPixel();
192 SetUsePINDiode();
193
194}
195
196MJCalibration::~MJCalibration()
197{
198 if (fEnv)
199 delete fEnv;
200}
201
202// --------------------------------------------------------------------------
203//
204// Display the results in MStatusDisplay:
205//
206// - Add "Calibration" to the MStatusDisplay title
207// - Retrieve the MGeomCam from MParList
208// - Initialize the following MHCamera's:
209// 1) MCalibrationPix::GetMean()
210// 2) MCalibrationPix::Sigma()
211// 3) MCalibrationChargePix::GetRSigma()
212// 4) MCalibrationChargePix::GetRSigmaPerCharge()
213// 5) MCalibrationChargePix::GetPheFFactorMethod()
214// 6) MCalibrationChargePix::GetMeanConvFADC2Phe()
215// 7) MCalibrationChargePix::GetMeanFFactorFADC2Phot()
216// 8) MCalibrationQEPix::GetQECascadesFFactor()
217// 9) MCalibrationQEPix::GetQECascadesBlindPixel()
218// 10) MCalibrationQEPix::GetQECascadesPINDiode()
219// 11) MCalibrationQEPix::GetQECascadesCombined()
220// 12) MCalibrationQEPix::IsAverageQEFFactorAvailable()
221// 13) MCalibrationQEPix::IsAverageQEBlindPixelAvailable()
222// 14) MCalibrationQEPix::IsAverageQEPINDiodeAvailable()
223// 15) MCalibrationQEPix::IsAverageQECombinedAvailable()
224// 16) MCalibrationChargePix::IsHiGainSaturation()
225// 17) MCalibrationPix::GetHiLoMeansDivided()
226// 18) MCalibrationPix::GetHiLoSigmasDivided()
227// 19) MCalibrationChargePix::GetHiGainPickup()
228// 20) MCalibrationChargePix::GetLoGainPickup()
229// 21) MCalibrationChargePix::GetHiGainBlackout()
230// 22) MCalibrationChargePix::GetLoGainBlackout()
231// 23) MCalibrationPix::IsExcluded()
232// 24) MBadPixelsPix::IsUnsuitable(MBadPixelsPix::kUnsuitableRun)
233// 25) MBadPixelsPix::IsUnsuitable(MBadPixelsPix::kUnreliableRun)
234// 26) MBadPixelsPix::IsUncalibrated(MBadPixelsPix::kHiGainOscillating)
235// 27) MBadPixelsPix::IsUncalibrated(MBadPixelsPix::kLoGainOscillating)
236// 28) MCalibrationChargePix::GetAbsTimeMean()
237// 29) MCalibrationChargePix::GetAbsTimeRms()
238//
239// If the flag SetFullDisplay() is set, all MHCameras will be displayed.
240// if the flag SetDataCheckDisplay() is set, only the most important ones are displayed
241// and otherwise, (default: SetNormalDisplay()), a good selection of plots is given
242//
243void MJCalibration::DisplayResult(MParList &plist)
244{
245
246 if (!fDisplay)
247 return;
248
249 //
250 // Update display
251 //
252 TString title = fDisplay->GetTitle();
253 title += "-- Calibration ";
254 title += fSequence ? Form("calib%06d", fSequence->GetSequence()) : fRuns->GetRunsAsString();
255 title += " --";
256 fDisplay->SetTitle(title);
257
258 //
259 // Get container from list
260 //
261 MGeomCam &geomcam = *(MGeomCam*)plist.FindObject("MGeomCam");
262
263 // Create histograms to display
264 MHCamera disp1 (geomcam, "Charge", "Fitted Mean Charges");
265 MHCamera disp2 (geomcam, "SigmaCharge", "Sigma of Fitted Charges");
266 MHCamera disp3 (geomcam, "RSigma", "Reduced Sigmas");
267 MHCamera disp4 (geomcam, "RSigmaPerCharge", "Reduced Sigma per Charge");
268 MHCamera disp5 (geomcam, "NumPhes", "Number of Phes");
269 MHCamera disp6 (geomcam, "ConvFADC2Phes", "Conversion Factor to Phes");
270 MHCamera disp7 (geomcam, "TotalFFactor", "Total F-Factor (F-Factor Method)");
271 MHCamera disp8 (geomcam, "CascadesQEFFactor", "Cascades QE (F-Factor Method)");
272 MHCamera disp9 (geomcam, "CascadesQEBlindPix","Cascades QE (Blind Pixel Method)");
273 MHCamera disp10(geomcam, "CascadesQEPINDiode","Cascades QE (PIN Diode Method)");
274 MHCamera disp11(geomcam, "CascadesQECombined","Cascades QE (Combined Method)");
275 MHCamera disp12(geomcam, "FFactorValid", "Pixels with valid F-Factor calibration");
276 MHCamera disp13(geomcam, "BlindPixelValid", "Pixels with valid BlindPixel calibration");
277 MHCamera disp14(geomcam, "PINdiodeValid", "Pixels with valid PINDiode calibration");
278 MHCamera disp15(geomcam, "CombinedValid", "Pixels with valid Combined calibration");
279 MHCamera disp16(geomcam, "Saturation", "Pixels with saturated Hi Gain");
280 MHCamera disp17(geomcam, "ConversionMeans", "Conversion HiGain.vs.LoGain Means");
281 MHCamera disp18(geomcam, "ConversionSigmas", "Conversion HiGain.vs.LoGain Sigmas");
282 MHCamera disp19(geomcam, "HiGainPickup", "Number Pickup events Hi Gain");
283 MHCamera disp20(geomcam, "LoGainPickup", "Number Pickup events Lo Gain");
284 MHCamera disp21(geomcam, "HiGainBlackout", "Number Blackout events Hi Gain");
285 MHCamera disp22(geomcam, "LoGainBlackout", "Number Blackout events Lo Gain");
286 MHCamera disp23(geomcam, "Excluded", "Pixels previously excluded");
287 MHCamera disp24(geomcam, "UnSuitable", "Pixels not suited for further analysis");
288 MHCamera disp25(geomcam, "UnReliable", "Pixels not reliable for further analysis");
289 MHCamera disp26(geomcam, "HiGainOscillating", "Oscillating Pixels High Gain");
290 MHCamera disp27(geomcam, "LoGainOscillating", "Oscillating Pixels Low Gain");
291 MHCamera disp28(geomcam, "AbsTimeMean", "Abs. Arrival Times");
292 MHCamera disp29(geomcam, "AbsTimeRms", "RMS of Arrival Times");
293 MHCamera disp30(geomcam, "MeanTime", "Mean Rel. Arrival Times");
294 MHCamera disp31(geomcam, "SigmaTime", "Sigma Rel. Arrival Times");
295 MHCamera disp32(geomcam, "TimeProb", "Probability of Time Fit");
296 MHCamera disp33(geomcam, "TimeNotFitValid", "Pixels with not valid fit results");
297 MHCamera disp34(geomcam, "TimeOscillating", "Oscillating Pixels");
298 MHCamera disp35(geomcam, "TotalConv", "Conversion Factor to photons");
299
300 // Fitted charge means and sigmas
301 disp1.SetCamContent(fCalibrationCam, 0);
302 disp1.SetCamError( fCalibrationCam, 1);
303 disp2.SetCamContent(fCalibrationCam, 2);
304 disp2.SetCamError( fCalibrationCam, 3);
305
306 // Reduced Sigmas and reduced sigmas per charge
307 disp3.SetCamContent(fCalibrationCam, 5);
308 disp3.SetCamError( fCalibrationCam, 6);
309 disp4.SetCamContent(fCalibrationCam, 7);
310 disp4.SetCamError( fCalibrationCam, 8);
311
312 // F-Factor Method
313 disp5.SetCamContent(fCalibrationCam, 9);
314 disp5.SetCamError( fCalibrationCam, 10);
315 disp6.SetCamContent(fCalibrationCam, 11);
316 disp6.SetCamError( fCalibrationCam, 12);
317 disp7.SetCamContent(fCalibrationCam, 13);
318 disp7.SetCamError( fCalibrationCam, 14);
319
320 // Quantum Efficiencies
321 disp8.SetCamContent (fQECam, 0 );
322 disp8.SetCamError (fQECam, 1 );
323 disp9.SetCamContent (fQECam, 2 );
324 disp9.SetCamError (fQECam, 3 );
325 disp10.SetCamContent(fQECam, 4 );
326 disp10.SetCamError (fQECam, 5 );
327 disp11.SetCamContent(fQECam, 6 );
328 disp11.SetCamError (fQECam, 7 );
329
330 // Valid flags
331 disp12.SetCamContent(fQECam, 8 );
332 disp13.SetCamContent(fQECam, 9 );
333 disp14.SetCamContent(fQECam, 10);
334 disp15.SetCamContent(fQECam, 11);
335
336 // Conversion Hi-Lo
337 disp16.SetCamContent(fCalibrationCam, 25);
338 disp17.SetCamContent(fCalibrationCam, 16);
339 disp17.SetCamError (fCalibrationCam, 17);
340 disp18.SetCamContent(fCalibrationCam, 18);
341 disp18.SetCamError (fCalibrationCam, 19);
342
343 // Pickup and Blackout
344 disp19.SetCamContent(fCalibrationCam, 21);
345 disp20.SetCamContent(fCalibrationCam, 22);
346 disp21.SetCamContent(fCalibrationCam, 23);
347 disp22.SetCamContent(fCalibrationCam, 24);
348
349 // Pixels with defects
350 disp23.SetCamContent(fCalibrationCam, 20);
351 disp24.SetCamContent(fBadPixels, 6);
352 disp25.SetCamContent(fBadPixels, 7);
353
354 // Oscillations
355 disp26.SetCamContent(fBadPixels, 10);
356 disp27.SetCamContent(fBadPixels, 11);
357
358 // Arrival Times
359 disp28.SetCamContent(fCalibrationCam, 26);
360 disp28.SetCamError( fCalibrationCam, 27);
361 disp29.SetCamContent(fCalibrationCam, 27);
362
363 disp1.SetYTitle("Q [FADC counts]");
364 disp2.SetYTitle("\\sigma_{Q} [FADC counts]");
365
366 disp3.SetYTitle("\\sqrt{\\sigma^{2}_{Q} - RMS^{2}_{Ped}} [FADC Counts]");
367 disp4.SetYTitle("Red.Sigma/<Q> [1]");
368
369 disp5.SetYTitle("Phes [1]");
370 disp6.SetYTitle("Conv.Factor [PhE/FADC counts]");
371 disp7.SetYTitle("Total F-Factor [1]");
372
373 disp8.SetYTitle("QE [1]");
374 disp9.SetYTitle("QE [1]");
375 disp10.SetYTitle("QE [1]");
376 disp11.SetYTitle("QE [1]");
377
378 disp12.SetYTitle("[1]");
379 disp13.SetYTitle("[1]");
380 disp14.SetYTitle("[1]");
381 disp15.SetYTitle("[1]");
382 disp16.SetYTitle("[1]");
383
384 disp17.SetYTitle("<Q>(High)/<Q>(Low) [1]");
385 disp18.SetYTitle("\\sigma_{Q}(High)/\\sigma_{Q}(Low) [1]");
386
387 disp19.SetYTitle("[1]");
388 disp20.SetYTitle("[1]");
389 disp21.SetYTitle("[1]");
390 disp22.SetYTitle("[1]");
391 // disp23.SetYTitle("[1]");
392 // disp24.SetYTitle("[1]");
393 // disp25.SetYTitle("[1]");
394 disp26.SetYTitle("[1]");
395 disp27.SetYTitle("[1]");
396
397 disp28.SetYTitle("Mean Abs. Time [FADC slice]");
398 disp29.SetYTitle("RMS Abs. Time [FADC slices]");
399
400 disp35.SetYTitle("Conv.Factor [Ph/FADC counts]");
401
402 for (UInt_t i=0;i<geomcam.GetNumPixels();i++)
403 {
404
405 MCalibrationChargePix &pix = (MCalibrationChargePix&)fCalibrationCam[i];
406 MCalibrationQEPix &qe = (MCalibrationQEPix&) fQECam [i];
407
408 if (!pix.IsFFactorMethodValid())
409 continue;
410
411 const Float_t convphe = pix.GetMeanConvFADC2Phe();
412 const Float_t quaeff = qe.GetQECascadesFFactor(0.);
413
414 disp35.Fill(i,convphe/quaeff);
415 disp35.SetUsed(i);
416 }
417
418
419 if (fRelTimes)
420 {
421 disp30.SetCamContent(fRelTimeCam,0);
422 disp30.SetCamError( fRelTimeCam,1);
423 disp31.SetCamContent(fRelTimeCam,2);
424 disp31.SetCamError( fRelTimeCam,3);
425 disp32.SetCamContent(fRelTimeCam,4);
426 disp33.SetCamContent(fBadPixels,20);
427 disp34.SetCamContent(fBadPixels,21);
428
429 disp30.SetYTitle("Time Offset [FADC units]");
430 disp31.SetYTitle("Timing resolution [FADC units]");
431 disp32.SetYTitle("P_{Time} [1]");
432 disp33.SetYTitle("[1]");
433 disp34.SetYTitle("[1]");
434 }
435
436
437
438 if (fDisplayType == kDataCheckDisplay)
439 {
440
441 TCanvas &c1 = fDisplay->AddTab("Fit.Charge");
442 c1.Divide(3, 3);
443
444 //
445 // MEAN CHARGES
446 //
447
448 c1.cd(1);
449 gPad->SetBorderMode(0);
450 gPad->SetTicks();
451 MHCamera *obj1=(MHCamera*)disp1.DrawCopy("hist");
452 //
453 // for the datacheck, fix the ranges!!
454 //
455 // obj1->SetMinimum(fgChargeMin);
456 // obj1->SetMaximum(fgChargeMax);
457 //
458 // Set the datacheck sizes:
459 //
460 FixDataCheckHist((TH1D*)obj1);
461 //
462 // set reference lines
463 //
464 // DisplayReferenceLines(obj1,0);
465
466 c1.cd(4);
467 gPad->SetBorderMode(0);
468 obj1->SetPrettyPalette();
469 obj1->Draw();
470
471 c1.cd(7);
472 gPad->SetBorderMode(0);
473 gPad->SetTicks();
474 TH1D *obj2 = (TH1D*)obj1->Projection(obj1->GetName());
475 obj2->Draw();
476 obj2->SetBit(kCanDelete);
477 obj2->Fit("gaus","Q");
478 TF1 *fun2 = obj2->GetFunction("gaus");
479 fun2->SetLineColor(kYellow);
480 //
481 // Set the datacheck sizes:
482 //
483 FixDataCheckHist(obj2);
484 obj2->SetStats(1);
485
486 //
487 // Display the outliers as dead and noisy pixels
488 //
489 DisplayOutliers(obj2,"dead","noisy");
490 TLatex flattex;
491 flattex.SetTextSize(0.06);
492 const Double_t minl = obj2->GetBinCenter(obj2->GetXaxis()->GetFirst());
493 const Double_t maxl = obj2->GetBinCenter(obj2->GetXaxis()->GetLast());
494 flattex.DrawLatex(minl+0.1*(maxl-minl),obj2->GetBinContent(obj2->GetMaximumBin())/1.3,
495 Form("Flatfielding precision: %4.2f%%",
496 fun2->GetParameter(2)/fun2->GetParameter(1)*100.));
497
498 //
499 // REDUCED SIGMAS
500 //
501
502 c1.cd(2);
503 gPad->SetBorderMode(0);
504 gPad->SetTicks();
505 MHCamera *obj3=(MHCamera*)disp4.DrawCopy("hist");
506 //
507 // for the datacheck, fix the ranges!!
508 //
509 // obj3->SetMinimum(fgChargeMin);
510 // obj3->SetMaximum(fgChargeMax);
511 //
512 // Set the datacheck sizes:
513 //
514 FixDataCheckHist((TH1D*)obj3);
515 //
516 // set reference lines
517 //
518 // DisplayReferenceLines(obj3,0);
519
520 c1.cd(5);
521 gPad->SetBorderMode(0);
522 obj3->SetPrettyPalette();
523 obj3->Draw();
524
525 c1.cd(8);
526 gPad->SetBorderMode(0);
527 if (geomcam.InheritsFrom("MGeomCamMagic"))
528 DisplayDoubleProject(&disp4, "dead", "noisy");
529
530 //
531 // PHOTO ELECTRONS
532 //
533
534 c1.cd(3);
535 gPad->SetBorderMode(0);
536 gPad->SetTicks();
537 MHCamera *obj4=(MHCamera*)disp5.DrawCopy("hist");
538 //
539 // for the datacheck, fix the ranges!!
540 //
541 // obj3->SetMinimum(fgChargeMin);
542 // obj3->SetMaximum(fgChargeMax);
543 //
544 // Set the datacheck sizes:
545 //
546 FixDataCheckHist((TH1D*)obj4);
547 //
548 // set reference lines
549 //
550 // DisplayReferenceLines(obj3,0);
551
552 c1.cd(6);
553 gPad->SetBorderMode(0);
554 obj4->SetPrettyPalette();
555 obj4->Draw();
556
557 c1.cd(9);
558 gPad->SetBorderMode(0);
559 if (geomcam.InheritsFrom("MGeomCamMagic"))
560 DisplayDoubleProject(&disp5, "dead", "noisy");
561
562 //
563 // CONVERSION FACTORS
564 //
565
566 TCanvas &c2 = fDisplay->AddTab("Conversion");
567 c2.Divide(3,3);
568
569 c2.cd(1);
570 gPad->SetBorderMode(0);
571 gPad->SetTicks();
572 MHCamera *obj5=(MHCamera*)disp6.DrawCopy("hist");
573 //
574 // for the datacheck, fix the ranges!!
575 //
576 obj5->SetMinimum(fgConvFADC2PheMin);
577 obj5->SetMaximum(fgConvFADC2PheMax);
578 //
579 // Set the datacheck sizes:
580 //
581 FixDataCheckHist((TH1D*)obj5);
582 //
583 // set reference lines
584 //
585 DisplayReferenceLines(obj5,2);
586
587 c2.cd(4);
588 gPad->SetBorderMode(0);
589 obj5->SetPrettyPalette();
590 obj5->Draw();
591
592 c2.cd(7);
593 gPad->SetBorderMode(0);
594 if (geomcam.InheritsFrom("MGeomCamMagic"))
595 DisplayDoubleProject(&disp6, "noisy", "dead");
596
597 //
598 // QUANTUM EFFICIENCY
599 //
600
601 c2.cd(2);
602 gPad->SetBorderMode(0);
603 gPad->SetTicks();
604 MHCamera *obj6=(MHCamera*)disp8.DrawCopy("hist");
605 //
606 // for the datacheck, fix the ranges!!
607 //
608 obj6->SetMinimum(fgQEMin);
609 obj6->SetMaximum(fgQEMax);
610 //
611 // Set the datacheck sizes:
612 //
613 FixDataCheckHist((TH1D*)obj6);
614 //
615 // set reference lines
616 //
617 DisplayReferenceLines(obj6,0);
618
619 c2.cd(5);
620 gPad->SetBorderMode(0);
621 obj6->SetPrettyPalette();
622 obj6->Draw();
623
624 c2.cd(8);
625 gPad->SetBorderMode(0);
626 if (geomcam.InheritsFrom("MGeomCamMagic"))
627 DisplayDoubleProject(&disp8, "noisy", "dead");
628
629 //
630 // CONVERSION FADC TO PHOTONS
631 //
632
633 c2.cd(3);
634 gPad->SetBorderMode(0);
635 gPad->SetTicks();
636 MHCamera *obj7=(MHCamera*)disp35.DrawCopy("hist");
637 //
638 // for the datacheck, fix the ranges!!
639 //
640 obj7->SetMinimum(fgConvFADC2PhotMin);
641 obj7->SetMaximum(fgConvFADC2PhotMax);
642 //
643 // Set the datacheck sizes:
644 //
645 FixDataCheckHist((TH1D*)obj7);
646 //
647 // set reference lines
648 //
649 DisplayReferenceLines(obj7,1);
650
651 c2.cd(6);
652 gPad->SetBorderMode(0);
653 obj7->SetPrettyPalette();
654 obj7->Draw();
655 c2.cd(9);
656 gPad->SetBorderMode(0);
657 if (geomcam.InheritsFrom("MGeomCamMagic"))
658 DisplayDoubleProject(&disp35, "noisy", "dead");
659
660 //
661 // UNSUITABLE PIXELS
662 //
663 TCanvas &c4 = fDisplay->AddTab("Defect");
664 c4.Divide(2,2);
665
666 c4.cd(1);
667 gPad->SetBorderMode(0);
668 gPad->SetTicks();
669 MHCamera *obj8=(MHCamera*)disp24.DrawCopy("hist");
670 //
671 // for the datacheck, fix the ranges!!
672 //
673 const Double_t max = 11.;
674 obj8->SetMinimum(0.);
675 obj8->SetMaximum(11.);
676 //
677 // Set the datacheck sizes:
678 //
679 FixDataCheckHist((TH1D*)obj8);
680
681 gStyle->SetPalette(1);
682 const Int_t numcol = gStyle->GetNumberOfColors();
683
684 TPaveText *pave = new TPaveText(0.0,0.0,0.99,0.99);
685 pave->SetBit(kCanDelete);
686 pave->ConvertNDCtoPad();
687 pave->SetTextSize(0.05);
688 TText *t0 = pave->AddText(" ");
689 TText *t1 = pave->AddText("Signal smaller 3 Pedestal RMS");
690 t1->SetTextColor(gStyle->GetColorPalette(Int_t(1./max*numcol)));
691 TText *t2 = pave->AddText("Signal Rel. error too large");
692 t2->SetTextColor(gStyle->GetColorPalette(Int_t(2./max*numcol)));
693 TText *t3 = pave->AddText("Signal Sigma smaller than Pedestal RMS");
694 t3->SetTextColor(gStyle->GetColorPalette(Int_t(3./max*numcol)));
695 TText *t4 = pave->AddText("Low Gain Saturation");
696 t4->SetTextColor(gStyle->GetColorPalette(Int_t(4./max*numcol)));
697 TText *t5 = pave->AddText("Mean Arr. Time In First Extraction Bin");
698 t5->SetTextColor(gStyle->GetColorPalette(Int_t(5./max*numcol)));
699 TText *t6 = pave->AddText("Mean Arr. Time In Last 2 Extraction Bins");
700 t6->SetTextColor(gStyle->GetColorPalette(Int_t(6./max*numcol)));
701 TText *t7 = pave->AddText("Deviating Number of Photo-electrons");
702 t7->SetTextColor(gStyle->GetColorPalette(Int_t(7./max*numcol)));
703 TText *t8 = pave->AddText("Deviating global F-Factor");
704 t8->SetTextColor(gStyle->GetColorPalette(Int_t(8./max*numcol)));
705 TText *t9 = pave->AddText("Deviating Number of Photons");
706 t9->SetTextColor(gStyle->GetColorPalette(Int_t(9./max*numcol)));
707 TText *t10= pave->AddText("Previously Excluded");
708 t10->SetTextColor(gStyle->GetColorPalette(Int_t(10./max*numcol)));
709 pave->Draw();
710
711 c4.cd(3);
712 gPad->SetBorderMode(0);
713 obj8->Draw();
714 obj8->SetPrettyPalette();
715
716 //
717 // UNRELIABLE PIXELS
718 //
719
720 c4.cd(2);
721 gPad->SetBorderMode(0);
722 gPad->SetTicks();
723 MHCamera *obj9=(MHCamera*)disp25.DrawCopy("hist");
724 //
725 // for the datacheck, fix the ranges!!
726 //
727 const Double_t max2 = 8.;
728 obj9->SetMinimum(0.);
729 obj9->SetMaximum(max2);
730 //
731 // Set the datacheck sizes:
732 //
733 FixDataCheckHist((TH1D*)obj9);
734
735 gStyle->SetPalette(1);
736
737 TPaveText *pave2 = new TPaveText(0.0,0.0,0.99,0.99);
738 pave2->SetBit(kCanDelete);
739 pave2->ConvertNDCtoPad();
740 pave2->SetTextSize(0.05);
741 TText *tt0 = pave2->AddText(" ");
742 TText *tt1 = pave2->AddText("High Gain Signals could not be fitted");
743 tt1->SetTextColor(gStyle->GetColorPalette(Int_t(1./max2*numcol)));
744 TText *tt2 = pave2->AddText("Low Gain Signals could not be fitted");
745 tt2->SetTextColor(gStyle->GetColorPalette(Int_t(2./max2*numcol)));
746 TText *tt3 = pave2->AddText("Relative Arr. Times could not be fitted");
747 tt3->SetTextColor(gStyle->GetColorPalette(Int_t(3./max2*numcol)));
748 TText *tt4 = pave2->AddText("High Gain Signals Oscillation");
749 tt4->SetTextColor(gStyle->GetColorPalette(Int_t(4./max2*numcol)));
750 TText *tt5 = pave2->AddText("Low Gain Signals Oscillation");
751 tt5->SetTextColor(gStyle->GetColorPalette(Int_t(5./max2*numcol)));
752 TText *tt6 = pave2->AddText("Relative Arr. Times Oscillation");
753 tt6->SetTextColor(gStyle->GetColorPalette(Int_t(6./max2*numcol)));
754 pave2->Draw();
755
756 c4.cd(4);
757 gPad->SetBorderMode(0);
758 obj9->SetPrettyPalette();
759 obj9->Draw();
760
761 if (fRelTimes)
762 {
763 // Rel. Times
764 TCanvas &c5 = fDisplay->AddTab("Rel. Times");
765 c5.Divide(2,4);
766
767 disp30.CamDraw(c5, 1, 2, 2);
768 disp31.CamDraw(c5, 2, 2, 2);
769 }
770
771 return;
772 }
773
774 if (fDisplayType == kNormalDisplay)
775 {
776
777 // Charges
778 TCanvas &c11 = fDisplay->AddTab("Fit.Charge");
779 c11.Divide(2, 4);
780
781 disp1.CamDraw(c11, 1, 2, 5, 1);
782 disp2.CamDraw(c11, 2, 2, 5, 1);
783
784 // Reduced Sigmas
785 TCanvas &c12 = fDisplay->AddTab("Red.Sigma");
786 c12.Divide(2,4);
787
788 disp3.CamDraw(c12, 1, 2, 5, 1);
789 disp4.CamDraw(c12, 2, 2, 5, 1);
790
791 // F-Factor
792 TCanvas &c13 = fDisplay->AddTab("Phe's");
793 c13.Divide(3,4);
794
795 disp5.CamDraw(c13, 1, 3, 5, 1);
796 disp6.CamDraw(c13, 2, 3, 5, 1);
797 disp7.CamDraw(c13, 3, 3, 5, 1);
798
799 // QE's
800 TCanvas &c14 = fDisplay->AddTab("QE's");
801 c14.Divide(4,4);
802
803 disp8.CamDraw(c14, 1, 4, 5, 1);
804 disp9.CamDraw(c14, 2, 4, 5, 1);
805 disp10.CamDraw(c14, 3, 4, 5, 1);
806 disp11.CamDraw(c14, 4, 4, 5, 1);
807
808 // Defects
809 TCanvas &c15 = fDisplay->AddTab("Defect");
810 // c15.Divide(5,2);
811 c15.Divide(4,2);
812
813 /*
814 disp23.CamDraw(c15, 1, 5, 0);
815 disp24.CamDraw(c15, 2, 5, 0);
816 disp25.CamDraw(c15, 3, 5, 0);
817 disp26.CamDraw(c15, 4, 5, 0);
818 disp27.CamDraw(c15, 5, 5, 0);
819 */
820 disp24.CamDraw(c15, 1, 4, 0);
821 disp25.CamDraw(c15, 2, 4, 0);
822 disp26.CamDraw(c15, 3, 4, 0);
823 disp27.CamDraw(c15, 4, 4, 0);
824
825 // Abs. Times
826 TCanvas &c16 = fDisplay->AddTab("Abs. Times");
827 c16.Divide(2,3);
828
829 disp28.CamDraw(c16, 1, 2, 5);
830 disp29.CamDraw(c16, 2, 2, 5);
831
832 if (fRelTimes)
833 {
834 // Rel. Times
835 TCanvas &c17 = fDisplay->AddTab("Rel. Times");
836 c17.Divide(2,4);
837
838 disp30.CamDraw(c17, 1, 2, 5, 1);
839 disp31.CamDraw(c17, 2, 2, 5, 1);
840 }
841
842 return;
843 }
844
845 if (fDisplayType == kFullDisplay)
846 {
847 MHCalibrationCam *cam = (MHCalibrationCam*)plist.FindObject("MHCalibrationChargeCam");
848
849 for (Int_t sector=1;sector<cam->GetAverageSectors();sector++)
850 {
851 cam->GetAverageHiGainSector(sector).DrawClone("all");
852 cam->GetAverageLoGainSector(sector).DrawClone("all");
853 }
854
855 // Charges
856 TCanvas &c21 = fDisplay->AddTab("Fit.Charge");
857 c21.Divide(2, 4);
858
859 disp1.CamDraw(c21, 1, 2, 2, 1);
860 disp2.CamDraw(c21, 2, 2, 2, 1);
861
862 // Reduced Sigmas
863 TCanvas &c23 = fDisplay->AddTab("Red.Sigma");
864 c23.Divide(2,4);
865
866 disp3.CamDraw(c23, 1, 2, 2, 1);
867 disp4.CamDraw(c23, 2, 2, 2, 1);
868
869 // F-Factor
870 TCanvas &c24 = fDisplay->AddTab("Phe's");
871 c24.Divide(3,5);
872
873 disp5.CamDraw(c24, 1, 3, 2, 1, 1);
874 disp6.CamDraw(c24, 2, 3, 2, 1, 1);
875 disp7.CamDraw(c24, 3, 3, 2, 1, 1);
876
877 // QE's
878 TCanvas &c25 = fDisplay->AddTab("QE's");
879 c25.Divide(4,5);
880
881 disp8.CamDraw(c25, 1, 4, 2, 1, 1);
882 disp9.CamDraw(c25, 2, 4, 2, 1, 1);
883 disp10.CamDraw(c25, 3, 4, 2, 1, 1);
884 disp11.CamDraw(c25, 4, 4, 2, 1, 1);
885
886 // Validity
887 TCanvas &c26 = fDisplay->AddTab("Valid");
888 c26.Divide(4,2);
889
890 disp12.CamDraw(c26, 1, 4, 0);
891 disp13.CamDraw(c26, 2, 4, 0);
892 disp14.CamDraw(c26, 3, 4, 0);
893 disp15.CamDraw(c26, 4, 4, 0);
894
895 // Other info
896 TCanvas &c27 = fDisplay->AddTab("HiLoGain");
897 c27.Divide(3,3);
898
899 disp16.CamDraw(c27, 1, 3, 0);
900 disp17.CamDraw(c27, 2, 3, 1);
901 disp18.CamDraw(c27, 3, 3, 1);
902
903 // Pickup
904 TCanvas &c28 = fDisplay->AddTab("Pickup");
905 c28.Divide(4,2);
906
907 disp19.CamDraw(c28, 1, 4, 0);
908 disp20.CamDraw(c28, 2, 4, 0);
909 disp21.CamDraw(c28, 3, 4, 0);
910 disp22.CamDraw(c28, 4, 4, 0);
911
912 // Defects
913 TCanvas &c29 = fDisplay->AddTab("Defect");
914 // c29.Divide(5,2);
915 c29.Divide(4,2);
916
917 disp24.CamDraw(c29, 1, 4, 0);
918 disp25.CamDraw(c29, 2, 4, 0);
919 disp26.CamDraw(c29, 3, 4, 0);
920 disp27.CamDraw(c29, 4, 4, 0);
921
922 // Abs. Times
923 TCanvas &c30 = fDisplay->AddTab("Abs. Times");
924 c30.Divide(2,3);
925
926 disp28.CamDraw(c30, 1, 2, 2);
927 disp29.CamDraw(c30, 2, 2, 1);
928
929 if (fRelTimes)
930 {
931 // Rel. Times
932 TCanvas &c31 = fDisplay->AddTab("Rel. Times");
933 c31.Divide(3,5);
934
935 disp30.CamDraw(c31, 1, 3, 2, 1, 1);
936 disp31.CamDraw(c31, 2, 3, 2, 1, 1);
937 disp32.CamDraw(c31, 3, 3, 4, 1, 1);
938
939 // Time Defects
940 TCanvas &c32 = fDisplay->AddTab("Time Def.");
941 c32.Divide(2,2);
942
943 disp33.CamDraw(c32, 1, 2, 0);
944 disp34.CamDraw(c32, 2, 2, 0);
945
946 MHCalibrationCam *cam = (MHCalibrationCam*)plist.FindObject("MHCalibrationRelTimeCam");
947
948 for (Int_t sector=1;sector<cam->GetAverageSectors();sector++)
949 {
950 cam->GetAverageHiGainSector(sector).DrawClone("fourierevents");
951 cam->GetAverageLoGainSector(sector).DrawClone("fourierevents");
952 }
953
954 }
955
956 return;
957 }
958}
959
960
961void MJCalibration::DisplayReferenceLines(MHCamera *cam, const Int_t what) const
962{
963
964 const MGeomCam *geom = cam->GetGeometry();
965
966 Double_t x = geom->InheritsFrom("MGeomCamMagic") ? 397 : cam->GetNbinsX() ;
967
968 TLine line;
969 line.SetLineStyle(kDashed);
970 line.SetLineWidth(3);
971 line.SetLineColor(kBlue);
972
973 TLine *l1 = NULL;
974
975 if (what == 0)
976 l1 = line.DrawLine(0, fgRefQEInner, x, fgRefQEInner);
977 else if (what == 1)
978 l1 = line.DrawLine(0, fgRefConvFADC2PhotInner, x, fgRefConvFADC2PhotInner);
979 else if (what == 2)
980 l1 = line.DrawLine(0, fgRefConvFADC2PheInner, x, fgRefConvFADC2PheInner );
981
982 if (geom->InheritsFrom("MGeomCamMagic"))
983 {
984 const Double_t x2 = cam->GetNbinsX();
985
986 switch (what)
987 {
988 case 0:
989 line.DrawLine(x2, fgRefQEOuter, 398, fgRefQEOuter);
990 break;
991 case 1:
992 line.DrawLine(x2, fgRefConvFADC2PhotOuter, 398, fgRefConvFADC2PhotOuter );
993 break;
994 case 2:
995 line.DrawLine(x2, fgRefConvFADC2PheOuter, 398, fgRefConvFADC2PheOuter);
996 break;
997 }
998 }
999
1000 TLegend *leg = new TLegend(what ? 0.2 : 0.6,0.75,what ? 0.5 : 0.9 ,0.85);
1001 leg->SetBit(kCanDelete);
1002 leg->AddEntry(l1, "Reference","l");
1003 leg->Draw();
1004}
1005
1006void MJCalibration::DisplayOutliers(TH1D *hist, const char* whatsmall, const char* whatbig) const
1007{
1008
1009 const Float_t mean = hist->GetFunction("gaus")->GetParameter(1);
1010 const Float_t lolim = mean - 4.0*hist->GetFunction("gaus")->GetParameter(2);
1011 const Float_t uplim = mean + 4.0*hist->GetFunction("gaus")->GetParameter(2);
1012 const Stat_t dead = hist->Integral(0,hist->FindBin(lolim)-1);
1013 const Stat_t noisy = hist->Integral(hist->FindBin(uplim)+1,hist->GetNbinsX()+1);
1014
1015 const Double_t max = hist->GetBinContent(hist->GetMaximumBin());
1016
1017 const Double_t minl = hist->GetBinCenter(hist->GetXaxis()->GetFirst());
1018 const Double_t maxl = hist->GetBinCenter(hist->GetXaxis()->GetLast());
1019
1020 TLatex deadtex;
1021 deadtex.SetTextSize(0.06);
1022 deadtex.DrawLatex(minl+0.1*(maxl-minl),max/1.1,
1023 Form("%3i %s pixels",(Int_t)dead,whatsmall));
1024
1025 TLatex noisytex;
1026 noisytex.SetTextSize(0.06);
1027 noisytex.DrawLatex(minl+0.1*(maxl-minl),max/1.2,
1028 Form("%3i %s pixels",(Int_t)noisy,whatbig));
1029
1030}
1031
1032void MJCalibration::FixDataCheckHist(TH1D *hist) const
1033{
1034
1035 hist->SetDirectory(NULL);
1036
1037 //
1038 // set the labels bigger
1039 //
1040 TAxis *xaxe = hist->GetXaxis();
1041 TAxis *yaxe = hist->GetYaxis();
1042
1043 xaxe->CenterTitle();
1044 yaxe->CenterTitle();
1045 xaxe->SetTitleSize(0.06);
1046 yaxe->SetTitleSize(0.06);
1047 xaxe->SetTitleOffset(0.8);
1048 yaxe->SetTitleOffset(0.85);
1049 xaxe->SetLabelSize(0.05);
1050 yaxe->SetLabelSize(0.05);
1051
1052}
1053
1054// --------------------------------------------------------------------------
1055//
1056// Find the colour of the pulsing LED:
1057// - If the run number is smaller than gkIFAEBoxInaugurationRun, take MCalibrationCam::kCT1
1058// - Otherwise find the colour out of the run name
1059// - If no colour is found, return kFALSE
1060//
1061Bool_t MJCalibration::FindColor()
1062{
1063
1064 if (fSequence)
1065 {
1066 fColor = MCalibrationCam::kCT1;
1067 return kTRUE;
1068 }
1069
1070 const UInt_t nruns = fRuns->GetNumRuns();
1071
1072 if (nruns == 0)
1073 return kFALSE;
1074
1075 TArrayI arr = fRuns->GetRuns();
1076
1077 if (arr[nruns-1] < gkIFAEBoxInaugurationRun)
1078 {
1079 *fLog << "Found colour kCT1 in runs: " << fRuns->GetRunsAsString() << endl;
1080 fColor = MCalibrationCam::kCT1;
1081 return kTRUE;
1082 }
1083
1084 TString filenames;
1085 ((MDirIter*)fRuns)->Reset();
1086
1087 while (!(filenames=((MDirIter*)fRuns)->Next()).IsNull())
1088 {
1089
1090 filenames.ToLower();
1091
1092 //
1093 // Here starts the list of runs where the shifters did not put
1094 // a colour, but which have been found out by other means.
1095 // FIXME: This list has is only preliminary and has to move into the
1096 // database!!
1097 //
1098 if (filenames.Contains("_30090_"))
1099 if (fColor == MCalibrationCam::kNONE)
1100 {
1101 *fLog << "Found colour: kGREEN in " << filenames << endl;
1102 fColor = MCalibrationCam::kGREEN;
1103 }
1104 else if (fColor != MCalibrationCam::kNONE)
1105 {
1106 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1107 return kFALSE;
1108 }
1109
1110 if (filenames.Contains("_27474_"))
1111 if (fColor == MCalibrationCam::kNONE)
1112 {
1113 *fLog << "Sorry, run 27474 was taken with CLOSED LIDS. It should not be used! "
1114 << "Selected runs were: " << filenames << endl;
1115 fColor = MCalibrationCam::kNONE;
1116 return kFALSE;
1117 }
1118 else if (fColor != MCalibrationCam::kNONE)
1119 {
1120 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1121 return kFALSE;
1122 }
1123
1124 if (filenames.Contains("_26924_"))
1125 if (fColor == MCalibrationCam::kNONE)
1126 {
1127 *fLog << "Found colour: kGREEN in " << filenames << endl;
1128 fColor = MCalibrationCam::kGREEN;
1129 }
1130 else if (fColor != MCalibrationCam::kGREEN)
1131 {
1132 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1133 return kFALSE;
1134 }
1135
1136
1137 if (filenames.Contains("_26568_"))
1138 if (fColor == MCalibrationCam::kNONE)
1139 {
1140 *fLog << "Found colour: kGREEN in " << filenames << endl;
1141 fColor = MCalibrationCam::kGREEN;
1142 }
1143 else if (fColor != MCalibrationCam::kGREEN)
1144 {
1145 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1146 return kFALSE;
1147 }
1148
1149 if (filenames.Contains("_26412_"))
1150 if (fColor == MCalibrationCam::kNONE)
1151 {
1152 *fLog << "Found colour: kGREEN in " << filenames << endl;
1153 fColor = MCalibrationCam::kGREEN;
1154 }
1155 else if (fColor != MCalibrationCam::kGREEN)
1156 {
1157 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1158 return kFALSE;
1159 }
1160
1161
1162 if (filenames.Contains("_26409_"))
1163 if (fColor == MCalibrationCam::kNONE)
1164 {
1165 *fLog << "Found colour: kGREEN in " << filenames << endl;
1166 fColor = MCalibrationCam::kGREEN;
1167 }
1168 else if (fColor != MCalibrationCam::kGREEN)
1169 {
1170 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1171 return kFALSE;
1172 }
1173
1174 if (filenames.Contains("_26408_"))
1175 if (fColor == MCalibrationCam::kNONE)
1176 {
1177 *fLog << "Found colour: kGREEN in " << filenames << endl;
1178 fColor = MCalibrationCam::kGREEN;
1179 }
1180 else if (fColor != MCalibrationCam::kGREEN)
1181 {
1182 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1183 return kFALSE;
1184 }
1185
1186
1187 if (filenames.Contains("_26402_"))
1188 if (fColor == MCalibrationCam::kNONE)
1189 {
1190 *fLog << "Found colour: kBLUE in " << filenames << endl;
1191 fColor = MCalibrationCam::kBLUE;
1192 }
1193 else if (fColor != MCalibrationCam::kBLUE)
1194 {
1195 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1196 return kFALSE;
1197 }
1198
1199 if (filenames.Contains("_20661_"))
1200 if (fColor == MCalibrationCam::kNONE)
1201 {
1202 *fLog << "Found colour: kGREEN in " << filenames << endl;
1203 fColor = MCalibrationCam::kGREEN;
1204 }
1205 else if (fColor != MCalibrationCam::kGREEN)
1206 {
1207 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1208 return kFALSE;
1209 }
1210
1211 if (filenames.Contains("_20660_"))
1212 if (fColor == MCalibrationCam::kNONE)
1213 {
1214 *fLog << "Found colour: kGREEN in " << filenames << endl;
1215 fColor = MCalibrationCam::kGREEN;
1216 }
1217 else if (fColor != MCalibrationCam::kGREEN)
1218 {
1219 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1220 return kFALSE;
1221 }
1222
1223 //
1224 // Here start the runs where the shifter put
1225 // the colour.
1226 //
1227 if (filenames.Contains("green"))
1228 if (fColor == MCalibrationCam::kNONE)
1229 {
1230 *fLog << "Found colour: kGREEN in " << filenames << endl;
1231 fColor = MCalibrationCam::kGREEN;
1232 }
1233 else if (fColor != MCalibrationCam::kGREEN)
1234 {
1235 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1236 return kFALSE;
1237 }
1238
1239 if (filenames.Contains("blue"))
1240 if (fColor == MCalibrationCam::kNONE)
1241 {
1242 *fLog << "Found colour: kBLUE in " << filenames << endl;
1243 fColor = MCalibrationCam::kBLUE;
1244 }
1245 else if (fColor != MCalibrationCam::kBLUE)
1246 {
1247 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1248 return kFALSE;
1249 }
1250
1251 if (filenames.Contains("uv"))
1252 if (fColor == MCalibrationCam::kNONE)
1253 {
1254 *fLog << "Found colour: kUV in " << filenames << endl;
1255 fColor = MCalibrationCam::kUV;
1256 }
1257 else if (fColor != MCalibrationCam::kUV)
1258 {
1259 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1260 return kFALSE;
1261 }
1262
1263 if (filenames.Contains("ct1"))
1264 if (fColor == MCalibrationCam::kNONE)
1265 {
1266 *fLog << "Found colour: kCT1 in " << filenames << endl;
1267 fColor = MCalibrationCam::kCT1;
1268 }
1269 else if (fColor != MCalibrationCam::kCT1)
1270 {
1271 *fLog << err << "Different colour found in " << filenames << "... abort" << endl;
1272 return kFALSE;
1273 }
1274
1275 }
1276
1277 if (fColor == MCalibrationCam::kNONE)
1278 {
1279 *fLog << "No colour found in filenames of runs: " << fRuns->GetRunsAsString()
1280 << "... abort" << endl;
1281 return kFALSE;
1282 }
1283
1284
1285 return kTRUE;
1286}
1287
1288// --------------------------------------------------------------------------
1289//
1290// Retrieve the output file written by WriteResult()
1291//
1292const char* MJCalibration::GetOutputFile() const
1293{
1294 if (fSequence)
1295 return Form("%s/calib%06d.root", (const char*)fOutputPath, fSequence->GetSequence());
1296 if (!fRuns)
1297 return "";
1298
1299 return Form("%s/%s-F1.root", (const char*)fOutputPath, (const char*)fRuns->GetRunsAsFileName());
1300}
1301
1302Bool_t MJCalibration::IsUseBlindPixel() const
1303{
1304 return TESTBIT(fDevices,kUseBlindPixel);
1305}
1306
1307Bool_t MJCalibration::IsUsePINDiode() const
1308{
1309 return TESTBIT(fDevices,kUsePINDiode);
1310}
1311
1312void MJCalibration::SetEnv(const char *env)
1313{
1314 if (fEnv)
1315 delete fEnv;
1316 fEnv = new TEnv(env);
1317}
1318
1319void MJCalibration::CheckEnv()
1320{
1321 if (!fEnv)
1322 return;
1323
1324 TString e1 = fEnv->GetValue("MJCalibration.OutputPath", "");
1325 if (!e1.IsNull())
1326 {
1327 e1.ReplaceAll("\015", "");
1328 SetOutputPath(e1);
1329 }
1330
1331 TString col = fEnv->GetValue("MJCalibration.Color", "");
1332 if (!col.IsNull())
1333 {
1334 }
1335
1336 TString dis = fEnv->GetValue("MJCalibration.Display", "");
1337 if (dis.BeginsWith("Full", TString::kIgnoreCase))
1338 SetFullDisplay();
1339 if (dis.BeginsWith("DataCheck", TString::kIgnoreCase))
1340 SetDataCheckDisplay();
1341 if (dis.BeginsWith("Normal", TString::kIgnoreCase))
1342 SetNormalDisplay();
1343
1344 SetRelTimeCalibration(fEnv->GetValue("MJCalibration.RelTimeCalibration", fRelTimes));
1345 SetDataCheck(fEnv->GetValue("MJCalibration.Datacheck", fDataCheck));
1346 SetDebug(fEnv->GetValue("MJCalibration.Debug", fDebug));
1347 SetUseBlindPixel(fEnv->GetValue("MJCalibration.UseBlindPixel", IsUseBlindPixel()));
1348 SetUsePINDiode(fEnv->GetValue("MJCalibration.UsePINDiode", IsUsePINDiode()));
1349}
1350
1351// --------------------------------------------------------------------------
1352//
1353// Call the ProcessFile(MPedestalCam)
1354//
1355Bool_t MJCalibration::Process(MPedestalCam &pedcam)
1356{
1357 if (!ReadCalibrationCam())
1358 return ProcessFile(pedcam);
1359
1360 return kTRUE;
1361}
1362
1363void MJCalibration::InitBlindPixel(MExtractBlindPixel &blindext,
1364 MHCalibrationChargeBlindCam &blindcam)
1365{
1366
1367 Int_t run = fSequence ? fSequence->GetLastRun() : fRuns->GetRuns()[fRuns->GetNumRuns()-1];
1368
1369 //
1370 // Initialize the blind pixel. Unfortunately, there is a hardware difference
1371 // in the first blind pixel until run "gkSecondBlindPixelInstallation" and the
1372 // later setup. The first needs to use a filter because of the length of
1373 // spurious NSB photon signals. The latter get better along extracting the amplitude
1374 // from a small window.
1375 //
1376 if (run < gkSecondBlindPixelInstallation)
1377 {
1378 blindext.SetModified(kFALSE);
1379 blindext.SetExtractionType(MExtractBlindPixel::kIntegral);
1380 blindext.SetExtractionType(MExtractBlindPixel::kFilter);
1381 blindext.SetRange(10,19,0,6);
1382 blindext.SetNSBFilterLimit(70);
1383 blindcam.SetFitFunc( MHCalibrationChargeBlindPix::kEPoisson5 );
1384 }
1385 else
1386 {
1387 blindext.SetModified(kTRUE);
1388 blindext.SetExtractionType(MExtractBlindPixel::kAmplitude);
1389 blindext.SetExtractionType(MExtractBlindPixel::kFilter);
1390 blindext.SetRange(5,8,0,2);
1391 blindext.SetNSBFilterLimit(38);
1392
1393 if (run < gkThirdBlindPixelInstallation)
1394 blindext.SetNumBlindPixels(2);
1395 else
1396 blindext.SetNumBlindPixels(3);
1397 }
1398}
1399
1400// --------------------------------------------------------------------------
1401//
1402// Execute the task list and the eventloop:
1403//
1404// - Check if there are fRuns, otherwise return
1405// - Check the colour of the files in fRuns (FindColor()), otherwise return
1406// - Check for consistency between run numbers and number of files
1407// - Add fRuns to MReadMarsFile
1408// - Put into MParList:
1409// 1) MPedestalCam (pedcam)
1410// 2) MCalibrationQECam (fQECam)
1411// 3) MCalibrationChargeCam (fCalibrationCam)
1412// 4) MCalibrationRelTimeCam (fRelTimeCam) (only if flag fRelTimes is chosen)
1413// 5) MBadPixelsCam (fBadPixels)
1414// 6) MCalibrationChargePINDiode
1415// 7) MCalibrationChargeBlindPix
1416// - Put into the MTaskList:
1417// 1) MReadMarsFile
1418// 2) MBadPixelsMerge
1419// 3) MGeomApply
1420// 4) MExtractor
1421// 5) MExtractPINDiode
1422// 6) MExtractBlindPixel
1423// 7) MExtractTime (only if flag fRelTimes is chosen)
1424// 8) MContinue(MFCosmics)
1425// 9) MFillH("MHCalibrationChargePINDiode", "MExtractedSignalPINDiode")
1426// 10) MFillH("MHCalibrationChargeBlindCam", "MExtractedSignalBlindPixel")
1427// 11) MFillH("MHCalibrationChargeCam", "MExtractedSignalCam")
1428// 12) MFillH("MHCalibrationChargeCam", "MExtractedSignalCam")
1429// 13) MCalibrationChargeCalc
1430// 14) MFillH("MHCalibrationRelTimeCam", "MArrivalTimeCam") (only if flag fRelTimes is chosen)
1431// 15) MCalibrationRelTimeCalc
1432// - Execute MEvtLoop
1433// - DisplayResult()
1434// - WriteResult()
1435//
1436Bool_t MJCalibration::ProcessFile(MPedestalCam &pedcam)
1437{
1438 if (!fRuns && !fSequence)
1439 {
1440 *fLog << err << "No Runs choosen... abort." << endl;
1441 return kFALSE;
1442 }
1443
1444 if (!fSequence && fRuns->GetNumRuns() != fRuns->GetNumEntries())
1445 {
1446 *fLog << err << "Number of files found doesn't match number of runs... abort."
1447 << fRuns->GetNumRuns() << " vs. " << fRuns->GetNumEntries() << endl;
1448 return kFALSE;
1449 }
1450
1451 *fLog << inf;
1452 fLog->Separator(GetDescriptor());
1453
1454 if (!FindColor())
1455 return kFALSE;
1456
1457 *fLog << "Calculate MCalibrationCam from ";
1458 if (fSequence)
1459 *fLog << "Sequence #" << fSequence->GetSequence() << endl;
1460 else
1461 *fLog << "Runs " << fRuns->GetRunsAsString() << endl;
1462 *fLog << endl;
1463
1464 CheckEnv();
1465
1466 // Setup Tasklist
1467 MParList plist;
1468 MTaskList tlist;
1469 plist.AddToList(&tlist);
1470
1471 MReadMarsFile read("Events");
1472 MRawFileRead rawread(NULL);
1473
1474 MDirIter iter;
1475 if (fSequence)
1476 fSequence->SetupCalRuns(iter);
1477
1478 if (fDataCheck)
1479 {
1480 rawread.AddFiles(fSequence ? iter : *fRuns);
1481 tlist.AddToList(&rawread);
1482 }
1483 else
1484 {
1485 read.DisableAutoScheme();
1486 static_cast<MRead&>(read).AddFiles(fSequence ? iter : *fRuns);
1487 tlist.AddToList(&read);
1488 }
1489
1490 MHCalibrationChargeCam chargecam;
1491 MHCalibrationChargeBlindCam blindcam;
1492
1493 plist.AddToList(&pedcam);
1494 plist.AddToList(&chargecam);
1495 plist.AddToList(&blindcam);
1496 plist.AddToList(&fBadPixels);
1497 plist.AddToList(&fQECam);
1498 plist.AddToList(&fCalibrationCam);
1499 plist.AddToList(&fCalibrationBlindCam);
1500 plist.AddToList(&fCalibrationPINDiode);
1501 plist.AddToList(&fRelTimeCam);
1502
1503 MGeomApply apply;
1504 MBadPixelsMerge merge(&fBadPixels);
1505 MExtractPINDiode pinext;
1506 MExtractBlindPixel blindext;
1507 InitBlindPixel(blindext, blindcam);
1508 MExtractSlidingWindow extract2;
1509 MExtractTimeFastSpline timespline;
1510 MCalibrationChargeCalc calcalc;
1511 MCalibrationRelTimeCalc timecalc;
1512
1513 if (!fSequence)
1514 {
1515 calcalc.SetOutputPath(fOutputPath);
1516 calcalc.SetOutputFile(Form("%s-ChargeCalibStat.txt",(const char*)fRuns->GetRunsAsFileName()));
1517 }
1518
1519 if (fDebug)
1520 {
1521 chargecam.SetDebug();
1522 calcalc.SetDebug();
1523 }
1524
1525 //
1526 // As long as there are no DM's, have to colour by hand
1527 //
1528 chargecam.SetColor (fColor);
1529 calcalc.SetPulserColor(fColor);
1530
1531 MFillH fillpin("MHCalibrationChargePINDiode", "MExtractedSignalPINDiode");
1532 MFillH fillbnd("MHCalibrationChargeBlindPix", "MExtractedSignalBlindPixel");
1533 MFillH fillcam("MHCalibrationChargeCam", "MExtractedSignalCam");
1534 MFillH filltme("MHCalibrationRelTimeCam", "MArrivalTimeCam");
1535 fillpin.SetNameTab("PINDiode");
1536 fillbnd.SetNameTab("BlindPix");
1537 fillcam.SetNameTab("Charge");
1538 filltme.SetNameTab("RelTimes");
1539
1540 TString drawoption;
1541
1542 if (fDisplayType == kDataCheckDisplay)
1543 drawoption += "datacheck";
1544 if (fDisplayType == kFullDisplay)
1545 drawoption += " all";
1546
1547 fillcam.SetDrawOption(drawoption.Data());
1548 fillbnd.SetDrawOption(drawoption.Data());
1549 fillpin.SetDrawOption(drawoption.Data());
1550 filltme.SetDrawOption(drawoption.Data());
1551
1552 //
1553 // Apply a filter against cosmics
1554 // (will have to be needed in the future
1555 // when the calibration hardware-trigger is working)
1556 //
1557 MFCosmics cosmics;
1558 MContinue cont(&cosmics);
1559
1560 tlist.AddToList(&merge);
1561 tlist.AddToList(&apply);
1562
1563 MTaskEnv taskenv("ExtractSignal");
1564 taskenv.SetDefault(fExtractor ? fExtractor : &extract2);
1565
1566 tlist.AddToList(&taskenv);
1567 tlist.AddToList(&pinext);
1568 tlist.AddToList(&blindext);
1569
1570 MTaskEnv taskenv2("ExtractTime");
1571 taskenv2.SetDefault(fTimeExtractor ? fTimeExtractor : &timespline);
1572
1573 if (fRelTimes)
1574 tlist.AddToList(&taskenv2);
1575
1576 if (fColor == MCalibrationCam::kCT1)
1577 tlist.AddToList(&cont);
1578
1579 tlist.AddToList(&fillcam);
1580
1581 if (fRelTimes)
1582 {
1583 tlist.AddToList(&filltme);
1584 tlist.AddToList(&timecalc);
1585 }
1586
1587 if (IsUseBlindPixel())
1588 tlist.AddToList(&fillbnd);
1589 if (IsUsePINDiode())
1590 tlist.AddToList(&fillpin);
1591
1592 tlist.AddToList(&calcalc);
1593
1594 // Create and setup the eventloop
1595 MEvtLoop evtloop(fName);
1596 evtloop.SetParList(&plist);
1597 evtloop.SetDisplay(fDisplay);
1598 evtloop.SetLogStream(fLog);
1599 if (fEnv)
1600 evtloop.ReadEnv(*fEnv);
1601
1602 // Execute first analysis
1603 if (!evtloop.Eventloop())
1604 {
1605 *fLog << err << GetDescriptor() << ": Failed." << endl;
1606 return kFALSE;
1607 }
1608
1609 tlist.PrintStatistics();
1610
1611 //
1612 // The next lines are necessary in order to avoid that
1613 // the last entry drawn by MFillH gets deleted again from
1614 // the display. No idea where this comes from...
1615 //
1616 if (fDisplay)
1617 {
1618 if (IsUsePINDiode())
1619 {
1620 MHCalibrationChargePINDiode *pin =
1621 (MHCalibrationChargePINDiode*)plist.FindObject("MHCalibrationChargePINDiode");
1622 pin->DrawClone(Form("nonew %s",drawoption.Data()));
1623 }
1624 else if (IsUseBlindPixel())
1625 {
1626 MHCalibrationChargeBlindCam *cam =
1627 (MHCalibrationChargeBlindCam*)plist.FindObject("MHCalibrationChargeBlindCam");
1628 cam->DrawClone(Form("nonew %s",drawoption.Data()));
1629 }
1630 else if (fRelTimes)
1631 {
1632 MHCalibrationRelTimeCam *cam =
1633 (MHCalibrationRelTimeCam*)plist.FindObject("MHCalibrationRelTimeCam");
1634 cam->DrawClone(Form("nonew %s",drawoption.Data()));
1635 }
1636 else
1637 {
1638 MHCalibrationChargeCam *cam =
1639 (MHCalibrationChargeCam*)plist.FindObject("MHCalibrationChargeCam");
1640 cam->DrawClone(Form("nonew %s",drawoption.Data()));
1641 }
1642 }
1643
1644 DisplayResult(plist);
1645
1646 if (!WriteResult())
1647 return kFALSE;
1648
1649 *fLog << inf << GetDescriptor() << ": Done." << endl;
1650
1651 return kTRUE;
1652}
1653
1654// --------------------------------------------------------------------------
1655//
1656// Read the following containers from GetOutputFile()
1657// - MCalibrationChargeCam
1658// - MCalibrationQECam
1659// - MBadPixelsCam
1660//
1661Bool_t MJCalibration::ReadCalibrationCam()
1662{
1663 const TString fname = GetOutputFile();
1664
1665 if (gSystem->AccessPathName(fname, kFileExists))
1666 {
1667 *fLog << err << "Input file " << fname << " doesn't exist." << endl;
1668 return kFALSE;
1669 }
1670
1671 *fLog << inf << "Reading from file: " << fname << endl;
1672
1673 TFile file(fname, "READ");
1674 if (fCalibrationCam.Read()<=0)
1675 {
1676 *fLog << err << "Unable to read MCalibrationChargeCam from " << fname << endl;
1677 return kFALSE;
1678 }
1679
1680 if (fQECam.Read()<=0)
1681 {
1682 *fLog << err << "Unable to read MCalibrationQECam from " << fname << endl;
1683 return kFALSE;
1684 }
1685
1686
1687 if (file.FindKey("MCalibrationRelTimeCam"))
1688 if (fRelTimeCam.Read()<=0)
1689 {
1690 *fLog << err << "Unable to read MCalibrationRelTimeCam from " << fname << endl;
1691 return kFALSE;
1692 }
1693
1694 if (file.FindKey("MBadPixelsCam"))
1695 {
1696 MBadPixelsCam bad;
1697 if (bad.Read()<=0)
1698 {
1699 *fLog << err << "Unable to read MBadPixelsCam from " << fname << endl;
1700 return kFALSE;
1701 }
1702 fBadPixels.Merge(bad);
1703 }
1704
1705 if (fDisplay /*&& !fDisplay->GetCanvas("Pedestals")*/) // FIXME!
1706 fDisplay->Read();
1707
1708 return kTRUE;
1709}
1710
1711
1712// --------------------------------------------------------------------------
1713//
1714// Set the path for output files, written by WriteResult()
1715//
1716void MJCalibration::SetOutputPath(const char *path)
1717{
1718 fOutputPath = path;
1719 if (fOutputPath.EndsWith("/"))
1720 fOutputPath = fOutputPath(0, fOutputPath.Length()-1);
1721}
1722
1723// --------------------------------------------------------------------------
1724//
1725// Set the useage of the Blind Pixel device
1726//
1727void MJCalibration::SetUseBlindPixel(const Bool_t b)
1728{
1729 b ? SETBIT(fDevices,kUseBlindPixel) : CLRBIT(fDevices,kUseBlindPixel);
1730}
1731
1732// --------------------------------------------------------------------------
1733//
1734// Set the useage of the PIN Diode device
1735//
1736void MJCalibration::SetUsePINDiode(const Bool_t b)
1737{
1738 b ? SETBIT(fDevices,kUsePINDiode) : CLRBIT(fDevices,kUsePINDiode);
1739}
1740
1741// --------------------------------------------------------------------------
1742//
1743// Write the result into the output file GetOutputFile(), if fOutputPath exists.
1744//
1745// The following containers are written:
1746// - MStatusDisplay
1747// - MCalibrationChargeCam
1748// - MCalibrationChargeBlindPix
1749// - MCalibrationQECam
1750// - MBadPixelsCam
1751//
1752Bool_t MJCalibration::WriteResult()
1753{
1754 if (fOutputPath.IsNull())
1755 return kTRUE;
1756
1757 const TString oname(GetOutputFile());
1758
1759 *fLog << inf << "Writing to file: " << oname << endl;
1760
1761 TFile file(oname, "UPDATE");
1762
1763 if (fDisplay && fDisplay->Write()<=0)
1764 {
1765 *fLog << err << "Unable to write MStatusDisplay to " << oname << endl;
1766 return kFALSE;
1767 }
1768
1769 if (fCalibrationCam.Write()<=0)
1770 {
1771 *fLog << err << "Unable to write MCalibrationChargeCam to " << oname << endl;
1772 return kFALSE;
1773 }
1774
1775 if (fCalibrationBlindCam.Write()<=0)
1776 {
1777 *fLog << err << "Unable to write MCalibrationChargeBlindCam to " << oname << endl;
1778 return kFALSE;
1779 }
1780
1781 if (fCalibrationPINDiode.Write()<=0)
1782 {
1783 *fLog << err << "Unable to write MCalibrationChargePINDiode to " << oname << endl;
1784 return kFALSE;
1785 }
1786
1787 if (fQECam.Write()<=0)
1788 {
1789 *fLog << err << "Unable to write MCalibrationQECam to " << oname << endl;
1790 return kFALSE;
1791 }
1792
1793 if (fRelTimes)
1794 if (fRelTimeCam.Write()<=0)
1795 {
1796 *fLog << err << "Unable to write MCalibrationRelTimeCam to " << oname << endl;
1797 return kFALSE;
1798 }
1799
1800 if (fBadPixels.Write()<=0)
1801 {
1802 *fLog << err << "Unable to write MBadPixelsCam to " << oname << endl;
1803 return kFALSE;
1804 }
1805
1806 return kTRUE;
1807
1808}
1809
1810void MJCalibration::DisplayDoubleProject(MHCamera *cam, const char* whatsmall, const char* whatbig) const
1811{
1812
1813 TArrayI inner(1);
1814 inner[0] = 0;
1815
1816 TArrayI outer(1);
1817 outer[0] = 1;
1818
1819 TArrayI s0(6);
1820 s0[0] = 6;
1821 s0[1] = 1;
1822 s0[2] = 2;
1823 s0[3] = 3;
1824 s0[4] = 4;
1825 s0[5] = 5;
1826
1827 TArrayI s1(3);
1828 s1[0] = 6;
1829 s1[1] = 1;
1830 s1[2] = 2;
1831
1832 TArrayI s2(3);
1833 s2[0] = 3;
1834 s2[1] = 4;
1835 s2[2] = 5;
1836
1837 TVirtualPad *pad = gPad;
1838 pad->Divide(2,1);
1839
1840 TH1D *inout[2];
1841 inout[0] = cam->ProjectionS(s0, inner, "Inner");
1842 inout[1] = cam->ProjectionS(s0, outer, "Outer");
1843 FixDataCheckHist(inout[0]);
1844 FixDataCheckHist(inout[1]);
1845
1846 inout[0]->SetTitle(Form("%s %s",cam->GetTitle(),"Inner"));
1847 inout[1]->SetTitle(Form("%s %s",cam->GetTitle(),"Outer"));
1848
1849 for (int i=0; i<2; i++)
1850 {
1851 pad->cd(i+1);
1852 gPad->SetBorderMode(0);
1853 gPad->SetTicks();
1854
1855 inout[i]->SetDirectory(NULL);
1856 inout[i]->SetLineColor(kRed+i);
1857 inout[i]->SetBit(kCanDelete);
1858 inout[i]->Draw();
1859 inout[i]->Fit("gaus", "Q");
1860
1861 TLegend *leg2 = new TLegend(0.6,0.5,0.9,0.7);
1862 //
1863 // Display the outliers as dead and noisy pixels
1864 //
1865 DisplayOutliers(inout[i],whatsmall,whatbig);
1866
1867 //
1868 // Display the two half of the camera separately
1869 //
1870 TH1D *half[2];
1871 half[0] = cam->ProjectionS(s1, i==0 ? inner : outer , "Sector 6-1-2");
1872 half[1] = cam->ProjectionS(s2, i==0 ? inner : outer , "Sector 3-4-5");
1873
1874 for (int j=0; j<2; j++)
1875 {
1876 half[j]->SetLineColor(kRed+i+2*j+1);
1877 half[j]->SetDirectory(NULL);
1878 half[j]->SetBit(kCanDelete);
1879 half[j]->Draw("same");
1880 leg2->AddEntry(half[j], half[j]->GetName(), "l");
1881 }
1882 leg2->Draw();
1883 }
1884}
Note: See TracBrowser for help on using the repository browser.