source: trunk/MagicSoft/Mars/mastro/MAstroCamera.cc@ 3833

Last change on this file since 3833 was 3813, checked in by reyes, 21 years ago
*** empty log message ***
File size: 11.5 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, 3/2004 <mailto:tbretz@astro.uni-wuerzburg.de>
19!
20! Copyright: MAGIC Software Development, 2000-2004
21!
22!
23\* ======================================================================== */
24
25/////////////////////////////////////////////////////////////////////////////
26//
27// MAstroCamera
28// ============
29//
30// A tools displaying stars from a catalog in the camera display.
31// PRELIMINARY!!
32//
33//
34// Usage:
35// ------
36// For a usage example see macros/starfield.C
37//
38// To be able to reflect the star-light you need the geometry of the
39// mirror and the distance of the plain screen.
40//
41// You can get the mirror geometry from a MC file and the distance of
42// the screen from MGeomCam.
43//
44//
45// Algorithm:
46// ----------
47// The caluclation of the position of the reflection in the camera is
48// done by:
49// - Rotation of the star-field such that the camera is looking into
50// the pointing direction
51// - Calculation of the reflected star-light vector by calling
52// MGeomMirror::GetReflection (which returns the point at which
53// the vector hits the camera plain)
54// - Depending on the draw-option you get each reflected point, the
55// reflection on a virtual ideal mirror or the reflection on each
56// individual mirror
57//
58//
59// GUI:
60// ----
61// * You can use the the cursor keys to change the pointing position
62// and plus/minus to change the time by a quarter of an hour.
63//
64// ToDo:
65// -----
66// * possibility to overwrite distance from mirror to screen
67// * read the mirror geometry directly from the MC input file
68//
69/////////////////////////////////////////////////////////////////////////////
70#include "MAstroCamera.h"
71
72#include <KeySymbols.h> // kKey_*
73
74#include <TH2.h> // TH2D
75#include <TMarker.h> // TMarker
76#include <TVirtualPad.h> // gPad
77
78#include "MLog.h"
79#include "MLogManip.h"
80
81#include "MGeomCam.h"
82#include "MGeomMirror.h"
83
84#include "MTime.h"
85#include "MAstroSky2Local.h"
86#include "MObservatory.h"
87
88#include "../mhist/MHCamera.h" // FIXME: This dependancy is very bad!
89 // HOW TO GET RID OF IT? Move MHCamera to mgeom?
90
91//#include "MStarLocalPos.h"
92
93ClassImp(MAstroCamera);
94
95using namespace std;
96
97// --------------------------------------------------------------------------
98//
99// Create a virtual MGeomMirror which is in the center of the coordinate
100// system and has a normal vector in z-direction.
101//
102MAstroCamera::MAstroCamera() : fGeom(0), fMirrors(0)
103{
104 fMirror0 = new MGeomMirror;
105 fMirror0->SetMirrorContent(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1);
106}
107
108// --------------------------------------------------------------------------
109//
110// Delete fGeom, fMirrors and the virtual 0-Mirror fMirror0
111//
112MAstroCamera::~MAstroCamera()
113{
114 if (fGeom)
115 delete fGeom;
116 if (fMirrors)
117 delete fMirrors;
118
119 delete fMirror0;
120
121}
122
123// --------------------------------------------------------------------------
124//
125// Set a list of mirrors. The Mirrors must be of type MGeomMirror and
126// stored in a TClonesArray
127//
128void MAstroCamera::SetMirrors(TClonesArray &arr)
129{
130 if (arr.GetClass()!=MGeomMirror::Class())
131 {
132 cout << "ERROR - TClonesArray doesn't contain objects of type MGeomMirror... ignored." << endl;
133 return;
134 }
135
136 const Int_t n = arr.GetSize();
137
138 if (!fMirrors)
139 fMirrors = new TClonesArray(MGeomMirror::Class(), n);
140
141 fMirrors->ExpandCreate(n);
142
143 for (int i=0; i<n; i++)
144 memcpy((*fMirrors)[i], arr[i], sizeof(MGeomMirror));
145
146}
147
148// --------------------------------------------------------------------------
149//
150// Set the camera geometry. The MGeomCam object is cloned.
151//
152void MAstroCamera::SetGeom(const MGeomCam &cam)
153{
154 if (fGeom)
155 delete fGeom;
156
157 fGeom = (MGeomCam*)cam.Clone();
158}
159
160// --------------------------------------------------------------------------
161//
162// Convert To Pad coordinates (see MAstroCatalog)
163//
164Int_t MAstroCamera::ConvertToPad(const TVector3 &w, TVector2 &v) const
165{
166 /*
167 --- Use this to plot the 'mean grid' instead of the grid of a
168 theoretical central mirror ---
169
170 TVector3 spot;
171 const Int_t num = fConfig->GetNumMirror();
172 for (int i=0; i<num; i++)
173 spot += fConfig->GetMirror(i).GetReflection(w, fGeom->GetCameraDist())*1000;
174 spot *= 1./num;
175 */
176
177 const TVector3 spot = fMirror0->GetReflection(w, fGeom->GetCameraDist())*1000;
178 v.Set(spot(0), spot(1));
179
180 const Float_t max = fGeom->GetMaxRadius()*0.70;
181 return v.X()>-max && v.Y()>-max && v.X()<max && v.Y()<max;
182}
183
184// --------------------------------------------------------------------------
185//
186// Find an object with a given name in the list of primitives of this pad.
187//
188TObject *FindObjectInPad(const char *name, TVirtualPad *pad)
189{
190 if (!pad)
191 pad = gPad;
192
193 if (!pad)
194 return NULL;
195
196 TObject *o;
197
198 TIter Next(pad->GetListOfPrimitives());
199 while ((o=Next()))
200 {
201 if (o->InheritsFrom(gROOT->GetClass(name)))
202 return o;
203
204 if (o->InheritsFrom("TPad"))
205 if ((o = FindObjectInPad(name, (TVirtualPad*)o)))
206 return o;
207 }
208 return NULL;
209}
210
211// --------------------------------------------------------------------------
212//
213// Options:
214//
215// '*' Draw the mean of the reflections on all mirrors
216// '.' Draw a dot for the reflection on each individual mirror
217// 'h' To create a TH2D of the star-light which is displayed
218// 'c' Use the underlaying MHCamera as histogram
219// '0' Draw the reflection on a virtual perfect mirror
220//
221// If the Pad contains an object MHCamera of type MHCamera it is used.
222// Otherwise a new object is created.
223//
224void MAstroCamera::AddPrimitives(TString o)
225{
226 if (!fTime || !fObservatory || !fMirrors)
227 {
228 cout << "Missing data..." << endl;
229 return;
230 }
231
232 if (o.IsNull())
233 o = "*.";
234
235 const Bool_t hasnull = o.Contains("0", TString::kIgnoreCase);
236 const Bool_t hashist = o.Contains("h", TString::kIgnoreCase);
237 const Bool_t hasmean = o.Contains("*", TString::kIgnoreCase);
238 const Bool_t hasdot = o.Contains(".", TString::kIgnoreCase);
239 const Bool_t usecam = o.Contains("c", TString::kIgnoreCase);
240
241 // Get camera
242 MHCamera *camera=(MHCamera*)FindObjectInPad("MHCamera", gPad);
243 if (camera)
244 {
245 if (!camera->GetGeometry() || camera->GetGeometry()->IsA()!=fGeom->IsA())
246 camera->SetGeometry(*fGeom);
247 }
248 else
249 {
250 camera = new MHCamera(*fGeom);
251 camera->SetName("MHCamera");
252 camera->SetStats(0);
253 camera->SetInvDeepBlueSeaPalette();
254 camera->SetBit(kCanDelete);
255 camera->Draw();
256 }
257
258 camera->SetTitle(GetPadTitle());
259
260 gPad->cd(1);
261
262 if (!usecam)
263 {
264 if (camera->GetEntries()==0)
265 camera->SetBit(MHCamera::kNoLegend);
266 }
267 else
268 {
269 camera->Reset();
270 camera->SetYTitle("arb.cur");
271 }
272
273 TH2 *h=0;
274 if (hashist)
275 {
276 TH2F hist("","", 90, -650, 650, 90, -650, 650);
277 hist.SetMinimum(0);
278 h = (TH2*)hist.DrawCopy("samecont1");
279 }
280
281 const TRotation rot(GetGrid(kTRUE));
282
283 MVector3 *radec;
284 TIter Next(&fList);
285
286 while ((radec=(MVector3*)Next()))
287 {
288 const Double_t mag = radec->Magnitude();
289
290 TVector3 star(*radec);
291
292 // Rotate Star into telescope system
293 star *= rot;
294
295 TVector3 mean;
296
297 Int_t num = 0;
298
299 MGeomMirror *mirror = 0;
300 TIter NextM(fMirrors);
301 while ((mirror=(MGeomMirror*)NextM()))
302 {
303 const TVector3 spot = mirror->GetReflection(star, fGeom->GetCameraDist())*1000;
304
305 // calculate mean of all 'stars' hitting the camera plane
306 // by taking the sum of the intersection points between
307 // the light vector and the camera plane
308 mean += spot;
309
310 if (hasdot)
311 {
312 TMarker *m=new TMarker(spot(0), spot(1), 1);
313 m->SetMarkerColor(kMagenta);
314 m->SetMarkerStyle(kDot);
315 AddMap(m);
316 }
317 if (h)
318 h->Fill(spot(0), spot(1), pow(10, -mag/2.5));
319
320 if (usecam)
321 camera->Fill(spot(0), spot(1), pow(10, -mag/2.5));
322
323 num++;
324 }
325
326 // transform meters into millimeters (camera display works with mm)
327 mean *= 1./num;
328 DrawStar(mean(0), mean(1), *radec, !hasmean, Form("x=%.1fmm y=%.1fmm", mean(0), mean(1)));
329
330 if (hasnull)
331 {
332 TVector3 star(*radec);
333 star *= rot;
334 const TVector3 spot = fMirror0->GetReflection(star, fGeom->GetCameraDist())*1000;
335 DrawStar(spot(0), spot(1), *radec, !hasmean, Form("x=%.1fmm y=%.1fmm", mean(0), mean(1)));
336 }
337 }
338}
339
340// --------------------------------------------------------------------------
341//
342// Options:
343//
344// '*' Draw the mean of the reflections on all mirrors
345// '.' Draw a dot for the reflection on each individual mirror
346// 'h' To create a TH2D of the star-light which is displayed
347// 'c' Use the underlaying MHCamera as histogram
348// '0' Draw the reflection on a virtual perfect mirror
349//
350// If the Pad contains an object MHCamera of type MHCamera it is used.
351// Otherwise a new object is created.
352//
353/*void MAstroCamera::FillStarList()
354{
355 fStars->SetOwner();
356 fStars->Delete();
357
358 if (!fTime || !fObservatory || !fMirrors || !fStars)
359 {
360 cout << "Missing data..." << endl;
361 return;
362 }
363
364 // Get camera
365 MHCamera *camera=(MHCamera*)FindObjectInPad("MHCamera", gPad);
366 if (camera)
367 {
368 if (!camera->GetGeometry() || camera->GetGeometry()->IsA()!=fGeom->IsA())
369 camera->SetGeometry(*fGeom);
370 }
371 else
372 {
373 camera = new MHCamera(*fGeom);
374 camera->SetName("MHCamera");
375 camera->SetStats(0);
376 camera->SetInvDeepBlueSeaPalette();
377 camera->SetBit(kCanDelete);
378 camera->Draw();
379 }
380
381 const TRotation rot(GetGrid(kTRUE));
382
383 MVector3 *radec;
384 TIter Next(&fList);
385
386 while ((radec=(MVector3*)Next()))
387 {
388 const Double_t mag = radec->Magnitude();
389
390 TVector3 mean;
391 TVector3 star(*radec);
392 star *= rot;
393 const TVector3 spot = fMirror0->GetReflection(star, fGeom->GetCameraDist())*1000;
394
395 MStarLocalPos *starpos = new MStarLocalPos;
396 starpos->SetExpValues(mag,mean(0),mean(1));
397 fStars->Add(starpos);
398 }
399}
400*/
401
402// ------------------------------------------------------------------------
403//
404// Execute a gui event on the camera
405//
406void MAstroCamera::ExecuteEvent(Int_t event, Int_t mp1, Int_t mp2)
407{
408 if (event==kKeyPress && fTime)
409 switch (mp2)
410 {
411 case kKey_Plus:
412 fTime->SetMjd(fTime->GetMjd()+0.25/24);
413 Update(kTRUE);
414 return;
415
416 case kKey_Minus:
417 fTime->SetMjd(fTime->GetMjd()-0.25/24);
418 Update(kTRUE);
419 return;
420 }
421
422 MAstroCatalog::ExecuteEvent(event, mp1, mp2);
423}
Note: See TracBrowser for help on using the repository browser.