Updated zero-misalignment object
[u/mrichter/AliRoot.git] / FMD / AliFMDDisplay.cxx
CommitLineData
bf000c32 1/**************************************************************************
2 * Copyright(c) 2004, ALICE Experiment at CERN, All rights reserved. *
3 * *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
6 * *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
bf000c32 15/* $Id$ */
c2fc1258 16/** @file AliFMDDisplay.cxx
17 @author Christian Holm Christensen <cholm@nbi.dk>
18 @date Mon Mar 27 12:39:09 2006
19 @brief FMD Event display
20*/
bf000c32 21//___________________________________________________________________
22//
23// The classes defined here, are utility classes for reading in data
24// for the FMD. They are put in a seperate library to not polute the
25// normal libraries. The classes are intended to be used as base
26// classes for customized class that do some sort of analysis on the
27// various types of data produced by the FMD.
28//
29// Latest changes by Christian Holm Christensen
30//
9edefa04 31
32#include <TApplication.h>
33#include <TButton.h>
34#include <TCanvas.h>
35#include <TGeoManager.h>
36#include <TH1D.h>
37#include <TMarker3DBox.h>
38#include <TMath.h>
39#include <TSlider.h>
40#include <TStyle.h>
41#include <TView.h>
42#include <TVirtualX.h>
43// #include <TArrayF.h>
44// #include <TParticle.h>
45
bf000c32 46#include "AliFMDDisplay.h" // ALIFMDDISPLAY_H
47#include "AliFMDHit.h" // ALIFMDHIT_H
48#include "AliFMDDigit.h" // ALIFMDDIGIT_H
49#include "AliFMDRecPoint.h" // ALIFMDRECPOINT_H
50#include "AliFMDGeometry.h" // ALIFMDGEOMETRY_H
51#include "AliFMDParameters.h" // ALIFMDPARAMETERS_H
15b17c89 52#include <AliESDFMD.h> // ALIESDFMD_H
f95a63c4 53// #include <AliLog.h>
54#include "AliFMDDebug.h" // Better debug macros
bf000c32 55
56//____________________________________________________________________
57ClassImp(AliFMDDisplay)
58#if 0
59 ; // This is here to keep Emacs for indenting the next line
60#endif
61
62//____________________________________________________________________
63AliFMDDisplay* AliFMDDisplay::fgInstance = 0;
64
65//____________________________________________________________________
66AliFMDDisplay*
67AliFMDDisplay::Instance()
68{
02a27b50 69 // Return static instance
bf000c32 70 return fgInstance;
71}
72
73//____________________________________________________________________
a9579262 74AliFMDDisplay::~AliFMDDisplay()
75{
76 if (fMarkers) {
77 fMarkers->Delete();
78 delete fMarkers;
79 }
80 if (fHits) {
81 fHits->Clear();
82 delete fHits;
83 }
84 if (fPad) delete fPad;
85 fButtons.Delete();
86 if (fSlider) delete fSlider;
87 if (fCanvas) delete fCanvas;
88}
89
90//____________________________________________________________________
91AliFMDDisplay::AliFMDDisplay(Bool_t onlyFMD, const char* gAliceFile)
bf000c32 92 : AliFMDInput(gAliceFile),
93 fWait(kFALSE),
b5ee4425 94 fMarkers(0),
95 fHits(0),
bf000c32 96 fCanvas(0),
97 fPad(0),
a9579262 98 fSlider(0),
b5ee4425 99 fZoomMode(kFALSE),
100 fX0(0),
101 fY0(0),
102 fX1(0),
103 fY1(0),
104 fMultCut(0),
105 fPedestalFactor(0),
106 fXPixel(0),
107 fYPixel(0),
108 fOldXPixel(0),
109 fOldYPixel(0),
a9579262 110 fLineDrawn(0),
111 fOnlyFMD(onlyFMD)
bf000c32 112{
113 // Constructor of an FMD display object.
114 AddLoad(kGeometry);
a9579262 115 if (fgInstance) delete fgInstance;
bf000c32 116 fgInstance = this;
15b17c89 117 SetMultiplicityCut();
118 SetPedestalFactor();
bf000c32 119}
120
121//____________________________________________________________________
1e8f773e 122void
a9579262 123AliFMDDisplay::MakeCanvas(const char** which)
124{
125 gStyle->SetPalette(1);
126 Double_t y1 = .10;
127 Int_t w = 700;
128 fCanvas = new TCanvas("display", "Display", w, Int_t(w / (1-y1)));
129 fCanvas->SetFillColor(1);
130 fCanvas->ToggleEventStatus();
131 fCanvas->cd();
132 fPad = new TPad("view", "3DView", 0.0, y1, 1.0, 1.0, 1, 0, 0);
133 fPad->Draw();
134
135 Double_t yb = 0;
136 fCanvas->cd();
137 if (TESTBIT(fTreeMask, kESD) ||
138 TESTBIT(fTreeMask, kDigits) ||
139 TESTBIT(fTreeMask, kRaw)) {
140 yb = .05;
141 fSlider = new TSlider("multCut", "Multiplicity cut", 0, 0, 1, yb);
142 fSlider->SetMethod("AliFMDDisplay::Instance()->ChangeCut()");
a9579262 143 fSlider->Draw();
97b4001e 144 fSlider->SetMinimum(TESTBIT(fTreeMask, kESD) ? fMultCut * 10 :
145 fPedestalFactor * 10);
a9579262 146 }
147 const char** p = which;
148 const char* m;
149 Int_t n = 0;
150 Int_t j = 0;
151 while (*(p++)) n++;
152 AliInfo(Form("Got %d buttons", n));
153 Float_t x0 = 0;
154 Float_t dx = 1. / n;
155 p = which;
156 while ((m = *(p++))) {
157 fCanvas->cd();
158 AliInfo(Form("Adding button %s", m));
159 TButton* b = new TButton(m, Form("AliFMDDisplay::Instance()->%s()", m),
160 x0, yb, x0 + dx, y1);
161 b->Draw();
162 fButtons.Add(b);
163 x0 += dx;
164 j++;
165 }
166}
167
168//____________________________________________________________________
169void
170AliFMDDisplay::ShowOnlyFMD()
171{
172 if (!fGeoManager) return;
173 static bool once = false;
174 if (once) return;
175 once = true;
176 AliInfo("Will only show the FMD");
177 TGeoVolume* top = gGeoManager->GetTopVolume();
178 top->InvisibleAll(kTRUE);
179 TGeoIterator next(top);
180 TGeoNode* node;
181 TGeoVolume* v = 0;
182 Bool_t hasFMD1 = kFALSE;
183 Bool_t hasFMD2 = kFALSE;
184 Bool_t hasFMD3 = kFALSE;
185 TObjArray toshow;
186 while ((node = static_cast<TGeoNode*>(next()))) {
187 const char* name = node->GetName();
188 if (!name) continue;
189 if (!(v = node->GetVolume())) continue;
190
191 if (name[0] == 'F') {
192 if (name[2] == 'M' && (name[3] == 'T' || name[3] == 'B')) {
193 // Virtual Master half-ring volume - top-level
194 Int_t det = node->GetNumber();
195 switch (det) {
196 case 1: hasFMD1 = true; break;
197 case 2: hasFMD2 = true; break;
198 case 3: hasFMD3 = true; break;
199 default: continue;
200 }
201 toshow.Add(v);
202 }
203 else if (name[3] == 'V' && (name[2] == 'T' || name[2] == 'B'))
204 toshow.Add(v); // Virtual Half-ring, bare detectors
205 // else if (name[3] == 'H' && (name[2] == 'F' || name[2] == 'B'))
206 // toshow.Add(v); // Virtual Hybrid container
207 }
208 v->SetVisibility(kFALSE);
209 v->SetVisDaughters(kFALSE);
210 v->InvisibleAll(kTRUE);
211 }
212 TIter i(&toshow);
213 while ((v = static_cast<TGeoVolume*>(i()))) {
214 v->SetVisibility(kTRUE);
215 v->SetVisDaughters(kTRUE);
216 v->InvisibleAll(kFALSE);
217 }
218}
219
220
221//____________________________________________________________________
222void
bf000c32 223AliFMDDisplay::ExecuteEvent(Int_t event, Int_t px, Int_t py)
224{
1e8f773e 225 // AliInfo(Form("Event %d, at (%d,%d)", px, py));
bf000c32 226 if (px == 0 && py == 0) return;
227 if (!fZoomMode && fPad->GetView()) {
228 fPad->GetView()->ExecuteRotateView(event, px, py);
229 return;
230 }
231 fPad->SetCursor(kCross);
232 switch (event) {
233 case kButton1Down:
234 fPad->TAttLine::Modify();
235 fX0 = fPad->AbsPixeltoX(px);
236 fY0 = fPad->AbsPixeltoY(py);
237 fXPixel = fOldXPixel = px;
238 fYPixel = fOldYPixel = py;
239 fLineDrawn = kFALSE;
240 return;
241 case kButton1Motion:
242 if (fLineDrawn)
243 gVirtualX->DrawBox(fXPixel, fYPixel, fOldXPixel, fOldYPixel,
244 TVirtualX::kHollow);
245 fOldXPixel = px;
246 fOldYPixel = py;
247 fLineDrawn = kTRUE;
248 gVirtualX->DrawBox(fXPixel, fYPixel, fOldXPixel, fOldYPixel,
249 TVirtualX::kHollow);
250 return;
251 case kButton1Up:
252 fPad->GetCanvas()->FeedbackMode(kFALSE);
253 if (px == fXPixel || py == fYPixel) return;
254 fX1 = fPad->AbsPixeltoX(px);
255 fY1 = fPad->AbsPixeltoY(py);
256 if (fX1 < fX0) std::swap(fX0, fX1);
257 if (fY1 < fY0) std::swap(fY0, fY1);
258 fPad->Range(fX0, fY0, fX1, fY1);
259 fPad->Modified();
260 return;
261 }
262}
263
264//____________________________________________________________________
1e8f773e 265Int_t
266AliFMDDisplay::DistancetoPrimitive(Int_t px, Int_t)
bf000c32 267{
1e8f773e 268 // AliInfo(Form("@ (%d,%d)", px, py));
bf000c32 269 fPad->SetCursor(kCross);
270 Float_t xmin = fPad->GetX1();
271 Float_t xmax = fPad->GetX2();
272 Float_t dx = .02 * (xmax - xmin);
273 Float_t x = fPad->AbsPixeltoX(px);
274 if (x < xmin + dx || x > xmax - dx) return 9999;
275 return (fZoomMode ? 0 : 7);
276}
277//____________________________________________________________________
278Bool_t
279AliFMDDisplay::Init()
280{
02a27b50 281 // Initialize. GEt transforms and such,
bf000c32 282 if (!AliFMDInput::Init()) return kFALSE;
283 AliFMDGeometry* geom = AliFMDGeometry::Instance();
284 geom->Init();
285 geom->InitTransformations();
97b4001e 286 if (TESTBIT(fTreeMask, kDigits) || TESTBIT(fTreeMask, kRaw))
287 AliFMDParameters::Instance()->Init();
288
a9579262 289 fMarkers = new TObjArray;
290 fHits = new TObjArray;
291 fMarkers->SetOwner(kTRUE);
292 fHits->SetOwner(kFALSE);
bf000c32 293 return kTRUE;
294}
a9579262 295
296//____________________________________________________________________
297void
298AliFMDDisplay::MakeAux()
299{
300 if ((TESTBIT(fTreeMask, kESD) ||
301 TESTBIT(fTreeMask, kDigits) ||
302 TESTBIT(fTreeMask, kRaw))) {
303 if (!fAux) {
304 fAux = new TCanvas("aux", "Aux");
305 fAux->SetLogy();
306 if (TESTBIT(fTreeMask, kESD))
97b4001e 307 fSpec = new TH1D("spec", "Mult spectra", 500, 0, 10);
a9579262 308 else
309 fSpec = new TH1D("spec", "Adc spectra", 1024, -.5, 1023.5);
310 fSpecCut = static_cast<TH1*>(fSpec->Clone("specCut"));
311 fSpec->SetFillColor(2);
312 fSpec->SetFillStyle(3001);
313 fSpecCut->SetFillColor(4);
314 fSpecCut->SetFillStyle(3001);
315 }
316 else {
317 fSpec->Reset();
318 fSpecCut->Reset();
319 }
320 }
321}
322
323//____________________________________________________________________
324void
325AliFMDDisplay::DrawAux()
326{
327 if (!fAux) return;
328 fAux->cd();
329 fAux->Clear();
330 fSpec->Draw();
331 fSpecCut->Draw("same");
332 fAux->Modified();
333 fAux->Update();
334 fAux->cd();
335}
336
bf000c32 337//____________________________________________________________________
338Bool_t
339AliFMDDisplay::Begin(Int_t event)
340{
02a27b50 341 // Begin of event. Make canvas is not already done
bf000c32 342 if (!fCanvas) {
a9579262 343 const char* m[] = { "Continue", "Zoom", "Pick", "Redisplay", 0 };
344 MakeCanvas(m);
bf000c32 345 }
97b4001e 346 MakeAux();
347
a9579262 348 // AliInfo("Clearing canvas");
bf000c32 349 // fCanvas->Clear();
350 if (!fGeoManager) {
351 Warning("End", "No geometry manager");
352 return kFALSE;
353 }
354 AliInfo("Drawing geometry");
355 fPad->cd();
356 fGeoManager->GetTopVolume()->Draw();
a9579262 357 if (fOnlyFMD) ShowOnlyFMD();
bf000c32 358 AliInfo("Adjusting view");
359 Int_t irep;
360 if (fPad->GetView()) {
361 fPad->GetView()->SetView(-200, -40, 80, irep);
362 fPad->GetView()->Zoom();
363 fPad->Modified();
364 fPad->cd();
365 }
366 return AliFMDInput::Begin(event);
367}
368
369//____________________________________________________________________
a9579262 370void
371AliFMDDisplay::AtEnd()
bf000c32 372{
373 fPad->cd();
374 fMarkers->Draw();
1e8f773e 375 fPad->cd();
bf000c32 376 AppendPad();
bf000c32 377 fPad->cd();
a9579262 378 DrawAux();
379}
380
381//____________________________________________________________________
382void
383AliFMDDisplay::Idle()
384{
bf000c32 385 fWait = kTRUE;
386 while (fWait) {
387 gApplication->StartIdleing();
388 gSystem->InnerLoop();
389 gApplication->StopIdleing();
390 }
391 AliInfo("After idle loop");
a9579262 392 if (fMarkers) fMarkers->Delete();
393 if (fHits) fHits->Clear();
bf000c32 394 AliInfo("After clearing caches");
a9579262 395}
396
397//____________________________________________________________________
398Bool_t
399AliFMDDisplay::End()
400{
401 // End of event. Draw everything
402 AtEnd();
403 Idle();
bf000c32 404 return AliFMDInput::End();
405}
406
407//____________________________________________________________________
408Int_t
409AliFMDDisplay::LookupColor(Float_t x, Float_t max) const
410{
02a27b50 411 // Look-up color
bf000c32 412 Int_t idx = Int_t(x / max * gStyle->GetNumberOfColors());
413 return gStyle->GetColorPalette(idx);
414}
415
15b17c89 416//____________________________________________________________________
417void
a9579262 418AliFMDDisplay::ChangeCut()
419{
97b4001e 420 fMultCut = fSlider->GetMinimum() * 10;
a9579262 421 fPedestalFactor = fSlider->GetMinimum() * 10;
422 AliInfo(Form("Multiplicity cut: %7.5f, Pedestal factor: %7.4f (%6.5f)",
423 fMultCut, fPedestalFactor, fSlider->GetMinimum()));
424 Redisplay();
425}
426
427//____________________________________________________________________
428void
429AliFMDDisplay::Redisplay()
430{
431 if (fMarkers) fMarkers->Delete();
432 if (fHits) fHits->Clear();
433 if (fSpec) fSpec->Reset();
434 if (fSpecCut) fSpecCut->Reset();
435 Event();
436 AtEnd();
437}
438
439//____________________________________________________________________
440void
15b17c89 441AliFMDDisplay::AddMarker(UShort_t det, Char_t rng, UShort_t sec, UShort_t str,
442 TObject* o, Float_t s, Float_t max)
443{
444 // Add a marker to the display
445 //
446 // det Detector
447 // rng Ring
448 // sec Sector
449 // str Strip
450 // o Object to refer to
451 // s Signal
452 // max Maximum of signal
453 //
454 AliFMDGeometry* geom = AliFMDGeometry::Instance();
455 Double_t x, y, z;
456 geom->Detector2XYZ(det, rng, sec, str, x, y, z);
457 Float_t size = .1;
458 Float_t zsize = s / max * 10;
459 Float_t r = TMath::Sqrt(x * x + y * y);
460 Float_t theta = TMath::ATan2(r, z);
461 Float_t phi = TMath::ATan2(y, x);
462 Float_t rz = z + (z < 0 ? 1 : -1) * zsize;
463 TMarker3DBox* marker = new TMarker3DBox(x,y,rz,size,size,zsize,theta,phi);
464 if (o) marker->SetRefObject(o);
465 marker->SetLineColor(LookupColor(s, max));
466 fMarkers->Add(marker);
467}
468
bf000c32 469
470//____________________________________________________________________
471Bool_t
a9579262 472AliFMDDisplay::ProcessHit(AliFMDHit* hit, TParticle* /* p */)
bf000c32 473{
02a27b50 474 // Process a hit
bf000c32 475 if (!hit) { AliError("No hit"); return kFALSE; }
a9579262 476 // if (!p) { AliError("No track"); return kFALSE; }
bf000c32 477
a9579262 478 if (fHits) fHits->Add(hit);
bf000c32 479 Float_t size = .1;
a9579262 480 Float_t zsize = TMath::Sqrt(hit->Edep() * 20);
15b17c89 481 Float_t z = hit->Z() + (hit->Z() < 0 ? 1 : -1) * zsize;
bf000c32 482 Float_t pt = TMath::Sqrt(hit->Py()*hit->Py()+hit->Px()*hit->Px());
483 Float_t theta = TMath::ATan2(pt, hit->Pz());
484 Float_t phi = TMath::ATan2(hit->Py(), hit->Px());
15b17c89 485 TMarker3DBox* marker = new TMarker3DBox(hit->X(), hit->Y(), z,
486 size, size, zsize, theta, phi);
bf000c32 487 marker->SetLineColor(LookupColor(hit->Edep(), 1));
488 marker->SetRefObject(hit);
489 fMarkers->Add(marker);
490 return kTRUE;
491}
492
493//____________________________________________________________________
494Bool_t
495AliFMDDisplay::ProcessDigit(AliFMDDigit* digit)
496{
02a27b50 497 // Process a digit
bf000c32 498 if (!digit) { AliError("No digit"); return kFALSE; }
499
bf000c32 500 AliFMDParameters* parm = AliFMDParameters::Instance();
15b17c89 501 UShort_t det = digit->Detector();
502 Char_t ring = digit->Ring();
503 UShort_t sec = digit->Sector();
504 UShort_t str = digit->Strip();
505 Double_t ped = parm->GetPedestal(det,ring, sec, str);
506 Double_t pedW = parm->GetPedestalWidth(det,ring, sec, str);
97b4001e 507 Double_t threshold = ped + fPedestalFactor * pedW;
508 Float_t counts = digit->Counts();
f95a63c4 509 AliFMDDebug(10, ("FMD%d%c[%2d,%3d] ADC: %d > %d (=%4.2f+%4.2f*%4.2f)",
97b4001e 510 digit->Detector(), digit->Ring(), digit->Sector(),
511 digit->Strip(), Int_t(counts), Int_t(threshold),
512 ped, fPedestalFactor, pedW));
a9579262 513 if (fSpec) fSpec->Fill(counts);
15b17c89 514 if (counts < threshold) return kTRUE;
a9579262 515 if (fHits) fHits->Add(digit);
516 if (fSpecCut) fSpecCut->Fill(counts);
15b17c89 517
518 AddMarker(det, ring, sec, str, digit, counts, 1024);
bf000c32 519 return kTRUE;
520}
521
522//____________________________________________________________________
523Bool_t
d760ea03 524AliFMDDisplay::ProcessRaw(AliFMDDigit* digit)
525{
02a27b50 526 // PRocess raw data
d760ea03 527 return ProcessDigit(digit);
528}
529
530//____________________________________________________________________
531Bool_t
bf000c32 532AliFMDDisplay::ProcessRecPoint(AliFMDRecPoint* recpoint)
533{
02a27b50 534 // Process reconstructed point
bf000c32 535 if (!recpoint) { AliError("No recpoint"); return kFALSE; }
15b17c89 536 if (recpoint->Particles() < fMultCut) return kTRUE;
a9579262 537 if (fHits) fHits->Add(recpoint);
15b17c89 538 AddMarker(recpoint->Detector(), recpoint->Ring(), recpoint->Sector(),
539 recpoint->Strip(), recpoint, recpoint->Particles(), 20);
540 return kTRUE;
541}
bf000c32 542
15b17c89 543//____________________________________________________________________
544Bool_t
a9579262 545AliFMDDisplay::ProcessESD(UShort_t det, Char_t rng, UShort_t sec, UShort_t str,
97b4001e 546 Float_t, Float_t mult)
15b17c89 547{
97b4001e 548 Double_t cmult = mult;
a9579262 549 if (fSpec) fSpec->Fill(cmult);
550 if (cmult < fMultCut || cmult == AliESDFMD::kInvalidMult) return kTRUE;
551 AddMarker(det,rng,sec,str, 0, cmult, 20);
552 if (fSpecCut) fSpecCut->Fill(cmult);
bf000c32 553 return kTRUE;
554}
555
556//____________________________________________________________________
557//
558// EOF
559//