2 # include "SummaryDrawer.C"
3 # include "AliFMDCorrAcceptance.h"
4 # include "AliFMDCorrSecondaryMap.h"
5 # include "AliFMDCorrELossFit.h"
6 # include "AliFMDCorrNoiseGain.h"
7 # include "AliForwardUtil.h"
8 # include "AliForwardCorrectionManager.h"
16 class AliFMDCorrAcceptance;
17 class AliFMDCorrSecondaryMap;
18 class AliFMDCorrELossFit;
19 class AliFMDCorrNoiseGain;
23 class CorrDrawer : public SummaryDrawer
33 fELossExtra = ""; // forward_eloss.root";
37 * Destructor. Closes the PDF
44 * Create output file name
46 * @param out Output file name on return
47 * @param prefix Prefix of the file name
49 static void MakeFileName(TString& out,
50 const TString& prefix)
52 out = TString::Format("forward_%s.pdf", prefix.Data());
56 * Run the correction drawer, fetching information from extra file
58 * @param what What to draw
59 * @param extra Extra file
60 * @param options Options
61 * @param local Local DB
63 void Run(const Char_t* what,
66 const Char_t* local="")
68 Run(AliForwardCorrectionManager::ParseFields(what),
69 extra, options, local);
72 * Run the correction drawer, fetching information from extra file
74 * @param what What to draw
75 * @param extra Extra file
76 * @param options Options
77 * @param local Local DB
79 void Run(UShort_t what,
82 const Char_t* local="")
91 if (!GetInformation(runNo, sys, sNN, fld, mc, sat)) return;
93 Run(what, runNo, sys, sNN, fld, mc, sat, options, local);
97 * Draw corrections using the correction manager to get them
99 * @param what What to draw
100 * @param runNo Run Number
101 * @param sys Collision system
102 * @param sNN Center of mass energy
103 * @param field L3 Field
104 * @param mc Simulations or not
105 * @param sat Satellite interactions or not
106 * @param options Options
107 * @param local Local database file
109 void Run(const Char_t* what,
116 Option_t* options="",
117 const char* local="")
119 Run(AliForwardCorrectionManager::ParseFields(what),
120 runNo, AliForwardUtil::ParseCollisionSystem(sys),
121 sNN, field, mc, sat, options, local);
124 * Draw corrections using the correction manager to get them
126 * @param what What to draw
127 * @param runNo Run Number
128 * @param sys Collision system
129 * @param sNN Center of mass energy
130 * @param field L3 Field
131 * @param mc Simulations or not
132 * @param sat Satellite interactions or not
133 * @param local Local database file
135 void Run(UShort_t what,
142 Option_t* options="",
143 const char* local="")
145 AliForwardCorrectionManager& mgr = AliForwardCorrectionManager::Instance();
149 if (local) mgr.SetPrefix(gSystem->DirName(local));
151 // Get output file name
153 if (what & AliForwardCorrectionManager::kSecondaryMap)
154 AppendName(name, AliForwardCorrectionManager::kSecondaryMap);
155 if (what & AliForwardCorrectionManager::kAcceptance)
156 AppendName(name, AliForwardCorrectionManager::kAcceptance);
157 if (what & AliForwardCorrectionManager::kELossFits)
158 AppendName(name, AliForwardCorrectionManager::kELossFits);
159 if (what & AliForwardCorrectionManager::kNoiseGain)
160 AppendName(name, AliForwardCorrectionManager::kNoiseGain);
161 if (what & AliForwardCorrectionManager::kVertexBias)
162 Warning("CorrDrawer","Vertex bias not implemented yet");
163 if (what & AliForwardCorrectionManager::kDoubleHit)
164 Warning("CorrDrawer","Double hit not implemented yet");
165 if (what & AliForwardCorrectionManager::kMergingEfficiency)
166 Warning("CorrDrawer","Merging efficiency not implemented yet");
168 // Filter the ones we can handle
169 UShort_t flags = what & (AliForwardCorrectionManager::kELossFits|
170 AliForwardCorrectionManager::kAcceptance|
171 AliForwardCorrectionManager::kSecondaryMap|
172 AliForwardCorrectionManager::kNoiseGain);
173 if (!mgr.Init(runNo, sys, sNN, field, mc, sat, flags, true)) {
174 Error("CorrDrawer", "Failed to initialize for flags=0x%02x"
175 "run=%lu, sys=%hu, sNN=%hu, field=%hd, mc=%d, sat=%d",
176 flags, runNo, sys, sNN, field, mc, sat);
181 MakeFileName(out, name); // , runNo, sys, sNN, field, mc, sat);
183 TString opts(options);
185 Bool_t landscape = opts.Contains("LANDSCAPE");
186 Bool_t few = opts.Contains("FEW");
187 Bool_t details = !opts.Contains("SINGLE");
188 if (opts.Contains("PORTRAIT")) landscape = false;
189 CreateCanvas(out, landscape);
195 DrawParameter(y, "Run #", Form("%lu", runNo));
196 DrawParameter(y, "System", AliForwardUtil::CollisionSystemString(sys));
197 DrawParameter(y, "#sqrt{s_{NN}}",
198 AliForwardUtil::CenterOfMassEnergyString(sNN));
199 DrawParameter(y, "L3 field", AliForwardUtil::MagneticFieldString(field));
200 DrawParameter(y, "Simulation", Form("%s", mc ? "yes" : "no"));
201 DrawParameter(y, "Satellite", Form("%s", sat ? "yes" : "no"));
202 PrintCanvas("Title");
205 if (what & AliForwardCorrectionManager::kSecondaryMap)
206 DrawIt(mgr.GetSecondaryMap(), details);
207 if (what & AliForwardCorrectionManager::kAcceptance)
208 DrawIt(mgr.GetAcceptance(), details);
209 if (what & AliForwardCorrectionManager::kELossFits)
210 DrawIt(mgr.GetELossFit(), details, few);
211 if (what & AliForwardCorrectionManager::kNoiseGain)
212 DrawIt(mgr.GetNoiseGain(), details);
220 * @param o Object to draw
222 virtual void Draw(const TObject* o)
225 Warning("CorrDrawer", "Don't know how to draw a %s object",
229 * Draw a single plot of the mean acceptance correction
231 * @param acc Acceptance correction
233 virtual void Draw(const AliFMDCorrAcceptance* acc) { Summarize(acc, false); }
235 * Draw a single plot of the mean secondary correction
237 * @param sec Secondary correction
239 virtual void Draw(const AliFMDCorrSecondaryMap* sec) { Summarize(sec, false);}
241 * Draw a single plot summarizing the energy loss fits
243 * @param fits Energy loss fits
245 virtual void Draw(const AliFMDCorrELossFit* fits) { Summarize(fits, false); }
247 * A generalized entry to the summarization functions
249 * @param what What to show - only one field
250 * @param runNo Run number
252 * @param sNN Center of mass energy in GeV
253 * @param field L3 magnetic field
254 * @param mc Simulation flag
255 * @param sat Satellite interaction flag
256 * @param options Options
257 * @param local Local storage
259 * @deprecated See Run instead
261 virtual void Summarize(const TString& what,
268 Option_t* options="",
269 const char* local="")
271 Summarize(AliForwardCorrectionManager::ParseFields(what),
272 runNo, AliForwardUtil::ParseCollisionSystem(sys),
273 sNN, field, mc, sat, options, local);
276 * A generalized entry to the summarization functions
278 * @param what What to show - only one field
279 * @param runNo Run number
281 * @param sNN Center of mass energy in GeV
282 * @param field L3 magnetic field
283 * @param mc Simulation flag
284 * @param sat Satellite interaction flag
285 * @param local Local storage
287 * @deprecated See Run instead
289 virtual void Summarize(UShort_t what,
296 Option_t* options="",
297 const char* local="")
299 Run(what, runNo, sys, sNN, field, mc, sat, options, local);
304 * @param o Object to draw
305 * @param pdf Not used
307 virtual void Summarize(const TObject* o, Bool_t pdf=true)
310 Warning("CorrDrawer", "Don't know how to draw a %s object (PDF: %s)",
311 o->ClassName(), pdf ? "yes" : "no");
314 * Draw a single summary plot or multiple plots of the acceptance
315 * correction. A new Canvas is created for this.
317 * @param acc Acceptance correction
318 * @param pdf If true, do multiple plots. Otherwise a single summary plot
320 virtual void Summarize(const AliFMDCorrAcceptance* acc, Bool_t pdf=true)
322 CreateCanvas(CanvasName("acceptance.pdf"), false, pdf);
324 if (pdf) CloseCanvas();
327 * Draw a single summary plot multiple plots of the secondary
328 * correction. A new canvas is created for this.
330 * @param sec Secondary correction
331 * @param pdf If true, do multiple plots. Otherwise a single summary plot
333 virtual void Summarize(const AliFMDCorrSecondaryMap* sec, Bool_t pdf=true)
335 CreateCanvas(CanvasName("secondarymap.pdf"), false, pdf);
337 if (pdf) CloseCanvas();
340 * Draw a single summary plot multiple plots of the energy loss
341 * fits. A new canvas is created for this.
343 * @param fits Energy loss fits
344 * @param pdf If true, do multiple plots. Otherwise a single summary plot
346 virtual void Summarize(const AliFMDCorrNoiseGain* corr, Bool_t pdf=true)
348 CreateCanvas(CanvasName("noisegain.pdf"), true, pdf);
350 if (pdf) CloseCanvas();
353 * Draw a single summary plot multiple plots of the energy loss
354 * fits. A new canvas is created for this.
356 * @param fits Energy loss fits
357 * @param pdf If true, do multiple plots. Otherwise a single summary plot
359 virtual void Summarize(const AliFMDCorrELossFit* fits, Bool_t pdf=true)
361 CreateCanvas(CanvasName("elossfits.pdf"), true, pdf);
363 if (pdf) CloseCanvas();
366 * Draw a single summary plot/multiple plots of the correction.
367 * A new canvas is created for this.
369 * @param what What to plot
370 * @param mc MC input or not
371 * @param output Output of correction pass (must exist)
372 * @param local Local storage of correction
373 * @param options Various options
375 * @deprecated Use Run instead
377 static void Summarize(const TString& what = "",
378 Bool_t /*mc*/ = false,
379 const TString& output = "",
380 const TString& local = "fmd_corrections.root",
381 Option_t* options= "")
383 CorrDrawer* drawer = new CorrDrawer;
384 drawer->Run(AliForwardCorrectionManager::ParseFields(what),
385 output, local, options);
388 * Draw a single summary plot/multiple plots of the correction.
389 * A new canvas is created for this.
391 * @param what What to plot
392 * @param mc MC input or not
393 * @param output Output of correction pass (must exist)
394 * @param local Local storage of correction
395 * @param options Various options
397 * @deprecated Use Run instead
399 static void Summarize(UShort_t what,
400 Bool_t /*mc*/ = false,
401 const TString& output = "",
402 const TString& local = "fmd_corrections.root",
403 Option_t* options= "")
405 CorrDrawer* drawer = new CorrDrawer;
406 drawer->Run(what, output, options, local);
410 * Append a name to output prefix
412 * @param what What to append to
413 * @param which Which string to append
415 void AppendName(TString& what, UShort_t which)
417 if (!what.IsNull()) what.Append("_");
419 case AliForwardCorrectionManager::kSecondaryMap:
420 what.Append("secondary"); break;
421 case AliForwardCorrectionManager::kAcceptance:
422 what.Append("acceptance"); break;
423 case AliForwardCorrectionManager::kELossFits:
424 what.Append("elossfits"); break;
425 case AliForwardCorrectionManager::kNoiseGain:
426 what.Append("noisegain"); break;
428 what.Append("unknown"); break;
433 * Get information from auxillary file
435 * @param runNo On return, the run number
436 * @param sys On return, the collision system
437 * @param sNN On return, the collision energy
438 * @param fld On return, the L3 magnetic field
439 * @param mc On return, true for MC input
440 * @param sat On return, true for satellite input enabled
442 * @return true on success, false otherwise
444 virtual Bool_t GetInformation(ULong_t& runNo,
451 TFile* fout = TFile::Open(fELossExtra, "READ");
453 Warning("SummarizeELoss", "Correction task output \"%s\" not found",
459 TCollection* forward = GetCollection(fout, "ForwardELossSums");
460 if (!forward) throw false;
462 TCollection* eventInsp = GetCollection(forward, "fmdEventInspector");
463 if (!eventInsp) throw false;
465 if (!GetParameter(eventInsp, "sys", sys)) throw false;
466 if (!GetParameter(eventInsp, "sNN", sNN)) throw false;
467 if (!GetParameter(eventInsp, "field", fld)) throw false;
468 if (!GetParameter(eventInsp, "satellite", sat)) throw false;
469 if (!GetParameter(eventInsp, "runNo", runNo)) throw false;
470 if (!GetParameter(eventInsp, "mc", mc)) throw false;
477 if (fout) fout->Close();
481 * Get the canvas name. If the auxillary file has been set, use
482 * that as the base of the canvas name. Otherwise use @a def.
484 * @param def Default value
486 * @return Canvas name
488 virtual TString CanvasName(const char* def)
490 TString canName(def);
491 if (!fELossExtra.IsNull()) {
492 canName = gSystem->BaseName(fELossExtra.Data());
493 canName.ReplaceAll(".root", ".pdf");
500 * @param o Object to summarize
502 virtual void DrawIt(const TObject* o)
505 Warning("CorrDrawer", "Don't know how to summarize a %s object",
509 * Draw the acceptance correction
511 * @param corr Correction
512 * @param details If true, make a multipage PDF, otherwise plot the mean.
514 virtual void DrawIt(const AliFMDCorrAcceptance* corr, Bool_t details=true)
517 Warning("CorrDrawer","No acceptance available");
522 Warning("CorrDrawer", "No canvas");
526 // --- Get vertex axis ---------------------------------------------
527 const TAxis& vtxAxis = corr->GetVertexAxis();
528 Int_t nVtx = vtxAxis.GetNbins();
530 // --- Create stacks for summaries ---------------------------------
531 TObjArray* stacks = CreateVtxStacks(vtxAxis);
532 TObjArray* stacks2 = (corr->HasOverflow() && details
533 ? CreateVtxStacks(vtxAxis) : 0);
535 //__________________________________________________________________
536 // Create a title page
539 TLatex* ll = new TLatex(.5,.8, fCanvas->GetTitle());
540 ll->SetTextAlign(22);
541 ll->SetTextSize(0.03);
545 TLatex* l = new TLatex(.5,.8, "");
547 l->SetTextSize(0.03);
550 l->DrawLatex(0.2, 0.70, "Acceptance due to dead channels");
552 l->DrawLatex(0.5, 0.55, "c_{v,r}(#eta,#phi) = #frac{"
553 "#sum active strips #in (#eta,#phi)}{"
554 "#sum strips #in (#eta,#phi)}");
556 PrintCanvas("Acceptance");
559 // --- Loop over vertex ------------------------------------------
560 for (UShort_t v=1; v <= nVtx; v++) {
561 Double_t vzMin = vtxAxis.GetBinLowEdge(v);
562 Double_t vzMax = vtxAxis.GetBinUpEdge(v);
564 if (details) DivideForRings(true, true);
566 // --- Loop over detectors -------------------------------------
567 for (UShort_t d = 1; d <= 3; d++) {
568 UShort_t nQ = (d == 1 ? 1 : 2);
569 for (UShort_t q = 0; q < nQ; q++) {
570 Char_t r = (q == 0 ? 'I' : 'O');
572 TH2* h2 = corr->GetCorrection(d, r, v);
574 Warning("DrawCorrAcc", "No correction for FMD%d%c, v=%d", d, r, v);
579 if (details) DrawInRingPad(d, r, h2, "colz");
581 Int_t nY = h2->GetNbinsY();
582 TH1* hh = h2->ProjectionX(Form("FMD%d%c", d, r), 1, nY);
585 hh->SetMarkerColor(AliForwardUtil::RingColor(d, r));
586 hh->SetLineColor(AliForwardUtil::RingColor(d, r));
587 hh->SetFillColor(AliForwardUtil::RingColor(d, r));
588 hh->SetFillStyle(3001);
590 THStack* stack = static_cast<THStack*>(stacks->At(v-1));
592 Error("", "No stack at v=%d", v-1);
598 Warning("", "No phi acceptance defined");
601 stack = static_cast<THStack*>(stacks2->At(v-1));
603 Error("", "No stack at v=%d", v-1);
606 TH1* hp = corr->GetPhiAcceptance(d, r, v);
608 Error("", "No phi acceptance at v=%d", v-1);
612 hp->SetMarkerColor(AliForwardUtil::RingColor(d, r));
613 hp->SetLineColor(AliForwardUtil::RingColor(d, r));
614 hp->SetFillColor(AliForwardUtil::RingColor(d, r));
615 hp->SetFillStyle(3001);
616 // Info("", "Adding phi acceptance plot %d", Int_t(hp->GetEntries()));
622 PrintCanvas(Form("%+5.1fcm<IP_{z}<%+5.1fcm", vzMin, vzMax));
624 if (DrawVtxStacks(stacks2, 1.2)) {
625 PrintCanvas("#phi acceptance");
627 if (DrawVtxStacks(stacks, 1.2)) {
628 PrintCanvas("#LTacceptance#GT");
632 * Draw the secondary correction
634 * @param corr Correction
635 * @param details If true, make a multipage PDF, otherwise plot the mean.
637 virtual void DrawIt(const AliFMDCorrSecondaryMap* corr, bool details)
640 Warning("CorrDrawer","No secondary map available");
645 Warning("CorrDrawer", "No canvas");
649 const TAxis& vtxAxis = corr->GetVertexAxis();
650 Int_t nVtx = vtxAxis.GetNbins();
651 TObjArray* stacks = CreateVtxStacks(vtxAxis);
653 //__________________________________________________________________
654 // Create a title page
657 TLatex* ll = new TLatex(.5,.8, fCanvas->GetTitle());
658 ll->SetTextAlign(22);
659 ll->SetTextSize(0.03);
663 TLatex* l = new TLatex(.5,.8, "");
665 l->SetTextSize(0.03);
668 l->DrawLatex(0.2, 0.70, "Secondary map");
670 l->DrawLatex(0.5, 0.60, "c_{v,r}(#eta,#phi)=#frac{"
671 "#sum N_{ch,primary,i}(#eta,#phi)}{"
672 "#sum N_{ch,FMD,i}(#eta,#phi)}");
674 l->DrawLatex(0.2, 0.50, "N: Number of events");
675 l->DrawLatex(0.2, 0.45, "N_{ch,primary,i}(#eta,#phi): Number of charged, "
676 "primary particles in (#eta,#phi) bin");
677 l->DrawLatex(0.2, 0.40, "N_{ch,primary,i}(#eta,#phi): Number of charged, "
678 "particles that hit the FMD in (#eta,#phi) bin");
679 l->DrawLatex(0.2, 0.35, "All quantities determined in MC");
681 PrintCanvas("Secondary maps");
684 // --- Loop over vertex ------------------------------------------
685 for (UShort_t v=1; v <= nVtx; v++) {
686 Double_t vzMin = vtxAxis.GetBinLowEdge(v);
687 Double_t vzMax = vtxAxis.GetBinUpEdge(v);
689 if (details) DivideForRings(true, true);
691 // --- Loop over detectors -------------------------------------
692 for (UShort_t d = 1; d <= 3; d++) {
693 UShort_t nQ = (d == 1 ? 1 : 2);
694 for (UShort_t q = 0; q < nQ; q++) {
695 Char_t r = (q == 0 ? 'I' : 'O');
697 TH2* h2 = corr->GetCorrection(d, r, v);
699 Warning("DrawCorrSec", "No correction for FMD%d%c, v=%d", d, r, v);
703 if (details) DrawInRingPad(d, r, h2, "colz");
705 Int_t nY = h2->GetNbinsY();
706 TH1* hh = h2->ProjectionX(Form("FMD%d%c", d, r), 1, nY);
709 hh->SetMarkerColor(AliForwardUtil::RingColor(d, r));
710 hh->SetLineColor(AliForwardUtil::RingColor(d, r));
711 hh->SetFillColor(AliForwardUtil::RingColor(d, r));
712 hh->SetFillStyle(3001);
714 THStack* stack = static_cast<THStack*>(stacks->At(v-1));
716 Error("", "No stack at v=%d", v-1);
723 PrintCanvas(Form("%+5.1fcm<IP_{z}<%+5.1fcm", vzMin, vzMax));
725 if (DrawVtxStacks(stacks, 3.5)) {
726 PrintCanvas("#LTsecondary map#GT");
729 virtual void DrawIt(const AliFMDCorrNoiseGain* corr, bool /*details*/)
732 Warning("CorrDrawer","No noise-gain correction available");
737 Warning("CorrDrawer", "No canvas");
741 DivideForRings(false,false);
743 for (UShort_t d = 1; d <= 3; d++) {
744 UShort_t nQ = d == 1 ? 1 : 2;
745 for (UShort_t q = 0; q < nQ; q++) {
746 Char_t r = q == 0 ? 'I' : 'O';
747 UShort_t nS = q == 0 ? 20 : 40;
748 UShort_t nT = q == 0 ? 512 : 256;
750 TH2* h = new TH2D(Form("fmd%d%c", d, r),
751 Form("FMD%d%c", d, r),
752 nT, -.5, nT-.5, nS, -.5, nS-.5);
754 h->SetXTitle("Strip");
755 h->SetYTitle("Sector");
757 for (UShort_t s = 0; s < nS; s++) {
758 for (UShort_t t = 0; t < nT; t++) {
759 Float_t c = corr->Get(d,r,s,t);
763 h->GetZaxis()->SetRangeUser(0,0.05);
764 DrawInRingPad(d,r,h,"COLZ");
767 PrintCanvas("Noise correction");
770 * Draw the energy loss fits correction
772 * @param corr Correction
773 * @param details If true, make a multipage PDF,
774 * otherwise plot the parameters.
776 virtual void DrawIt(const AliFMDCorrELossFit* corr, bool details,
780 Warning("CorrDrawer","No energy loss fits available");
785 Warning("CorrDrawer", "No canvas");
789 AliFMDCorrELossFit* fits = const_cast<AliFMDCorrELossFit*>(corr);
795 TDirectory* savDir = gDirectory;
796 if (!gSystem->AccessPathName(fELossExtra.Data())) {
797 hists = TFile::Open(fELossExtra, "READ");
798 Info("", "Opened forward_eloss.root -> %p", hists);
801 Warning("", "Couldn't open %s", fELossExtra.Data());
803 TList* fr = static_cast<TList*>(hists->Get("ForwardELossResults"));
804 // Info("", "Got forward results -> %p", fr);
806 fitter = static_cast<TList*>(fr->FindObject("fmdEnergyFitter"));
807 // Info("", "Got fitter -> %p", fitter);
813 TLatex* ll = new TLatex(.5,.9, "ESD #rightarrow #Delta-fits"
814 /* fCanvas->GetTitle() */);
815 ll->SetTextAlign(22);
816 ll->SetTextSize(0.05);
820 const Double_t fontSize = 0.03;
821 #define DL(X,Y,T) do { l->DrawLatex(X,Y,T); Y -= fontSize; } while (false)
822 TLatex* l = new TLatex(.5,.8, "");
824 l->SetTextSize(fontSize);
830 DL(x,y,"1^{st} page is a summary of fit parameters");
831 DL(x,y,"2^{nd} page is a summary of relative errors");
832 DL(x,y,"Subsequent pages shows the fitted functions");
834 DL(z,y,"Black line is the full fitted function");
835 DL(z,y,"Coloured lines are the individual N-mip comp.");
836 DL(x,y,"Each component has the form");
838 DL(z,y,"f_{n}(x; #Delta, #xi, #sigma') = "
839 "#int_{-#infty}^{+#infty}dx' "
840 "landau(x'; #Delta, #xi)gaus(x'; x, #sigma')");
842 DL(x,y,"The full function is given by");
844 DL(z,y,"f_{N}(x; #Delta, #xi, #sigma', #bf{a}) = "
845 "C #sum_{i=1}^{N} a_{i} "
846 "f_{i}(x; #Delta_{i}, #xi_{i}, #sigma_{i}')");
848 DL(z,y,"#Delta_{i} = i (#Delta_{1} + #xi_{1} log(i)) +#delta_{i}");
849 DL(z,y,"#xi_{i} = i #xi_{1}");
850 DL(z,y,"#sigma_{i} = #sqrt{i} #sigma_{1}");
851 DL(z,y,"#sigma_{n} #dot{=} 0");
852 DL(z,y,"#sigma_{i}'^{2} = #sigma^{2}_{n} + #sigma_{i}^{2}");
853 DL(z,y,"#delta_{i} = c#sigmau/(1+1/i)^{pu#sqrt{u}}");
854 DL(z,y,"u = #sigma/#xi");
855 DL(z,y,"a_{1} #dot{=} 1");
857 DL(z,y,Form("Least quality: %d", fMinQuality));
860 TObject* refit = fitter->FindObject("refitted");
861 if (refit) DL(z,y, "Refitted distributions");//.10
863 PrintCanvas("Energy loss fits");
866 if (details && fitter) {
867 // Draw parameter from the fitter
870 Double_t s = fParName->GetTextSize();
871 Double_t t = fParVal->GetTextSize();
872 fParName->SetTextSize(0.04);
873 fParVal->SetTextSize(0.04);
874 DrawTParameter<double>(y, fitter, "lowCut");
875 DrawTParameter<int> (y, fitter, "nParticles");
876 DrawTParameter<int> (y, fitter, "minEntries");
877 DrawTParameter<int> (y, fitter, "subtractBins");
878 DrawTParameter<bool> (y, fitter, "doFits");
879 DrawTParameter<double>(y, fitter, "maxE");
880 DrawTParameter<int> (y, fitter, "nEbins");
881 DrawTParameter<bool> (y, fitter, "increasingBins");
882 DrawTParameter<double>(y, fitter, "maxRelPerError");
883 DrawTParameter<double>(y, fitter, "maxChi2PerNDF");
884 DrawTParameter<double>(y, fitter, "minWeight");
885 DrawTParameter<double>(y, fitter, "regCut");
886 DrawParameter(y,"Use #delta#Delta(#sigma/#xi)",
888 fits->TestBit(AliFMDCorrELossFit::kHasShift)
890 PrintCanvas("Fitter settings");
891 fParName->SetTextSize(s);
892 fParVal->SetTextSize(t);
896 fits->Draw("error good");
897 PrintCanvas("Fit overview");
898 if (!details) return;
900 //__________________________________________________________________
901 // Draw relative parameter errors
903 fits->Draw("relative good");
904 PrintCanvas("Relative parameter errors");
906 //__________________________________________________________________
907 // Draw all fits individually
908 for (UShort_t d=1; d<=3; d++) {
909 UShort_t nQ = (d == 1 ? 1 : 2);
910 for (UShort_t q = 0; q < nQ; q++) {
911 Char_t r = (q == 0 ? 'I' : 'O');
915 // Info("", "Fitter: %s", fitter->GetName());
917 static_cast<TList*>(fitter->FindObject(Form("FMD%d%c",d,r)));
918 // Info("", "Got detector list -> %p", dl);
920 // Info("", "Detector list: %s", dl->GetName());
921 dists = static_cast<TList*>(dl->FindObject("elossDists"));
922 // Info("", "Got distributions -> %p", dists);
923 resis = static_cast<TList*>(dl->FindObject("elossResiduals"));
924 // Info("", "Got residuals -> %p", resis);
928 printf("FMD%d%c ", d, r);
930 TObjArray* ra = fits->GetRingArray(d, r);
932 DrawELossFits(d, r, ra, dists, resis, few);
937 * CINT does too much when optimizing on a loop, so we take this out
938 * to force CINT to not optimize the third nested loop.
942 * @param ra Ring array
943 * @param dists Distributions (optional)
944 * @param resis Residuals (optional)
946 void DrawELossFits(UShort_t d, Char_t r, TObjArray* ra,
947 TList* dists, TList* resis, bool few)
950 Int_t nCol = (few ? 1 : 2);
951 Int_t nPad = nRow * nCol;
952 AliFMDCorrELossFit::ELossFit* fit = 0;
956 DividedPad divided(fBody, fLandscape, nCol, nRow);
957 while ((fit = static_cast<AliFMDCorrELossFit::ELossFit*>(next()))) {
959 Bool_t last = j == nPad-1;
960 if (j == 0) divided.Divide(true, true);
963 TVirtualPad* drawPad = divided.GetPad(j); // fBody->GetPad(j+1);
966 // Info("", "Now in sub-pad %d of %d: %p", j, nPad, drawPad);
967 // Info("", "Pad %s", drawPad->GetName());
969 // Info("", "Distributions: %s", dists->GetName());
970 TString hName(Form("FMD%d%c_etabin%03d", d,r,fit->GetBin()));
971 TH1* dist = static_cast<TH1*>(dists->FindObject(hName));
973 if (resis) resi = static_cast<TH1*>(resis->FindObject(hName));
974 // Info("", "Got histogram -> %p", dist);
976 Bool_t err = resi->GetUniqueID() <= 1;
979 resi->SetYTitle("#chi^{2}_{bin}=(h-f)^{2}/#delta^{2}h");
980 for (Int_t k=1; k<=resi->GetNbinsX(); k++) {
981 Double_t c = resi->GetBinContent(k);
982 Double_t e = resi->GetBinError(k);
983 if (e <= 0) continue;
986 resi->SetBinContent(k, c);
987 resi->SetBinError(k, 0);
990 drawPad->Divide(1,2,0,0);
991 DrawInPad(drawPad, 2, resi, "HIST", kGridx);
993 Double_t red = fit->GetNu() > 0 ? fit->GetChi2() / fit->GetNu() : 0;
996 TLine* l = new TLine(resi->GetXaxis()->GetXmin(), red,
997 resi->GetXaxis()->GetXmax(), red);
1001 TLatex* cltx = new TLatex(0.5, 0.5,
1002 Form("#chi^{2}/#nu=%6.2f", red));
1004 cltx->SetTextAlign(22);
1005 cltx->SetTextFont(42);
1006 cltx->SetTextSize(0.07);
1008 cltx->DrawLatex(0.5,0.4,Form("%g", dist->GetEntries()));
1012 // Info("", "Histogram: %s", dist->GetName());
1013 dist->SetFillStyle(3001);
1014 dist->SetMarkerStyle(0);
1015 DrawInPad(drawPad, subPad, dist, "HIST E", (subPad * kGridx) + kLogy);
1020 DrawInPad(drawPad, subPad, fit,
1021 Form("comp good values legend peak %s", (same ? "same" : "")),
1023 if (fit->GetQuality() < fMinQuality) {
1024 TLatex* ltx = new TLatex(.2, .2, "NOT USED");
1026 ltx->SetTextFont(62);
1027 ltx->SetTextColor(kRed+1);
1028 ltx->SetTextAngle(30);
1029 ltx->SetTextSize(0.2);
1030 DrawInPad(fBody, j+1, ltx, "", 0);
1035 // DrawInPad(fBody, j+1, fit, "comp good values legend", kLogy);
1039 PrintCanvas(Form("FMD%d%c page %d", d, r, (i/nPad)+1));
1044 PrintCanvas(Form("FMD%d%c page %d", d, r, (i/nPad)+1));
1049 * Create an array of per-vertex bin stacks
1051 * @param vtxAxis Vertex axis
1053 * @return Array of stacks
1055 TObjArray* CreateVtxStacks(const TAxis& vtxAxis)
1057 // --- Create stacks for summaries ---------------------------------
1058 Int_t nVtx = vtxAxis.GetNbins();
1059 TObjArray* stacks = new TObjArray(nVtx);
1060 for (UShort_t v = 1; v <= nVtx; v++) {
1061 THStack* stack = new THStack(Form("vtx%02d", v),
1062 Form("%+5.1f<v_{z}<%+5.1f",
1063 vtxAxis.GetBinLowEdge(v),
1064 vtxAxis.GetBinUpEdge(v)));
1065 stacks->AddAt(stack, v-1);
1070 * Draw the vertex stacks in the canvas
1072 * @param stacks Stacks to draw
1073 * @param max Possible maximum of the stacks
1075 * @return true on success
1077 Bool_t DrawVtxStacks(TObjArray* stacks, Double_t max=-1)
1079 if (!stacks) return false;
1080 // --- Make summary page -------------------------------------------
1081 Int_t nVtx = 10; // stacks->GetEntries();
1083 fBody->Divide(3, (nVtx+2)/3, 0, 0);
1085 for (UShort_t v = 1; v <= nVtx; v++) {
1088 if (ipad == 1 || ipad == 12) ipad++;
1090 THStack* stack = static_cast<THStack*>(stacks->At(v-1));
1092 Error("", "No stack at v=%d", v-1);
1095 TVirtualPad* pad = fBody->cd(ipad);
1097 Error("", "No pad at %d", ipad);
1100 pad->SetFillColor(kWhite);
1102 if (max > 0) stack->SetMaximum(max);
1103 stack->Draw("nostack hist");