]> git.uio.no Git - u/mrichter/AliRoot.git/blame - RALICE/AliAstrolab.cxx
Bug fix: corrected file name (Levente)
[u/mrichter/AliRoot.git] / RALICE / AliAstrolab.cxx
CommitLineData
8bde545d 1/**************************************************************************
2 * Copyright(c) 1998-1999, 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 **************************************************************************/
15
16// $Id$
17
18///////////////////////////////////////////////////////////////////////////
19// Class AliAstrolab
20// Virtual lab to correlate measurements with astrophysical phenomena.
21//
caa58e1a 22// This class is derived from TTask, but the only reason for this
23// is to enable this class to serve as a base class for other TTask
24// derived classes (e.g. AliEventSelector) without the need for
25// multiple virtual inheritance.
26// So, this AliAstrolab class itself does not provide any TTask
27// related functionality.
28//
8bde545d 29// The lab can be given a terrestrial location via the usual longitude
30// and latitude specifications.
31// Since this class is derived from AliTimestamp, a lab can also be
32// given a specific timestamp. Together with the terrestrial location
33// this provides access to local (sidereal) times etc...
34// In addition to the usual astronomical reference frames, a local
35// lab reference frame can also be specified. Together with the lab's
36// timestamp this uniquely defines all the coordinate transformations
37// between the various reference frames.
38// These lab characteristics allow a space-time correlation of lab
39// observations with external (astrophysical) phenomena.
40//
41// Observations are entered as generic signals containing a position,
42// reference frame specification and a timestamp.
43// These observations can then be analysed in various reference frames
44// via the available GET functions.
45//
46// Various external (astrophysical) phenomena may be entered as
47// so-called reference signals.
48// This class provides facilities (e.g. MatchRefSignal) to check
49// correlations of the stored measurement with these reference signals.
b867da20 50// Also graphical facilities (e.g. DisplaySignals) are available to
51// provide skymaps in various projections.
8bde545d 52//
53// Coding example :
54// ----------------
55// gSystem->Load("ralice");
56//
57// AliAstrolab lab("IceCube","The South Pole Neutrino Observatory");
58// lab.SetLabPosition(0,-90,"deg"); // South Pole
59//
60// lab.SetLocalFrame(90,180,90,270,0,0); // Local frame has X-axis to the North
61//
62// lab.Data(1,"dms"); // Print laboratory parameters
63//
64// // Enter some observed event to be investigated
65// AliTimestamp ts;
66// ts.SetUT(1989,7,30,8,14,23,738504,0);
67// Float_t vec[3]={1,23.8,118.65};
68// Ali3Vector r;
69// r.SetVector(vec,"sph","deg");
70// lab.SetSignal(&r,"loc","M",&ts,0,"Event10372");
71//
72// // Enter some reference signals
73// Float_t alpha=194818.0;
74// Float_t delta=84400.;
75// lab.SetSignal(alpha,delta,"B",1950,"M",-1,"Altair");
76// alpha=124900.0;
77// delta=272400.;
78// lab.SetSignal(alpha,delta,"B",1950,"M",-1,"NGP");
79// alpha=64508.917;
80// delta=-164258.02;
81// lab.SetSignal(alpha,delta,"J",2000,"M",-1,"Sirius");
82// alpha=23149.08;
83// delta=891550.8;
84// lab.SetSignal(alpha,delta,"J",2000,"M",-1,"Polaris");
85// alpha=43600.;
86// delta=163100.;
87// lab.SetSignal(alpha,delta,"J",2000,"M",-1,"Aldebaran");
88// Float_t l=327.531;
89// Float_t b=-35.8903;
90// Float_t pos[3]={1,90.-b,l};
91// r.SetVector(pos,"sph","deg");
92// lab.SetUT(1989,7,30,8,14,16,0,0);
caa58e1a 93// lab.SetSignal(&r,"gal","M",0,-1,"GRB890730");
8bde545d 94//
95// // List all stored objects
96// lab.ListSignals("equ","M",5);
97//
98// // Determine minimal space and time differences with reference signals
99// Double_t da,dt;
100// Int_t ia,it;
101// da=lab.GetDifference(0,"deg",dt,"s",1,&ia,&it);
102// cout << " Minimal differences damin (deg) : " << da << " dtmin (s) : " << dt
103// << " damin-index : " << ia << " dtmin-index : " << it << endl;
104// cout << " damin for "; lab->PrintSignal("equ","T",&ts,5,ia); cout << endl;
105// cout << " dtmin for "; lab->PrintSignal("equ","T",&ts,5,it); cout << endl;
106//
107// // Search for space and time match with the reference signals
108// da=5;
109// dt=10;
110// TArrayI* arr=lab.MatchRefSignal(da,"deg",dt,"s");
111// Int_t index=0;
112// if (arr)
113// {
114// for (Int_t i=0; i<arr->GetSize(); i++)
115// {
116// index=arr->At(i);
117// cout << " Match found for index : " << index << endl;
118// cout << " Corresponding ref. object "; lab->PrintSignal("equ","T",&ts,5,index); cout << endl;
119// }
120// }
121//
b867da20 122// // Display all stored objects in a skymap (Hammer projection)
123// lab.DisplaySignals("equ","M",&ts,"ham",1);
8bde545d 124//
125//--- Author: Nick van Eijndhoven 15-mar-2007 Utrecht University
126//- Modified: NvE $Date$ Utrecht University
127///////////////////////////////////////////////////////////////////////////
128
129#include "AliAstrolab.h"
130#include "Riostream.h"
131
132ClassImp(AliAstrolab) // Class implementation to enable ROOT I/O
133
caa58e1a 134AliAstrolab::AliAstrolab(const char* name,const char* title) : TTask(name,title),AliTimestamp()
8bde545d 135{
136// Default constructor
137
138 fToffset=0;
139 fXsig=0;
140 fRefs=0;
141 fBias=0;
142 fGal=0;
143 fIndices=0;
b867da20 144 fMeridian=-999;
145 fProj="none";
146 fCanvas=0;
147 fHist=0;
148 fMarkers=0;
8bde545d 149}
150///////////////////////////////////////////////////////////////////////////
151AliAstrolab::~AliAstrolab()
152{
153// Destructor to delete all allocated memory.
154
155 if (fXsig)
156 {
157 delete fXsig;
158 fXsig=0;
159 }
160 if (fRefs)
161 {
162 delete fRefs;
163 fRefs=0;
164 }
165 if (fIndices)
166 {
167 delete fIndices;
168 fIndices=0;
169 }
b867da20 170 if (fHist)
171 {
172 delete fHist;
173 fHist=0;
174 }
175 if (fMarkers)
176 {
177 delete fMarkers;
178 fMarkers=0;
179 }
180 if (fCanvas)
181 {
182 delete fCanvas;
183 fCanvas=0;
184 }
8bde545d 185}
186///////////////////////////////////////////////////////////////////////////
caa58e1a 187AliAstrolab::AliAstrolab(const AliAstrolab& t) : TTask(t),AliTimestamp(t)
8bde545d 188{
189// Copy constructor
190
191 fToffset=t.fToffset;
192 fLabPos=t.fLabPos;
193 fXsig=0;
194 if (t.fXsig) fXsig=new AliSignal(*(t.fXsig));
195 fRefs=0;
196 if (t.fRefs)
197 {
198 Int_t size=t.fRefs->GetSize();
199 fRefs=new TObjArray(size);
200 for (Int_t i=0; i<size; i++)
201 {
202 AliSignal* sx=(AliSignal*)t.fRefs->At(i);
203 if (sx) fRefs->AddAt(sx->Clone(),i);
204 }
205 }
206 fBias=0;
207 fGal=0;
208 fIndices=0;
b867da20 209 fMeridian=-999;
210 fProj="none";
211 fCanvas=0;
212 fHist=0;
213 fMarkers=0;
8bde545d 214}
215///////////////////////////////////////////////////////////////////////////
216void AliAstrolab::Data(Int_t mode,TString u)
217{
218// Provide lab information.
219//
220// "mode" indicates the mode of the timestamp info (see AliTimestamp::Date).
221//
222// The string argument "u" allows to choose between different angular units
223// in case e.g. a spherical frame is selected.
224// u = "rad" : angles provided in radians
225// "deg" : angles provided in degrees
226// "dms" : angles provided in ddd:mm:ss.sss
227// "hms" : angles provided in hh:mm:ss.sss
228//
229// The defaults are mode=1 and u="deg".
230
231 const char* name=GetName();
232 const char* title=GetTitle();
233 cout << " *" << ClassName() << "::Data*";
234 if (strlen(name)) cout << " Name : " << GetName();
235 if (strlen(title)) cout << " Title : " << GetTitle();
236 cout << endl;
237
238 Double_t l,b;
239 GetLabPosition(l,b,"deg");
240 cout << " Lab position longitude : "; PrintAngle(l,"deg",u,2);
241 cout << " latitude : "; PrintAngle(b,"deg",u,2);
242 cout << endl;
243 cout << " Lab time offset w.r.t. UT : "; PrintTime(fToffset,12); cout << endl;
244
245 // UT and Local time info
246 Date(mode,fToffset);
247}
248///////////////////////////////////////////////////////////////////////////
249void AliAstrolab::SetLabPosition(Ali3Vector& p)
250{
251// Set the lab position in the terrestrial coordinates.
252// The right handed reference frame is defined such that the North Pole
253// corresponds to a polar angle theta=0 and the Greenwich meridian corresponds
254// to an azimuth angle phi=0, with phi increasing eastwards.
255
256 fLabPos.SetPosition(p);
257
258 // Determine local time offset in fractional hours w.r.t. UT.
259 Double_t vec[3];
260 p.GetVector(vec,"sph","deg");
261 Double_t l=vec[2];
262 fToffset=l/15.;
263}
264///////////////////////////////////////////////////////////////////////////
265void AliAstrolab::SetLabPosition(Double_t l,Double_t b,TString u)
266{
267// Set the lab position in the terrestrial longitude (l) and latitude (b).
268// Positions north of the equator have b>0, whereas b<0 indicates
269// locations south of the equator.
270// Positions east of Greenwich have l>0, whereas l<0 indicates
271// locations west of Greenwich.
272//
273// The string argument "u" allows to choose between different angular units
274// u = "rad" : angles provided in radians
275// "deg" : angles provided in degrees
276// "dms" : angles provided in dddmmss.sss
277// "hms" : angles provided in hhmmss.sss
278//
279// The default is u="deg".
280
281 Double_t r=1,theta=0,phi=0;
282
283 l=ConvertAngle(l,u,"deg");
284 b=ConvertAngle(b,u,"deg");
285
286 Double_t offset=90.;
287
288 theta=offset-b;
289 phi=l;
290
291 Double_t p[3]={r,theta,phi};
292 fLabPos.SetPosition(p,"sph","deg");
293
294 // Local time offset in fractional hours w.r.t. UT.
295 fToffset=l/15.;
296}
297///////////////////////////////////////////////////////////////////////////
298AliPosition AliAstrolab::GetLabPosition() const
299{
300// Provide the lab position in the terrestrial coordinates.
301// The right handed reference frame is defined such that the North Pole
302// corresponds to a polar angle theta=0 and the Greenwich meridian corresponds
303// to an azimuth angle phi=0, with phi increasing eastwards.
304
305 return fLabPos;
306}
307///////////////////////////////////////////////////////////////////////////
308void AliAstrolab::GetLabPosition(Double_t& l,Double_t& b,TString u) const
309{
310// Provide the lab position in the terrestrial longitude (l) and latitude (b).
311// Positions north of the equator have b>0, whereas b<0 indicates
312// locations south of the equator.
313// Positions east of Greenwich have l>0, whereas l<0 indicates
314// locations west of Greenwich.
315//
316// The string argument "u" allows to choose between different angular units
317// u = "rad" : angles provided in radians
318// "deg" : angles provided in degrees
319//
320// The default is u="deg".
321
322 Double_t pi=acos(-1.);
323
324 Double_t offset=90.;
325 if (u=="rad") offset=pi/2.;
326
327 Double_t p[3];
328 fLabPos.GetPosition(p,"sph",u);
329 b=offset-p[1];
330 l=p[2];
331}
332///////////////////////////////////////////////////////////////////////////
333Double_t AliAstrolab::GetLT()
334{
335// Provide the Lab's local time in fractional hours.
336// A mean solar day lasts 24h (i.e. 86400s).
337//
338// In case a hh:mm:ss format is needed, please use the Convert() facility.
339
340 Double_t h=GetLT(fToffset);
341 return h;
342}
343///////////////////////////////////////////////////////////////////////////
344Double_t AliAstrolab::GetLMST()
345{
346// Provide the Lab's Local Mean Sidereal Time (LMST) in fractional hours.
347// A sidereal day corresponds to 23h 56m 04.09s (i.e. 86164.09s) mean solar time.
348// The definition of GMST is such that a sidereal clock corresponds with
349// 24 sidereal hours per revolution of the Earth.
350// As such, local time offsets w.r.t. UT and GMST can be treated similarly.
351//
352// In case a hh:mm:ss format is needed, please use the Convert() facility.
353
354 Double_t h=GetLMST(fToffset);
355 return h;
356}
357///////////////////////////////////////////////////////////////////////////
358Double_t AliAstrolab::GetLAST()
359{
360// Provide the Lab's Local Apparent Sidereal Time (LAST) in fractional hours.
361// A sidereal day corresponds to 23h 56m 04.09s (i.e. 86164.09s) mean solar time.
362// The definition of GMST and GAST is such that a sidereal clock corresponds with
363// 24 sidereal hours per revolution of the Earth.
364// As such, local time offsets w.r.t. UT, GMST and GAST can be treated similarly.
365//
366// In case a hh:mm:ss format is needed, please use the Convert() facility.
367
368 Double_t h=GetLAST(fToffset);
369 return h;
370}
371///////////////////////////////////////////////////////////////////////////
372void AliAstrolab::PrintAngle(Double_t a,TString in,TString out,Int_t ndig) const
373{
374// Printing of angles in various formats.
375//
376// The input argument "a" denotes the angle to be printed.
377// The string arguments "in" and "out" specify the angular I/O formats.
378//
379// in = "rad" : input angle provided in radians
380// "deg" : input angle provided in degrees
381// "dms" : input angle provided in dddmmss.sss
382// "hms" : input angle provided in hhmmss.sss
383//
384// out = "rad" : output angle provided in radians
385// "deg" : output angle provided in degrees
386// "dms" : output angle provided in dddmmss.sss
387// "hms" : output angle provided in hhmmss.sss
388//
389// The argument "ndig" specifies the number of digits for the fractional
390// part (e.g. ndig=6 for "dms" corresponds to micro-arcsecond precision).
391// No rounding will be performed, so an arcsecond count of 3.473 with ndig=1
392// will appear as 03.4 on the output.
393// Due to computer accuracy, precision on the pico-arcsecond level may get lost.
394//
395// The default is ndig=1.
396//
397// Note : The angle info is printed without additional spaces or "endline".
398// This allows the print to be included in various composite output formats.
399
400 Double_t b=ConvertAngle(a,in,out);
401
402 if (out=="deg" || out=="rad")
403 {
404 cout.setf(ios::fixed,ios::floatfield);
405 cout << setprecision(ndig) << b << " " << out.Data();
406 cout.unsetf(ios::fixed);
407 return;
408 }
409
410 Double_t epsilon=1.e-12; // Accuracy in (arc)seconds
411 Int_t word=0,ddd=0,hh=0,mm=0,ss=0;
412 Double_t s;
413 ULong64_t sfrac=0;
414
415 if (out=="dms")
416 {
417 word=Int_t(b);
418 word=abs(word);
419 ddd=word/10000;
420 word=word%10000;
421 mm=word/100;
422 ss=word%100;
423 s=fabs(b)-Double_t(ddd*10000+mm*100+ss);
424 if (s>(1.-epsilon))
425 {
426 s=0.;
427 ss++;
428 }
429 while (ss>=60)
430 {
431 ss-=60;
432 mm++;
433 }
434 while (mm>=60)
435 {
436 mm-=60;
437 ddd++;
438 }
439 while (ddd>=360)
440 {
441 ddd-=360;
442 }
443 s*=pow(10.,ndig);
444 sfrac=ULong64_t(s);
445 if (b<0) cout << "-";
446 cout << ddd << "d " << mm << "' " << ss << "."
447 << setfill('0') << setw(ndig) << sfrac << "\"";
448 return;
449 }
450
451 if (out=="hms")
452 {
453 word=Int_t(b);
454 word=abs(word);
455 hh=word/10000;
456 word=word%10000;
457 mm=word/100;
458 ss=word%100;
459 s=fabs(b)-Double_t(hh*10000+mm*100+ss);
460 if (s>(1.-epsilon))
461 {
462 s=0.;
463 ss++;
464 }
465 while (ss>=60)
466 {
467 ss-=60;
468 mm++;
469 }
470 while (mm>=60)
471 {
472 mm-=60;
473 hh++;
474 }
475 while (hh>=24)
476 {
477 hh-=24;
478 }
479 s*=pow(10.,ndig);
480 sfrac=ULong64_t(s);
481 if (b<0) cout << "-";
482 cout << hh << "h " << mm << "m " << ss << "."
483 << setfill('0') << setw(ndig) << sfrac << "s";
484 return;
485 }
486}
487///////////////////////////////////////////////////////////////////////////
488void AliAstrolab::SetSignal(Ali3Vector* r,TString frame,TString mode,AliTimestamp* ts,Int_t jref,TString name)
489{
490// Store a signal as specified by the position r and the timestamp ts.
491// The position is stored in International Celestial Reference System (ICRS) coordinates.
492// The ICRS is a fixed, time independent frame and as such provides a unique reference
493// frame without the need of specifying any epoch etc...
494// The ICRS coordinate definitions match within 20 mas with the mean ones of the J2000.0
495// equatorial system. Nevertheless, to obtain the highest accuracy, the slight
496// coordinate correction between J2000 and ICRS is performed here via the
497// so-called frame bias matrix.
498// For further details see the U.S. Naval Observatory (USNO) circular 179 (2005),
499// which is available on http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
500//
501// The input parameter "frame" allows the user to specify the frame to which
502// the components of r refer. Available options are :
503//
504// frame = "equ" ==> Equatorial coordinates with right ascension (a) and declination (d),
505// where the "sph" components of r correspond to theta=(pi/2)-d and phi=a.
b867da20 506// "gal" ==> Galactic coordinates with longitude (l) and latitude (b).
8bde545d 507// where the "sph" components of r correspond to theta=(pi/2)-b and phi=l.
b867da20 508// "ecl" ==> Ecliptic coordinates with longitude (l) and latitude (b),
8bde545d 509// where the "sph" components of r correspond to theta=(pi/2)-b and phi=l.
510// "hor" ==> Horizontal coordinates at the AliAstrolab location, where the "sph"
511// components of r correspond to theta=zenith angle and phi=pi-azimuth.
b867da20 512// "icr" ==> ICRS coordinates with longitude (l) and latitude (b),
8bde545d 513// where the "sph" components of r correspond to theta=(pi/2)-b and phi=l.
514// "loc" ==> Local coordinates at the AliAstrolab location, where the "sph"
515// components of r correspond to the usual theta and phi angles.
516//
517// In case the coordinates are the equatorial right ascension and declination (a,d),
518// they can represent so-called "mean" and "true" values.
519// The distinction between these two representations is the following :
520//
521// mean values : (a,d) are only corrected for precession and not for nutation
522// true values : (a,d) are corrected for both precession and nutation
523//
524// The input parameter "mode" allows the user to specifiy either "mean" or "true"
525// values for the input in case of equatorial (a,d) coordinates.
526//
527// mode = "M" --> Input coordinates are the mean values
528// "T" --> Input coordinates are the true values
529//
530// The input parameter "jref" allows the user to store so-called "reference" signals.
531// These reference signals may be used to check space-time event coincidences with the
532// stored measurement (e.g. coincidence of the measurement with transient phenomena).
533//
534// jref = 0 --> Storage of the measurement
535// j --> Storage of a reference signal at the j-th position (j=1 is first)
536// < 0 --> Add a reference signal at the next available position
537//
538// Via the input argument "name" the user can give the stored signal also a name.
539//
540// The default values are jref=0 and name="".
541//
542// Note : In case ts=0 the current timestamp of the lab will be taken.
543
544 if (!r)
545 {
546 if (!jref && fXsig)
547 {
548 delete fXsig;
549 fXsig=0;
550 }
551 return;
552 }
553
554 if (frame!="equ" && frame!="gal" && frame!="ecl" && frame!="hor" && frame!="icr" && frame!="loc")
555 {
556 if (!jref && fXsig)
557 {
558 delete fXsig;
559 fXsig=0;
560 }
561 return;
562 }
563
564 if (frame=="equ" && mode!="M" && mode!="m" && mode!="T" && mode!="t")
565 {
566 if (!jref && fXsig)
567 {
568 delete fXsig;
569 fXsig=0;
570 }
571 return;
572 }
573
574 if (!ts) ts=(AliTimestamp*)this;
575
576 Double_t vec[3]={1,0,0};
577 vec[1]=r->GetX(2,"sph","rad");
578 vec[2]=r->GetX(3,"sph","rad");
579 Ali3Vector q;
580 q.SetVector(vec,"sph","rad");
581
582 AliSignal* sxref=0;
583
584 if (!jref) // Storage of the measurement
585 {
586 if (!fXsig)
587 {
588 fXsig=new AliSignal();
589 }
590 else
591 {
592 fXsig->Reset(1);
593 }
594 if (name != "") fXsig->SetName(name);
595 fXsig->SetTitle("Event in ICRS coordinates");
596 fXsig->SetTimestamp(*ts);
597 }
598 else // Storage of a reference signal
599 {
600 if (!fRefs)
601 {
602 fRefs=new TObjArray();
603 fRefs->SetOwner();
604 }
605 // Expand array size if needed
606 if (jref>0 && jref>=fRefs->GetSize()) fRefs->Expand(jref+1);
607 sxref=new AliSignal();
608 if (name != "") sxref->SetName(name);
609 sxref->SetTitle("Reference event in ICRS coordinates");
610 sxref->SetTimestamp(*ts);
611 }
612
613 if (frame=="loc")
614 {
615 // Convert to horizontal coordinates
616 q=q.GetUnprimed(&fL);
617
618 // Store the signal
619 SetSignal(&q,"hor",mode,ts,jref);
620 return;
621 }
622
623 if (frame=="equ")
624 {
625 // Convert to "mean" values at specified epoch
626 if (mode=="T" || mode=="t")
627 {
628 SetNmatrix(ts);
629 q=q.GetUnprimed(&fN);
630 }
631
632 // Convert to "mean" values at J2000
633 SetPmatrix(ts);
634 q=q.GetUnprimed(&fP);
635
636 // Convert to ICRS values
637 if (!fBias) SetBmatrix();
638 q=q.GetUnprimed(&fB);
639 }
640
641 if (frame=="gal")
642 {
643 // Convert to J2000 equatorial mean coordinates
644 if (fGal != 2) SetGmatrix("J");
645 q=q.GetUnprimed(&fG);
646
647 // Convert to ICRS values
648 if (!fBias) SetBmatrix();
649 q=q.GetUnprimed(&fB);
650 }
651
652 if (frame=="ecl")
653 {
654 // Convert to mean equatorial values at specified epoch
655 SetEmatrix(ts);
656 q=q.GetUnprimed(&fE);
657
658 // Convert to "mean" values at J2000
659 SetPmatrix(ts);
660 q=q.GetUnprimed(&fP);
661
662 // Convert to ICRS values
663 if (!fBias) SetBmatrix();
664 q=q.GetUnprimed(&fB);
665 }
666
667 if (frame=="hor")
668 {
669 // Convert to "true" equatorial values at the specified timestamp
670 SetHmatrix(ts);
671 q=q.GetUnprimed(&fH);
672
673 // Convert to "mean" values at specified timestamp
674 SetNmatrix(ts);
675 q=q.GetUnprimed(&fN);
676
677 // Convert to "mean" values at J2000
678 SetPmatrix(ts);
679 q=q.GetUnprimed(&fP);
680
681 // Convert to ICRS values
682 if (!fBias) SetBmatrix();
683 q=q.GetUnprimed(&fB);
684 }
685
686 // Store the signal in ICRS coordinates
687 if (!jref) // Storage of a regular signal
688 {
689 fXsig->SetPosition(q);
690 }
691 else // Storage of a reference signal
692 {
693 sxref->SetPosition(q);
694 if (jref<0)
695 {
696 fRefs->Add(sxref);
697 }
698 else
699 {
700 fRefs->AddAt(sxref,jref-1);
701 }
702 }
703}
704///////////////////////////////////////////////////////////////////////////
705void AliAstrolab::SetSignal(Double_t a,Double_t d,TString s,Double_t e,TString mode,Int_t jref,TString name)
706{
707// Store a signal with right ascension (a) and declination (d) given for epoch e.
708// The position is stored in International Celestial Reference System (ICRS) coordinates.
709// The ICRS is a fixed, time independent frame and as such provides a unique reference
710// frame without the need of specifying any epoch etc...
711// The ICRS coordinate definitions match within 20 mas the mean ones of the J2000.0
712// equatorial system. Nevertheless, to obtain the highest accuracy, the slight
713// coordinate correction between J2000 and ICRS is performed here via the
714// so-called frame bias matrix.
715// For further details see the U.S. Naval Observatory (USNO) circular 179 (2005),
716// which is available on http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
717//
718// The coordinates (a,d) can represent so-called "mean" and "true" values.
719// The distinction between these two representations is the following :
720//
721// mean values : (a,d) are only corrected for precession and not for nutation
722// true values : (a,d) are corrected for both precession and nutation
723//
724// The input parameter "mode" allows the user to specifiy either "mean" or "true"
725// values for the input (a,d) coordinates.
726//
727// a : Right ascension in hhmmss.sss
728// d : Declination in dddmmss.sss
729// s = "B" --> Besselian reference epoch.
730// "J" --> Julian reference epoch.
731// e : Reference epoch for the input coordinates (e.g. 1900, 1950, 2000,...)
732// mode = "M" --> Input coordinates are the mean values
733// "T" --> Input coordinates are the true values
734//
735// The input parameter "jref" allows the user to store so-called "reference" signals.
736// These reference signals may be used to check space-time event coincidences with the
737// stored measurement (e.g. coincidence of the measurement with transient phenomena).
738//
739// jref = 0 --> Storage of the measurement
740// j --> Storage of a reference signal at the j-th position (j=1 is first)
741// < 0 --> Add a reference signal at the next available position
742//
743// Via the input argument "name" the user can give the stored signal also a name.
744//
745// The default values are jref=0 and name="".
746
747 if (s!="B" && s!="b" && s!="J" && s!="j")
748 {
749 if (!jref && fXsig)
750 {
751 delete fXsig;
752 fXsig=0;
753 }
754 return;
755 }
756
757 if (mode!="M" && mode!="m" && mode!="T" && mode!="t")
758 {
759 if (!jref && fXsig)
760 {
761 delete fXsig;
762 fXsig=0;
763 }
764 return;
765 }
766
767 // Convert coordinates to fractional degrees.
768 a=ConvertAngle(a,"hms","deg");
769 d=ConvertAngle(d,"dms","deg");
770
771
772 AliTimestamp tx;
773 tx.SetEpoch(e,s);
774
775 Ali3Vector r;
776 Double_t vec[3]={1.,90.-d,a};
777 r.SetVector(vec,"sph","deg");
778
779 SetSignal(&r,"equ",mode,&tx,jref,name);
780}
781///////////////////////////////////////////////////////////////////////////
782void AliAstrolab::SetSignal(Double_t a,Double_t d,TString mode,AliTimestamp* ts,Int_t jref,TString name)
783{
784// Store a signal with right ascension (a) and declination (d) given for timestamp ts.
785// The position is stored in International Celestial Reference System (ICRS) coordinates.
786// The ICRS is a fixed, time independent frame and as such provides a unique reference
787// frame without the need of specifying any epoch etc...
788// The ICRS coordinate definitions match within 20 mas the mean ones of the J2000.0
789// equatorial system. Nevertheless, to obtain the highest accuracy, the slight
790// coordinate correction between J2000 and ICRS is performed here via the
791// so-called frame bias matrix.
792// For further details see the U.S. Naval Observatory (USNO) circular 179 (2005),
793// which is available on http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
794//
795// The coordinates (a,d) can represent so-called "mean" and "true" values.
796// The distinction between these two representations is the following :
797//
798// mean values : (a,d) are only corrected for precession and not for nutation
799// true values : (a,d) are corrected for both precession and nutation
800//
801// The input parameter "mode" allows the user to specifiy either "mean" or "true"
802// values for the input (a,d) coordinates.
803//
804// a : Right ascension in hhmmss.sss
805// d : Declination in dddmmss.sss
806// mode = "M" --> Input coordinates are the mean values
807// "T" --> Input coordinates are the true values
808//
809// The input parameter "jref" allows the user to store so-called "reference" signals.
810// These reference signals may be used to check space-time event coincidences with the
811// stored measurement (e.g. coincidence of the measurement with transient phenomena).
812//
813// jref = 0 --> Storage of the measurement
814// j --> Storage of a reference signal at the j-th position (j=1 is first)
815// < 0 --> Add a reference signal at the next available position
816//
817// Via the input argument "name" the user can give the stored signal also a name.
818//
819// The default values are jref=0 and name="".
820//
821// Note : In case ts=0 the current timestamp of the lab will be taken.
822
823 // Convert coordinates to fractional degrees.
824 a=ConvertAngle(a,"hms","deg");
825 d=ConvertAngle(d,"dms","deg");
826
827 Ali3Vector r;
828 Double_t vec[3]={1.,90.-d,a};
829 r.SetVector(vec,"sph","deg");
830
831 SetSignal(&r,"equ",mode,ts,jref,name);
832}
833///////////////////////////////////////////////////////////////////////////
834AliSignal* AliAstrolab::GetSignal(Ali3Vector& r,TString frame,TString mode,AliTimestamp* ts,Int_t jref)
835{
836// Provide the user specified coordinates of a signal at the specific timestamp ts.
837// The coordinates are returned via the vector argument "r".
838// In addition also a pointer to the stored signal object is provided.
839// In case no stored signal was available or one of the input arguments was
840// invalid, the returned pointer will be 0.
841//
842// The input parameter "frame" allows the user to specify the frame to which
843// the components of r refer. Available options are :
844//
845// frame = "equ" ==> Equatorial coordinates with right ascension (a) and declination (d),
846// where the "sph" components of r correspond to theta=(pi/2)-d and phi=a.
b867da20 847// "gal" ==> Galactic coordinates with longitude (l) and latitude (b).
8bde545d 848// where the "sph" components of r correspond to theta=(pi/2)-b and phi=l.
b867da20 849// "ecl" ==> Ecliptic coordinates with longitude (l) and latitude (b),
8bde545d 850// where the "sph" components of r correspond to theta=(pi/2)-b and phi=l.
851// "hor" ==> Horizontal coordinates at the AliAstrolab location, where the "sph"
852// components of r correspond to theta=zenith angle and phi=pi-azimuth.
b867da20 853// "icr" ==> ICRS coordinates with longitude (l) and latitude (b),
8bde545d 854// where the "sph" components of r correspond to theta=(pi/2)-b and phi=l.
855// "loc" ==> Local coordinates at the AliAstrolab location, where the "sph"
856// components of r correspond to the usual theta and phi angles.
857//
858// In case the coordinates are the equatorial right ascension and declination (a,d),
859// they can represent so-called "mean" and "true" values.
860// The distinction between these two representations is the following :
861//
862// mean values : (a,d) are only corrected for precession and not for nutation
863// true values : (a,d) are corrected for both precession and nutation
864//
865// The input parameter "mode" allows the user to specifiy either "mean" or "true"
866// values for the input in case of equatorial (a,d) coordinates.
867//
868// mode = "M" --> Input coordinates are the mean values
869// "T" --> Input coordinates are the true values
870//
871// The input parameter "jref" allows the user to access so-called "reference" signals.
872// These reference signals may be used to check space-time event coincidences with the
873// stored measurement (e.g. coincidence of the measurement with transient phenomena).
874//
875// jref = 0 --> Access to the measurement
876// j --> Access to the reference signal at the j-th position (j=1 is first)
877//
878// Default value is jref=0.
879//
880// Note : In case ts=0 the current timestamp of the lab will be taken.
881
882 r.SetZero();
883
884 if (frame!="equ" && frame!="gal" && frame!="ecl" && frame!="hor" && frame!="icr" && frame!="loc") return 0;
885
886 if (frame=="equ" && mode!="M" && mode!="m" && mode!="T" && mode!="t") return 0;
887
888 AliSignal* sx=GetSignal(jref);
889
890 if (!sx) return 0;
891
892 if (!ts) ts=(AliTimestamp*)this;
893
894 Double_t vec[3];
895 sx->GetPosition(vec,"sph","rad");
896 Ali3Vector q;
897 q.SetVector(vec,"sph","rad");
898
899 if (frame=="icr")
900 {
901 r.Load(q);
902 return sx;
903 }
904
905 // Convert from ICRS to equatorial J2000 coordinates
906 if (!fBias) SetBmatrix();
907 q=q.GetPrimed(&fB);
908
909 if (frame=="equ")
910 {
911 // Precess to specified timestamp
912 AliTimestamp ts1;
913 ts1.SetEpoch(2000,"J");
914 Precess(q,&ts1,ts);
915
916 // Nutation correction if requested
917 if (mode=="T" || mode=="t") Nutate(q,ts);
918 }
919
920 if (frame=="gal")
921 {
922 // Convert from equatorial J2000 to galactic
923 if (fGal != 2) SetGmatrix("J");
924 q=q.GetPrimed(&fG);
925 }
926
927 if (frame=="ecl")
928 {
929 // Precess to specified timestamp
930 AliTimestamp ts1;
931 ts1.SetEpoch(2000,"J");
932 Precess(q,&ts1,ts);
933
934 // Convert from equatorial to ecliptic coordinates
935 SetEmatrix(ts);
936 q=q.GetPrimed(&fE);
937 }
938
939 if (frame=="hor")
940 {
941 // Precess to specified timestamp
942 AliTimestamp ts1;
943 ts1.SetEpoch(2000,"J");
944 Precess(q,&ts1,ts);
945
946 // Nutation correction
947 Nutate(q,ts);
948
949 // Convert from equatorial to horizontal coordinates
950 SetHmatrix(ts);
951 q=q.GetPrimed(&fH);
952 }
953
954 if (frame=="loc")
955 {
956 // Get the signal in horizontal coordinates
957 GetSignal(q,"hor",mode,ts);
958
959 // Convert from horizontal local-frame coordinates
960 q=q.GetPrimed(&fL);
961 }
962
963 r.Load(q);
964 return sx;
965}
966///////////////////////////////////////////////////////////////////////////
967AliSignal* AliAstrolab::GetSignal(Ali3Vector& r,TString frame,TString mode,AliTimestamp* ts,TString name)
968{
969// Provide the user specified coordinates of the signal with the specified
970// name at the specific timestamp ts.
971// The coordinates are returned via the vector argument "r".
972// In addition also a pointer to the stored signal object is provided.
973// In case no such stored signal was available or one of the input arguments was
974// invalid, the returned pointer will be 0.
975//
976// The input parameter "frame" allows the user to specify the frame to which
977// the components of r refer. Available options are :
978//
979// frame = "equ" ==> Equatorial coordinates with right ascension (a) and declination (d),
980// where the "sph" components of r correspond to theta=(pi/2)-d and phi=a.
b867da20 981// "gal" ==> Galactic coordinates with longitude (l) and latitude (b).
8bde545d 982// where the "sph" components of r correspond to theta=(pi/2)-b and phi=l.
b867da20 983// "ecl" ==> Ecliptic coordinates with longitude (l) and latitude (b),
8bde545d 984// where the "sph" components of r correspond to theta=(pi/2)-b and phi=l.
985// "hor" ==> Horizontal coordinates at the AliAstrolab location, where the "sph"
986// components of r correspond to theta=zenith angle and phi=pi-azimuth.
b867da20 987// "icr" ==> ICRS coordinates with longitude (l) and latitude (b),
8bde545d 988// where the "sph" components of r correspond to theta=(pi/2)-b and phi=l.
989// "loc" ==> Local coordinates at the AliAstrolab location, where the "sph"
990// components of r correspond to the usual theta and phi angles.
991//
992// In case the coordinates are the equatorial right ascension and declination (a,d),
993// they can represent so-called "mean" and "true" values.
994// The distinction between these two representations is the following :
995//
996// mean values : (a,d) are only corrected for precession and not for nutation
997// true values : (a,d) are corrected for both precession and nutation
998//
999// The input parameter "mode" allows the user to specifiy either "mean" or "true"
1000// values for the input in case of equatorial (a,d) coordinates.
1001//
1002// mode = "M" --> Input coordinates are the mean values
1003// "T" --> Input coordinates are the true values
1004//
1005// Note : In case ts=0 the current timestamp of the lab will be taken.
1006
1007 AliSignal* sx=0;
1008 Int_t j=GetSignalIndex(name);
1009 if (j>=0) sx=GetSignal(r,frame,mode,ts,j);
1010 return sx;
1011}
1012///////////////////////////////////////////////////////////////////////////
1013AliSignal* AliAstrolab::GetSignal(Double_t& a,Double_t& d,TString mode,AliTimestamp* ts,Int_t jref)
1014{
1015// Provide precession (and nutation) corrected right ascension (a) and
1016// declination (d) of the stored signal object at the specified timestamp.
1017// In addition also a pointer to the stored signal object is provided.
1018// In case no stored signal was available or one of the input arguments was
1019// invalid, the returned pointer will be 0.
1020//
1021// The coordinates (a,d) can represent so-called "mean" and "true" values.
1022// The distinction between these two representations is the following :
1023//
1024// mean values : (a,d) are only corrected for precession and not for nutation
1025// true values : (a,d) are corrected for both precession and nutation
1026//
1027// The input parameter "mode" allows the user to select either
1028// "mean" or "true" values for (a,d).
1029//
1030// The correction methods used are the new IAU 2000 ones as described in the
1031// U.S. Naval Observatory (USNO) circular 179 (2005), which is available on
1032// http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
1033//
1034// a : Right ascension in hhmmss.sss
1035// d : Declination in dddmmss.sss
1036// mode = "M" --> Output coordinates are the mean values
1037// "T" --> Output coordinates are the true values
1038// ts : Timestamp at which the corrected coordinate values are requested.
1039//
1040// The input parameter "jref" allows the user to access so-called "reference" signals.
1041// These reference signals may be used to check space-time event coincidences with the
1042// stored regular signal (e.g. coincidence of the stored signal with transient phenomena).
1043//
1044// jref = 0 --> Access to the measurement
1045// j --> Access to the reference signal at the j-th position (j=1 is first)
1046//
1047// Default value is jref=0.
1048//
1049// Note : In case ts=0 the current timestamp of the lab will be taken.
1050
1051 a=0;
1052 d=0;
1053
1054 Ali3Vector r;
1055 AliSignal* sx=GetSignal(r,"equ",mode,ts,jref);
1056
1057 if (!sx) return 0;
1058
1059 // Retrieve the requested (a,d) values
1060 Double_t vec[3];
1061 r.GetVector(vec,"sph","deg");
1062 d=90.-vec[1];
1063 a=vec[2];
1064
1065 while (a<-360.)
1066 {
1067 a+=360.;
1068 }
1069 while (a>360.)
1070 {
1071 a-=360.;
1072 }
1073 while (d<-90.)
1074 {
1075 d+=90.;
1076 }
1077 while (d>90.)
1078 {
1079 d-=90.;
1080 }
1081
1082 // Convert coordinates to appropriate format
1083 a=ConvertAngle(a,"deg","hms");
1084 d=ConvertAngle(d,"deg","dms");
1085
1086 return sx;
1087}
1088///////////////////////////////////////////////////////////////////////////
1089AliSignal* AliAstrolab::GetSignal(Double_t& a,Double_t& d,TString mode,AliTimestamp* ts,TString name)
1090{
1091// Provide precession (and nutation) corrected right ascension (a) and
1092// declination (d) of the stored signal object with the specified name
1093// at the specific timestamp ts.
1094// In addition also a pointer to the stored signal object is provided.
1095// In case no stored signal was available or one of the input arguments was
1096// invalid, the returned pointer will be 0.
1097//
1098// The coordinates (a,d) can represent so-called "mean" and "true" values.
1099// The distinction between these two representations is the following :
1100//
1101// mean values : (a,d) are only corrected for precession and not for nutation
1102// true values : (a,d) are corrected for both precession and nutation
1103//
1104// The input parameter "mode" allows the user to select either
1105// "mean" or "true" values for (a,d).
1106//
1107// The correction methods used are the new IAU 2000 ones as described in the
1108// U.S. Naval Observatory (USNO) circular 179 (2005), which is available on
1109// http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
1110//
1111// a : Right ascension in hhmmss.sss
1112// d : Declination in dddmmss.sss
1113// mode = "M" --> Output coordinates are the mean values
1114// "T" --> Output coordinates are the true values
1115// ts : Timestamp at which the corrected coordinate values are requested.
1116// name : Name of the requested signal object
1117//
1118// Note : In case ts=0 the current timestamp of the lab will be taken.
1119
1120 AliSignal* sx=0;
1121 Int_t j=GetSignalIndex(name);
1122 if (j>=0) sx=GetSignal(a,d,mode,ts,j);
1123 return sx;
1124}
1125///////////////////////////////////////////////////////////////////////////
1126AliSignal* AliAstrolab::GetSignal(Double_t& a,Double_t& d,TString s,Double_t e,TString mode,Int_t jref)
1127{
1128// Provide precession (and nutation) corrected right ascension (a) and
1129// declination (d) of the stored signal object at the specified epoch e.
1130// In addition also a pointer to the stored signal object is provided.
1131// In case no stored signal was available or one of the input arguments was
1132// invalid, the returned pointer will be 0.
1133//
1134// The coordinates (a,d) can represent so-called "mean" and "true" values.
1135// The distinction between these two representations is the following :
1136//
1137// mean values : (a,d) are only corrected for precession and not for nutation
1138// true values : (a,d) are corrected for both precession and nutation
1139//
1140// The input parameter "mode" allows the user to specifiy either "mean" or "true"
1141// values for the input (a,d) coordinates.
1142//
1143// a : Right ascension in hhmmss.sss
1144// d : Declination in dddmmss.sss
1145// s = "B" --> Besselian reference epoch.
1146// "J" --> Julian reference epoch.
1147// e : Reference epoch for the input coordinates (e.g. 1900, 1950, 2000,...)
1148// mode = "M" --> Input coordinates are the mean values
1149// "T" --> Input coordinates are the true values
1150//
1151// The input parameter "jref" allows the user to access so-called "reference" signals.
1152// These reference signals may be used to check space-time event coincidences with the
1153// stored measurement (e.g. coincidence of the measurement with transient phenomena).
1154//
1155// jref = 0 --> Access to the measurement
1156// j --> Access to the reference signal at the j-th position (j=1 is first)
1157//
1158// Default value is jref=0.
1159
1160 a=0;
1161 d=0;
1162
1163 if (s!="B" && s!="b" && s!="J" && s!="j") return 0;
1164
1165 if (mode!="M" && mode!="m" && mode!="T" && mode!="t") return 0;
1166
1167 // Convert coordinates to fractional degrees.
1168 a=ConvertAngle(a,"hms","deg");
1169 d=ConvertAngle(d,"dms","deg");
1170
1171
1172 AliTimestamp tx;
1173 tx.SetEpoch(e,s);
1174
1175 AliSignal* sx=GetSignal(a,d,mode,&tx,jref);
1176 return sx;
1177}
1178///////////////////////////////////////////////////////////////////////////
1179AliSignal* AliAstrolab::GetSignal(Double_t& a,Double_t& d,TString s,Double_t e,TString mode,TString name)
1180{
1181// Provide precession (and nutation) corrected right ascension (a) and
1182// declination (d) of the stored signal object with the specified name
1183// at the specific epoch e.
1184// In addition also a pointer to the stored signal object is provided.
1185// In case no stored signal was available or one of the input arguments was
1186// invalid, the returned pointer will be 0.
1187//
1188// The coordinates (a,d) can represent so-called "mean" and "true" values.
1189// The distinction between these two representations is the following :
1190//
1191// mean values : (a,d) are only corrected for precession and not for nutation
1192// true values : (a,d) are corrected for both precession and nutation
1193//
1194// The input parameter "mode" allows the user to specifiy either "mean" or "true"
1195// values for the input (a,d) coordinates.
1196//
1197// a : Right ascension in hhmmss.sss
1198// d : Declination in dddmmss.sss
1199// s = "B" --> Besselian reference epoch.
1200// "J" --> Julian reference epoch.
1201// e : Reference epoch for the input coordinates (e.g. 1900, 1950, 2000,...)
1202// mode = "M" --> Input coordinates are the mean values
1203// "T" --> Input coordinates are the true values
1204// name : Name of the requested signal object
1205
1206 AliSignal* sx=0;
1207 Int_t j=GetSignalIndex(name);
1208 if (j>=0) sx=GetSignal(a,d,s,e,mode,j);
1209 return sx;
1210}
1211///////////////////////////////////////////////////////////////////////////
1212AliSignal* AliAstrolab::GetSignal(Int_t jref)
1213{
1214// Provide the pointer to a stored signal object.
1215//
1216// The input parameter "jref" allows the user to access so-called "reference" signals.
1217// These reference signals may be used to check space-time event coincidences with the
1218// stored measurement (e.g. coincidence of the measurement with transient phenomena).
1219//
1220// jref = 0 --> Access to the measurement
1221// j --> Access to the reference signal at the j-th position (j=1 is first)
1222//
1223// Default value is jref=0.
1224
1225 AliSignal* sx=0;
1226 if (!jref)
1227 {
1228 sx=fXsig;
1229 }
1230 else
1231 {
1232 if (jref>0 && jref<fRefs->GetSize()) sx=(AliSignal*)fRefs->At(jref-1);
1233 }
1234 return sx;
1235}
1236///////////////////////////////////////////////////////////////////////////
1237AliSignal* AliAstrolab::GetSignal(TString name)
1238{
1239// Provide the pointer to the stored signal object with the specified name.
1240
1241 AliSignal* sx=0;
1242 Int_t j=GetSignalIndex(name);
1243 if (j>=0) sx=GetSignal(j);
1244 return sx;
1245}
1246///////////////////////////////////////////////////////////////////////////
1247void AliAstrolab::RemoveRefSignal(Int_t j,Int_t compress)
1248{
1249// Remove the reference signal which was stored at the j-th position (j=1 is first).
1250// Note : j=0 means that all stored reference signals will be removed.
1251// j<0 allows array compression (see below) without removing any signals.
1252//
1253// The "compress" parameter allows compression of the ref. signal storage array.
1254//
1255// compress = 1 --> Array will be compressed
1256// 0 --> Array will not be compressed
1257//
1258// Note : Compression of the storage array means that the indices of the
1259// reference signals in the storage array will change.
1260
1261 if (!fRefs) return;
1262
1263 // Clearing of the complete storage
1264 if (!j)
1265 {
1266 delete fRefs;
1267 fRefs=0;
1268 return;
1269 }
1270
1271 // Removing a specific reference signal
1272 if (j>0 && j<fRefs->GetSize())
1273 {
1274 TObject* obj=fRefs->RemoveAt(j-1);
1275 if (obj) delete obj;
1276 }
1277
1278 // Compression of the storage array
1279 if (compress) fRefs->Compress();
1280}
1281///////////////////////////////////////////////////////////////////////////
1282void AliAstrolab::RemoveRefSignal(TString name,Int_t compress)
1283{
1284// Remove the reference signal with the specified name.
1285//
1286// The "compress" parameter allows compression of the ref. signal storage array.
1287//
1288// compress = 1 --> Array will be compressed
1289// 0 --> Array will not be compressed
1290//
1291// Note : Compression of the storage array means that the indices of the
1292// reference signals in the storage array will change.
1293
1294 Int_t j=GetSignalIndex(name);
1295 if (j>0) RemoveRefSignal(j,compress);
1296}
1297///////////////////////////////////////////////////////////////////////////
1298Int_t AliAstrolab::GetSignalIndex(TString name)
1299{
1300// Provide storage index of the signal with the specified name.
1301// In case the name matches with the stored measurement,
1302// the value 0 is returned.
1303// In case no signal with the specified name was found, the value -1 is returned.
1304
1305 Int_t index=-1;
1306
1307 if (fXsig)
1308 {
1309 if (name==fXsig->GetName()) return 0;
1310 }
1311
1312 if (!fRefs) return -1;
1313
1314 for (Int_t i=0; i<fRefs->GetSize(); i++)
1315 {
1316 AliSignal* sx=(AliSignal*)fRefs->At(i);
1317 if (!sx) continue;
1318
1319 if (name==sx->GetName())
1320 {
1321 index=i+1;
1322 break;
1323 }
1324 }
1325
1326 return index;
1327}
1328///////////////////////////////////////////////////////////////////////////
1329void AliAstrolab::PrintSignal(TString frame,TString mode,AliTimestamp* ts,Int_t ndig,Int_t jref)
1330{
1331// Print data of a stored signal in user specified coordinates at the specific timestamp ts.
1332// In case no stored signal was available or one of the input arguments was
1333// invalid, no printout is produced.
1334//
1335// The argument "ndig" specifies the number of digits for the fractional
1336// part (e.g. ndig=6 for "dms" corresponds to micro-arcsecond precision).
1337// No rounding will be performed, so an arcsecond count of 3.473 with ndig=1
1338// will appear as 03.4 on the output.
1339// Due to computer accuracy, precision on the pico-arcsecond level may get lost.
1340//
1341// Note : The angle info is printed without additional spaces or "endline".
1342// This allows the print to be included in various composite output formats.
1343//
1344// The input parameter "frame" allows the user to specify the frame to which
1345// the coordinates refer. Available options are :
1346//
1347// frame = "equ" ==> Equatorial coordinates with right ascension (a) and declination (d).
1348//
b867da20 1349// "gal" ==> Galactic coordinates with longitude (l) and latitude (b).
8bde545d 1350//
b867da20 1351// "ecl" ==> Ecliptic coordinates with longitude (l) and latitude (b).
8bde545d 1352//
1353// "hor" ==> Horizontal azimuth and altitude coordinates at the AliAstrolab location.
1354//
b867da20 1355// "icr" ==> ICRS coordinates with longitude (l) and latitude (b).
8bde545d 1356//
1357// "loc" ==> Local spherical angles theta and phi at the AliAstrolab location.
1358//
1359// In case the coordinates are the equatorial right ascension and declination (a,d),
1360// they can represent so-called "mean" and "true" values.
1361// The distinction between these two representations is the following :
1362//
1363// mean values : (a,d) are only corrected for precession and not for nutation
1364// true values : (a,d) are corrected for both precession and nutation
1365//
1366// The input parameter "mode" allows the user to specifiy either "mean" or "true"
1367// values for the input in case of equatorial (a,d) coordinates.
1368//
1369// mode = "M" --> Input coordinates are the mean values
1370// "T" --> Input coordinates are the true values
1371//
661385a7 1372// The input parameter "mode" also determines which type of time and
1373// local hour angle will appear in the printout.
1374//
caa58e1a 1375// mode = "M" --> Mean Sidereal Time (MST) and Local Mean Hour Angle (LMHA)
1376// "T" --> Apparent Sidereal Time (AST) and Local Apparent Hour Angle (LAHA)
661385a7 1377//
8bde545d 1378// The input parameter "jref" allows printing of a so-called "reference" signal.
1379// These reference signals may serve to check space-time event coincidences with the
1380// stored measurement (e.g. coincidence of the measurement with transient phenomena).
1381//
1382// jref = 0 --> Printing of the measurement
1383// j --> Printing of the j-th reference signal
1384//
1385// Default value is jref=0.
1386//
1387// Note : In case ts=0 the current timestamp of the lab will be taken.
1388
1389 Ali3Vector r;
1390 AliSignal* sx=GetSignal(r,frame,mode,ts,jref);
1391
1392 if (!sx) return;
1393
661385a7 1394 // Local Hour Angle of the signal
1395 Double_t lha=GetHourAngle("A",ts,jref);
1396 TString slha="LAHA";
1397 if (mode=="M" || mode=="m")
1398 {
1399 lha=GetHourAngle("M",ts,jref);
1400 slha="LMHA";
1401 }
1402
8bde545d 1403 TString name=sx->GetName();
1404 if (name != "") cout << name.Data() << " ";
1405
1406 if (frame=="equ")
1407 {
1408 Double_t a,d;
1409 d=90.-r.GetX(2,"sph","deg");
1410 a=r.GetX(3,"sph","rad");
1411 cout << "Equatorial (" << mode.Data() <<") a : "; PrintAngle(a,"rad","hms",ndig);
1412 cout << " d : "; PrintAngle(d,"deg","dms",ndig);
661385a7 1413 cout << " " << slha.Data() << " : "; PrintAngle(lha,"deg","hms",ndig);
8bde545d 1414 return;
1415 }
1416
1417 if (frame=="gal")
1418 {
1419 Double_t l,b;
1420 b=90.-r.GetX(2,"sph","deg");
1421 l=r.GetX(3,"sph","deg");
1422 cout << "Galactic l : "; PrintAngle(l,"deg","deg",ndig);
1423 cout << " b : "; PrintAngle(b,"deg","deg",ndig);
661385a7 1424 cout << " " << slha.Data() << " : "; PrintAngle(lha,"deg","hms",ndig);
8bde545d 1425 return;
1426 }
1427
1428 if (frame=="icr")
1429 {
1430 Double_t a,d;
1431 d=90.-r.GetX(2,"sph","deg");
1432 a=r.GetX(3,"sph","rad");
1433 cout << "ICRS l : "; PrintAngle(a,"rad","hms",ndig);
1434 cout << " b : "; PrintAngle(d,"deg","dms",ndig);
661385a7 1435 cout << " " << slha.Data() << " : "; PrintAngle(lha,"deg","hms",ndig);
8bde545d 1436 return;
1437 }
1438
1439 if (frame=="ecl")
1440 {
1441 Double_t a,d;
1442 d=90.-r.GetX(2,"sph","deg");
1443 a=r.GetX(3,"sph","deg");
1444 cout << "Ecliptic l : "; PrintAngle(a,"deg","deg",ndig);
1445 cout << " b : "; PrintAngle(d,"deg","deg",ndig);
661385a7 1446 cout << " " << slha.Data() << " : "; PrintAngle(lha,"deg","hms",ndig);
8bde545d 1447 return;
1448 }
1449
1450 if (frame=="hor")
1451 {
1452 Double_t alt=90.-r.GetX(2,"sph","deg");
1453 Double_t azi=180.-r.GetX(3,"sph","deg");
1454 while (azi>360)
1455 {
1456 azi-=360.;
1457 }
1458 while (azi<0)
1459 {
1460 azi+=360.;
1461 }
1462 cout << "Horizontal azi : "; PrintAngle(azi,"deg","deg",ndig);
1463 cout << " alt : "; PrintAngle(alt,"deg","deg",ndig);
661385a7 1464 cout << " " << slha.Data() << " : "; PrintAngle(lha,"deg","hms",ndig);
8bde545d 1465 return;
1466 }
1467
1468 if (frame=="loc")
1469 {
1470 Double_t theta=r.GetX(2,"sph","deg");
1471 Double_t phi=r.GetX(3,"sph","deg");
1472 cout << "Local-frame phi : "; PrintAngle(phi,"deg","deg",ndig);
1473 cout << " theta : "; PrintAngle(theta,"deg","deg",ndig);
661385a7 1474 cout << " " << slha.Data() << " : "; PrintAngle(lha,"deg","hms",ndig);
8bde545d 1475 return;
1476 }
1477}
1478///////////////////////////////////////////////////////////////////////////
1479void AliAstrolab::PrintSignal(TString frame,TString mode,AliTimestamp* ts,Int_t ndig,TString name)
1480{
1481// Print data of the stored signal with the specified name in user specified coordinates
1482// at the specific timestamp ts.
b867da20 1483// In case no such stored signal was available or one of the input arguments was
8bde545d 1484// invalid, no printout is produced.
1485//
1486// The argument "ndig" specifies the number of digits for the fractional
1487// part (e.g. ndig=6 for "dms" corresponds to micro-arcsecond precision).
1488// No rounding will be performed, so an arcsecond count of 3.473 with ndig=1
1489// will appear as 03.4 on the output.
1490// Due to computer accuracy, precision on the pico-arcsecond level may get lost.
1491//
1492// Note : The angle info is printed without additional spaces or "endline".
1493// This allows the print to be included in various composite output formats.
1494//
1495// The input parameter "frame" allows the user to specify the frame to which
1496// the coordinates refer. Available options are :
1497//
1498// frame = "equ" ==> Equatorial coordinates with right ascension (a) and declination (d).
1499//
b867da20 1500// "gal" ==> Galactic coordinates with longitude (l) and latitude (b).
8bde545d 1501//
b867da20 1502// "ecl" ==> Ecliptic coordinates with longitude (l) and latitude (b).
8bde545d 1503//
1504// "hor" ==> Horizontal azimuth and altitude coordinates at the AliAstrolab location.
1505//
b867da20 1506// "icr" ==> ICRS coordinates with longitude (l) and latitude (b).
8bde545d 1507//
1508// "loc" ==> Local spherical angles theta and phi at the AliAstrolab location.
1509//
1510// In case the coordinates are the equatorial right ascension and declination (a,d),
1511// they can represent so-called "mean" and "true" values.
1512// The distinction between these two representations is the following :
1513//
1514// mean values : (a,d) are only corrected for precession and not for nutation
1515// true values : (a,d) are corrected for both precession and nutation
1516//
1517// The input parameter "mode" allows the user to specifiy either "mean" or "true"
1518// values for the input in case of equatorial (a,d) coordinates.
1519//
1520// mode = "M" --> Input coordinates are the mean values
1521// "T" --> Input coordinates are the true values
1522//
661385a7 1523// The input parameter "mode" also determines which type of time and
1524// local hour angle will appear in the printout.
1525//
caa58e1a 1526// mode = "M" --> Mean Sidereal Time (MST) and Local Mean Hour Angle (LMHA)
1527// "T" --> Apparent Sidereal Time (AST) and Local Apparent Hour Angle (LAHA)
661385a7 1528//
8bde545d 1529// Note : In case ts=0 the current timestamp of the lab will be taken.
1530
1531 Int_t j=GetSignalIndex(name);
1532 if (j>=0) PrintSignal(frame,mode,ts,ndig,j);
1533}
1534///////////////////////////////////////////////////////////////////////////
1535void AliAstrolab::ListSignals(TString frame,TString mode,Int_t ndig)
1536{
1537// List all stored signals in user specified coordinates at the timestamp
1538// of the actual recording of the stored measurement under investigation.
1539// In case no (timestamp of the) actual measurement is available,
1540// the current timestamp of the lab will be taken.
1541// In case no stored signal is available or one of the input arguments is
1542// invalid, no printout is produced.
1543//
1544// The argument "ndig" specifies the number of digits for the fractional
1545// part (e.g. ndig=6 for "dms" corresponds to micro-arcsecond precision).
1546// No rounding will be performed, so an arcsecond count of 3.473 with ndig=1
1547// will appear as 03.4 on the output.
1548// Due to computer accuracy, precision on the pico-arcsecond level may get lost.
1549//
661385a7 1550// The default value is ndig=1.
8bde545d 1551//
1552// Note : The angle info is printed without additional spaces or "endline".
1553// This allows the print to be included in various composite output formats.
1554//
1555// The input parameter "frame" allows the user to specify the frame to which
1556// the coordinates refer. Available options are :
1557//
1558// frame = "equ" ==> Equatorial coordinates with right ascension (a) and declination (d).
1559//
b867da20 1560// "gal" ==> Galactic coordinates with longitude (l) and latitude (b).
8bde545d 1561//
b867da20 1562// "ecl" ==> Ecliptic coordinates with longitude (l) and latitude (b).
8bde545d 1563//
1564// "hor" ==> Horizontal azimuth and altitude coordinates at the AliAstrolab location.
1565//
b867da20 1566// "icr" ==> ICRS coordinates with longitude (l) and latitude (b).
8bde545d 1567//
1568// "loc" ==> Local spherical angles theta and phi at the AliAstrolab location.
1569//
1570// In case the coordinates are the equatorial right ascension and declination (a,d),
1571// they can represent so-called "mean" and "true" values.
1572// The distinction between these two representations is the following :
1573//
1574// mean values : (a,d) are only corrected for precession and not for nutation
1575// true values : (a,d) are corrected for both precession and nutation
1576//
1577// The input parameter "mode" allows the user to specifiy either "mean" or "true"
1578// values for the input in case of equatorial (a,d) coordinates.
1579//
1580// mode = "M" --> Input coordinates are the mean values
1581// "T" --> Input coordinates are the true values
1582//
661385a7 1583// The input parameter "mode" also determines which type of time and
1584// local hour angle will appear in the listing.
1585//
caa58e1a 1586// mode = "M" --> Mean Sidereal Time (MST) and Local Mean Hour Angle (LMHA)
1587// "T" --> Apparent Sidereal Time (AST) and Local Apparent Hour Angle (LAHA)
8bde545d 1588
1589 Int_t iprint=0;
1590
1591 AliTimestamp* tx=0;
1592
661385a7 1593 Int_t dform=1;
1594 if (mode=="T" || mode=="t") dform=-1;
1595
8bde545d 1596 if (fXsig)
1597 {
661385a7 1598 tx=fXsig->GetTimestamp();
8bde545d 1599 if (!tx) tx=(AliTimestamp*)this;
1600 cout << " *AliAstrolab::ListSignals* List of all stored signals." << endl;
661385a7 1601 cout << " === The measurement under investigation ===" << endl;
1602 cout << " Timestamp of the actual observation" << endl;
1603 tx->Date(dform,fToffset);
1604 cout << " Location of the actual observation" << endl;
1605 cout << " "; PrintSignal(frame,mode,tx,ndig); cout << endl;
8bde545d 1606 iprint=1;
1607 }
1608
1609 if (!fRefs) return;
1610
1611 for (Int_t i=1; i<=fRefs->GetSize(); i++)
1612 {
1613 AliSignal* sx=GetSignal(i);
1614 if (!sx) continue;
1615
1616 if (!iprint)
1617 {
1618 cout << " *AliAstrolab::ListRefSignals* List of all stored signals." << endl;
1619 tx=(AliTimestamp*)this;
661385a7 1620 cout << " Current timestamp of the laboratory" << endl;
1621 tx->Date(dform,fToffset);
8bde545d 1622 iprint=1;
1623 }
1624 if (iprint==1)
1625 {
661385a7 1626 cout << " === All stored reference signals according to the above timestamp ===" << endl;
8bde545d 1627 iprint=2;
1628 }
661385a7 1629 cout << " Index : " << i << " "; PrintSignal(frame,mode,tx,ndig,i); cout << endl;
8bde545d 1630 }
1631}
1632///////////////////////////////////////////////////////////////////////////
1633void AliAstrolab::Precess(Ali3Vector& r,AliTimestamp* ts1,AliTimestamp* ts2)
1634{
1635// Correct mean right ascension and declination given for Julian date "jd"
1636// for the earth's precession corresponding to the specified timestamp.
1637// The results are the so-called "mean" (i.e. precession corrected) values,
1638// corresponding to the specified timestamp.
1639// The method used is the new IAU 2000 one as described in the
1640// U.S. Naval Observatory (USNO) circular 179 (2005), which is available on
1641// http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
1642// Since the standard reference epoch is J2000, this implies that all
1643// input (a,d) coordinates will be first internally converted to the
1644// corresponding J2000 values before the precession correction w.r.t. the
1645// specified lab timestamp will be applied.
1646//
1647// r : Input vector containing the right ascension and declination information
1648// in the form of standard Ali3Vector coordinates.
1649// In spherical coordinates the phi corresponds to the right ascension,
1650// whereas the declination corresponds to (pi/2)-theta.
1651// jd : Julian date corresponding to the input coordinate values.
1652// ts : Timestamp corresponding to the requested corrected coordinate values.
1653//
1654// Note : In case ts=0 the current timestamp of the lab will be taken.
1655
1656 // Convert back to J2000 values
1657 Ali3Vector r0;
1658 SetPmatrix(ts1);
1659 r0=r.GetUnprimed(&fP);
1660
1661 // Precess to the specified timestamp
1662 if (!ts2) ts2=(AliTimestamp*)this;
1663 SetPmatrix(ts2);
1664 r=r0.GetPrimed(&fP);
1665}
1666///////////////////////////////////////////////////////////////////////////
1667void AliAstrolab::Nutate(Ali3Vector& r,AliTimestamp* ts)
1668{
1669// Correct mean right ascension and declination for the earth's nutation
1670// corresponding to the specified timestamp.
1671// The results are the so-called "true" (i.e. nutation corrected) values,
1672// corresponding to the specified timestamp.
1673// The method used is the new IAU 2000 one as described in the
1674// U.S. Naval Observatory (USNO) circular 179 (2005), which is available on
1675// http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
1676//
1677// r : Input vector containing the right ascension and declination information
1678// in the form of standard Ali3Vector coordinates.
1679// In spherical coordinates the phi corresponds to the right ascension,
1680// whereas the declination corresponds to (pi/2)-theta.
1681// ts : Timestamp for which the corrected coordinate values are requested.
1682//
1683// Note : In case ts=0 the current timestamp of the lab will be taken.
1684
1685 // Nutation correction for the specified timestamp
1686 if (!ts) ts=(AliTimestamp*)this;
1687 SetNmatrix(ts);
1688 r=r.GetPrimed(&fN);
1689}
1690///////////////////////////////////////////////////////////////////////////
1691void AliAstrolab::SetBmatrix()
1692{
1693// Set the frame bias matrix elements.
1694// The formulas and numerical constants used are the ones from the
1695// U.S. Naval Observatory (USNO) circular 179 (2005), which is available on
1696// http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
1697
1698 Double_t pi=acos(-1.);
1699
1700 // Parameters in mas
1701 Double_t a=-14.6;
1702 Double_t x=-16.6170;
1703 Double_t e=-6.8192;
1704
1705 // Convert to radians
1706 a*=pi/(180.*3600.*1000.);
1707 x*=pi/(180.*3600.*1000.);
1708 e*=pi/(180.*3600.*1000.);
1709
1710 Double_t mat[9];
1711 mat[0]=1.-0.5*(a*a+x*x);
1712 mat[1]=a;
1713 mat[2]=-x;
1714 mat[3]=-a-e*x;
1715 mat[4]=1.-0.5*(a*a+e*e);
1716 mat[5]=-e;
1717 mat[6]=x-e*a;
1718 mat[7]=e+x*a;
1719 mat[8]=1.-0.5*(e*e+x*x);
1720
1721 fB.SetMatrix(mat);
1722 fBias=1;
1723}
1724///////////////////////////////////////////////////////////////////////////
1725void AliAstrolab::SetPmatrix(AliTimestamp* ts)
1726{
1727// Set precession matrix elements for Julian date jd w.r.t. J2000.
1728// The formulas and numerical constants used are the ones from the
1729// U.S. Naval Observatory (USNO) circular 179 (2005), which is available on
1730// http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
1731// All numerical constants refer to the standard reference epoch J2000.
1732
1733 Double_t mat[9]={0,0,0,0,0,0,0,0,0};
1734 if (!ts)
1735 {
1736 fP.SetMatrix(mat);
1737 return;
1738 }
1739
1740 Double_t pi=acos(-1.);
1741
1742 Double_t t=(ts->GetJD()-2451545.0)/36525.; // Julian centuries since J2000.0
1743
1744 // Parameters for the precession matrix in arcseconds
1745 Double_t eps0=84381.406; // Mean ecliptic obliquity at J2000.0
1746 Double_t psi=5038.481507*t-1.0790069*pow(t,2)-0.00114045*pow(t,3)+0.000132851*pow(t,4)
1747 -0.0000000951*pow(t,4);
1748 Double_t om=eps0-0.025754*t+0.0512623*pow(t,2)-0.00772503*pow(t,3)-0.000000467*pow(t,4)
1749 +0.0000003337*pow(t,5);
1750 Double_t chi=10.556403*t-2.3814292*pow(t,2)-0.00121197*pow(t,3)+0.000170663*pow(t,4)
1751 -0.0000000560*pow(t,5);
1752
1753 // Convert to radians
1754 eps0*=pi/(180.*3600.);
1755 psi*=pi/(180.*3600.);
1756 om*=pi/(180.*3600.);
1757 chi*=pi/(180.*3600.);
1758
1759 Double_t s1=sin(eps0);
1760 Double_t s2=sin(-psi);
1761 Double_t s3=sin(-om);
1762 Double_t s4=sin(chi);
1763 Double_t c1=cos(eps0);
1764 Double_t c2=cos(-psi);
1765 Double_t c3=cos(-om);
1766 Double_t c4=cos(chi);
1767
1768 mat[0]=c4*c2-s2*s4*c3;
1769 mat[1]=c4*s2*c1+s4*c3*c2*c1-s1*s4*s3;
1770 mat[2]=c4*s2*s1+s4*c3*c2*s1+c1*s4*s3;
1771 mat[3]=-s4*c2-s2*c4*c3;
1772 mat[4]=-s4*s2*c1+c4*c3*c2*c1-s1*c4*s3;
1773 mat[5]=-s4*s2*s1+c4*c3*c2*s1+c1*c4*s3;
1774 mat[6]=s2*s3;
1775 mat[7]=-s3*c2*c1-s1*c3;
1776 mat[8]=-s3*c2*s1+c3*c1;
1777
1778 fP.SetMatrix(mat);
1779}
1780///////////////////////////////////////////////////////////////////////////
1781void AliAstrolab::SetNmatrix(AliTimestamp* ts)
1782{
1783// Set nutation matrix elements for the specified Julian date jd.
1784// The formulas and numerical constants used are the ones from the
1785// U.S. Naval Observatory (USNO) circular 179 (2005), which is available on
1786// http://aa.usno,navy.mil/publications/docs/Circular_179.pdf.
1787
1788 Double_t mat[9]={0,0,0,0,0,0,0,0,0};
1789 if (!ts)
1790 {
1791 fN.SetMatrix(mat);
1792 return;
1793 }
1794
1795 Double_t pi=acos(-1.);
1796
1797 Double_t dpsi,deps,eps;
1798 ts->Almanac(&dpsi,&deps,&eps);
1799
1800 // Convert to radians
1801 dpsi*=pi/(180.*3600.);
1802 deps*=pi/(180.*3600.);
1803 eps*=pi/(180.*3600.);
1804
1805 Double_t s1=sin(eps);
1806 Double_t s2=sin(-dpsi);
1807 Double_t s3=sin(-(eps+deps));
1808 Double_t c1=cos(eps);
1809 Double_t c2=cos(-dpsi);
1810 Double_t c3=cos(-(eps+deps));
1811
1812 mat[0]=c2;
1813 mat[1]=s2*c1;
1814 mat[2]=s2*s1;
1815 mat[3]=-s2*c3;
1816 mat[4]=c3*c2*c1-s1*s3;
1817 mat[5]=c3*c2*s1+c1*s3;
1818 mat[6]=s2*s3;
1819 mat[7]=-s3*c2*c1-s1*c3;
1820 mat[8]=-s3*c2*s1+c3*c1;
1821
1822 fN.SetMatrix(mat);
1823}
1824///////////////////////////////////////////////////////////////////////////
1825void AliAstrolab::SetGmatrix(TString mode)
1826{
1827// Set the mean equatorial to galactic coordinate conversion matrix.
1828// The B1950 parameters were taken from section 22.3 of the book
1829// "An Introduction to Modern Astrophysics" by Carrol and Ostlie (1996).
1830// The J2000 parameters are obtained by precession of the B1950 values.
1831//
1832// Via the input argument "mode" the required epoch can be selected
1833// mode = "B" ==> B1950
1834// "J" ==> J2000
1835
1836 Ali3Vector x; // The Galactic x-axis in the equatorial frame
1837 Ali3Vector y; // The Galactic y-axis in the equatorial frame
1838 Ali3Vector z; // The Galactic z-axis in the equatorial frame
1839
1840 Double_t a,d;
1841 Double_t vec[3]={1,0,0};
1842
1843 fGal=1; // Set flag to indicate B1950 matrix values
1844
1845 // B1950 equatorial coordinates of the North Galactic Pole (NGP)
1846 a=124900.;
1847 d=272400.;
1848 a=ConvertAngle(a,"hms","deg");
1849 d=ConvertAngle(d,"dms","deg");
1850 vec[1]=90.-d;
1851 vec[2]=a;
1852 z.SetVector(vec,"sph","deg");
1853
1854 // B1950 equatorial coordinates of the Galactic l=b=0 point
1855 a=174224.;
1856 d=-285500.;
1857 a=ConvertAngle(a,"hms","deg");
1858 d=ConvertAngle(d,"dms","deg");
1859 vec[1]=90.-d;
1860 vec[2]=a;
1861 x.SetVector(vec,"sph","deg");
1862
1863 // Precess to the corresponding J2000 values if requested
1864 if (mode=="J")
1865 {
1866 fGal=2; // Set flag to indicate J2000 matrix values
1867 AliTimestamp t1;
1868 t1.SetEpoch(1950,"B");
1869 AliTimestamp t2;
1870 t2.SetEpoch(2000,"J");
1871 Precess(z,&t1,&t2);
1872 Precess(x,&t1,&t2);
1873 }
1874
1875 // The Galactic y-axis is determined for the right handed frame
1876 y=z.Cross(x);
1877
1878 fG.SetAngles(x.GetX(2,"sph","deg"),x.GetX(3,"sph","deg"),
1879 y.GetX(2,"sph","deg"),y.GetX(3,"sph","deg"),
1880 z.GetX(2,"sph","deg"),z.GetX(3,"sph","deg"));
1881}
1882///////////////////////////////////////////////////////////////////////////
1883void AliAstrolab::SetEmatrix(AliTimestamp* ts)
1884{
1885// Set the mean equatorial to ecliptic coordinate conversion matrix
1886// for the specified timestamp.
1887// A nice sketch and explanation of the two frames can be found
1888// in chapter 3 of the book "Astronomy Methods" by Hale Bradt (2004).
1889
1890 Double_t dpsi,deps,eps;
1891 ts->Almanac(&dpsi,&deps,&eps);
1892
1893 // Convert to degrees
1894 eps/=3600.;
1895
1896 // Positions of the ecliptic axes w.r.t. the equatorial ones
1897 // at the moment of the specified timestamp
1898 Double_t theta1=90; // Ecliptic x-axis
1899 Double_t phi1=0;
1900 Double_t theta2=90.-eps; //Ecliptic y-axis
1901 Double_t phi2=90;
1902 Double_t theta3=eps; // Ecliptic z-axis
1903 Double_t phi3=270;
1904
1905 fE.SetAngles(theta1,phi1,theta2,phi2,theta3,phi3);
1906}
1907///////////////////////////////////////////////////////////////////////////
1908void AliAstrolab::SetHmatrix(AliTimestamp* ts)
1909{
1910// Set the mean equatorial to horizontal coordinate conversion matrix
1911// for the specified timestamp.
1912// A nice sketch and explanation of the two frames can be found
1913// in chapter 3 of the book "Astronomy Methods" by Hale Bradt (2004).
1914//
1915// Note : In order to simplify the calculations, we use here a
1916// right-handed horizontal frame.
1917
1918 Ali3Vector x; // The (South pointing) horizontal x-axis in the equatorial frame
1919 Ali3Vector y; // The (East pointing) horizontal y-axis in the equatorial frame
1920 Ali3Vector z; // The (Zenith pointing) horizontal z-axis in the equatorial frame
1921
1922 Double_t l,b;
1923 GetLabPosition(l,b,"deg");
1924
1925 Double_t a;
1926 Double_t vec[3]={1,0,0};
1927
1928 // Equatorial coordinates of the horizontal z-axis
1929 // at the moment of the specified timestamp
1930 a=ts->GetLAST(fToffset);
1931 a*=15.; // Convert fractional hours to degrees
1932 vec[1]=90.-b;
1933 vec[2]=a;
1934 z.SetVector(vec,"sph","deg");
1935
1936 // Equatorial coordinates of the horizontal x-axis
1937 // at the moment of the specified timestamp
1938 vec[1]=180.-b;
1939 vec[2]=a;
1940 x.SetVector(vec,"sph","deg");
1941
1942 // The horizontal y-axis is determined for the right handed frame
1943 y=z.Cross(x);
1944
1945 fH.SetAngles(x.GetX(2,"sph","deg"),x.GetX(3,"sph","deg"),
1946 y.GetX(2,"sph","deg"),y.GetX(3,"sph","deg"),
1947 z.GetX(2,"sph","deg"),z.GetX(3,"sph","deg"));
1948}
1949///////////////////////////////////////////////////////////////////////////
1950void AliAstrolab::SetLocalFrame(Double_t t1,Double_t p1,Double_t t2,Double_t p2,Double_t t3,Double_t p3)
1951{
1952// Specification of the orientations of the local-frame axes.
1953// The input arguments represent the angles (in degrees) of the local-frame axes
1954// w.r.t. a so called Master Reference Frame (MRF), with the same convention
f535bc3b 1955// as the input arguments of TRotMatrix::SetAngles.
8bde545d 1956//
1957// The right handed Master Reference Frame is defined as follows :
1958// Z-axis : Points to the local Zenith
1959// X-axis : Makes an angle of 90 degrees with the Z-axis and points South
1960// Y-axis : Makes an angle of 90 degrees with the Z-axis and points East
1961//
1962// Once the user has specified the local reference frame, any observed event
1963// can be related to astronomical space-time locations via the SetSignal
1964// and GetSignal memberfunctions.
1965
1966 // Set the matrix for the conversion of our reference frame coordinates
1967 // into the local-frame ones.
1968
1969 fL.SetAngles(t1,p1,t2,p2,t3,p3);
1970}
1971///////////////////////////////////////////////////////////////////////////
1972Double_t AliAstrolab::ConvertAngle(Double_t a,TString in,TString out) const
1973{
1974// Conversion of various angular formats.
1975//
1976// The input argument "a" denotes the angle to be converted.
1977// The string arguments "in" and "out" specify the angular I/O formats.
1978//
1979// in = "rad" : input angle provided in radians
1980// "deg" : input angle provided in degrees
1981// "dms" : input angle provided in dddmmss.sss
1982// "hms" : input angle provided in hhmmss.sss
b867da20 1983// "hrs" : input angle provided in fractional hours
8bde545d 1984//
1985// out = "rad" : output angle provided in radians
1986// "deg" : output angle provided in degrees
1987// "dms" : output angle provided in dddmmss.sss
1988// "hms" : output angle provided in hhmmss.sss
b867da20 1989// "hrs" : output angle provided in fractional hours
8bde545d 1990
1991 if (in==out) return a;
1992
1993 // Convert input to its absolute value in (fractional) degrees.
1994 Double_t pi=acos(-1.);
1995 Double_t epsilon=1.e-12; // Accuracy in (arc)seconds
1996 Int_t word=0,ddd=0,hh=0,mm=0,ss=0;
1997 Double_t s=0;
1998
1999 Double_t b=fabs(a);
2000
2001 if (in=="rad") b*=180./pi;
2002
b867da20 2003 if (in=="hrs") b*=15.;
2004
8bde545d 2005 if (in=="dms")
2006 {
2007 word=Int_t(b);
2008 ddd=word/10000;
2009 word=word%10000;
2010 mm=word/100;
2011 ss=word%100;
2012 s=b-Double_t(ddd*10000+mm*100+ss);
2013 b=Double_t(ddd)+Double_t(mm)/60.+(Double_t(ss)+s)/3600.;
2014 }
2015
2016 if (in=="hms")
2017 {
2018 word=Int_t(b);
2019 hh=word/10000;
2020 word=word%10000;
2021 mm=word/100;
2022 ss=word%100;
2023 s=b-Double_t(hh*10000+mm*100+ss);
2024 b=15.*(Double_t(hh)+Double_t(mm)/60.+(Double_t(ss)+s)/3600.);
2025 }
2026
2027 while (b>360)
2028 {
2029 b-=360.;
2030 }
2031
2032 if (out=="rad") b*=pi/180.;
2033
b867da20 2034 if (out=="hrs") b/=15.;
2035
8bde545d 2036 if (out=="dms")
2037 {
2038 ddd=Int_t(b);
2039 b=b-Double_t(ddd);
2040 b*=60.;
2041 mm=Int_t(b);
2042 b=b-Double_t(mm);
2043 b*=60.;
2044 ss=Int_t(b);
2045 s=b-Double_t(ss);
2046 if (s>(1.-epsilon))
2047 {
2048 s=0.;
2049 ss++;
2050 }
2051 while (ss>=60)
2052 {
2053 ss-=60;
2054 mm++;
2055 }
2056 while (mm>=60)
2057 {
2058 mm-=60;
2059 ddd++;
2060 }
2061 while (ddd>=360)
2062 {
2063 ddd-=360;
2064 }
2065 b=Double_t(10000*ddd+100*mm+ss)+s;
2066 }
2067
2068 if (out=="hms")
2069 {
2070 b/=15.;
2071 hh=Int_t(b);
2072 b=b-Double_t(hh);
2073 b*=60.;
2074 mm=Int_t(b);
2075 b=b-Double_t(mm);
2076 b*=60.;
2077 ss=Int_t(b);
2078 s=b-Double_t(ss);
2079 if (s>(1.-epsilon))
2080 {
2081 s=0.;
2082 ss++;
2083 }
2084 while (ss>=60)
2085 {
2086 ss-=60;
2087 mm++;
2088 }
2089 while (mm>=60)
2090 {
2091 mm-=60;
2092 hh++;
2093 }
2094 while (hh>=24)
2095 {
2096 hh-=24;
2097 }
2098 b=Double_t(10000*hh+100*mm+ss)+s;
2099 }
2100
2101 if (a<0) b=-b;
2102
2103 return b;
2104}
2105///////////////////////////////////////////////////////////////////////////
2106Double_t AliAstrolab::GetHourAngle(TString mode,AliTimestamp* ts,Int_t jref)
2107{
2108// Provide the Local Hour Angle (in fractional degrees) of a stored signal
2109// object at the specified timestamp.
2110//
2111// The input parameter "mode" allows the user to select either the
2112// "mean" or "apparent" value for the returned Hour Angle.
2113//
2114// mode = "M" --> Output is the Mean Hour Angle
2115// "A" --> Output is the Apparent Hour Angle
2116// ts : Timestamp at which the hour angle is requested.
2117//
2118// The input parameter "jref" allows the user to specify so-called "reference" signals.
2119// These reference signals may be used to check space-time event coincidences with the
661385a7 2120// stored measurement (e.g. coincidence of the measurement with transient phenomena).
8bde545d 2121//
661385a7 2122// jref = 0 --> Use the stored measurement
8bde545d 2123// j --> Use the reference signal at the j-th position (j=1 is first)
2124//
2125// Default value is jref=0.
2126//
2127// Note : In case ts=0 the current timestamp of the lab will be taken.
2128
2129 if (!ts) ts=(AliTimestamp*)this;
2130
2131 // Get corrected right ascension and declination for the specified timestamp.
2132 Double_t a,d;
661385a7 2133 if (mode=="M" || mode=="m") GetSignal(a,d,"M",ts,jref);
2134 if (mode=="A" || mode=="a") GetSignal(a,d,"T",ts,jref);
8bde545d 2135
2136 // Convert coordinates to fractional degrees.
2137 a=ConvertAngle(a,"hms","deg");
2138 d=ConvertAngle(d,"dms","deg");
2139
2140 a/=15.; // Convert a to fractional hours
2141 Double_t ha=0;
2142 if (mode=="M" || mode=="m") ha=ts->GetLMST(fToffset)-a;
2143 if (mode=="A" || mode=="a") ha=ts->GetLAST(fToffset)-a;
2144 ha*=15.; // Convert to (fractional) degrees
2145
2146 return ha;
2147}
2148///////////////////////////////////////////////////////////////////////////
2149void AliAstrolab::SetLT(Int_t y,Int_t m,Int_t d,Int_t hh,Int_t mm,Int_t ss,Int_t ns,Int_t ps)
2150{
2151// Set the AliTimestamp parameters corresponding to the LT date and time
2152// in the Gregorian calendar as specified by the input arguments.
2153//
2154// The input arguments represent the following :
2155// y : year in LT (e.g. 1952, 2003 etc...)
2156// m : month in LT (1=jan 2=feb etc...)
2157// d : day in LT (1-31)
2158// hh : elapsed hours in LT (0-23)
2159// mm : elapsed minutes in LT (0-59)
2160// ss : elapsed seconds in LT (0-59)
2161// ns : remaining fractional elapsed second of LT in nanosecond
2162// ps : remaining fractional elapsed nanosecond of LT in picosecond
2163//
2164// Note : ns=0 and ps=0 are the default values.
2165//
2166
2167 SetLT(fToffset,y,m,d,hh,mm,ss,ns,ps);
2168}
2169///////////////////////////////////////////////////////////////////////////
2170void AliAstrolab::SetLT(Int_t y,Int_t d,Int_t s,Int_t ns,Int_t ps)
2171{
2172// Set the AliTimestamp parameters corresponding to the specified elapsed
2173// timespan since the beginning of the new LT year.
2174//
2175// The LT year and elapsed time span is entered via the following input arguments :
2176//
2177// y : year in LT (e.g. 1952, 2003 etc...)
2178// d : elapsed number of days
2179// s : (remaining) elapsed number of seconds
2180// ns : (remaining) elapsed number of nanoseconds
2181// ps : (remaining) elapsed number of picoseconds
2182//
2183// The specified d, s, ns and ps values will be used in an additive
2184// way to determine the elapsed timespan.
2185// So, specification of d=1, s=100, ns=0, ps=0 will result in the
2186// same elapsed time span as d=0, s=24*3600+100, ns=0, ps=0.
2187// However, by making use of the latter the user should take care
2188// of possible integer overflow problems in the input arguments,
2189// which obviously will provide incorrect results.
2190//
2191// Note : ns=0 and ps=0 are the default values.
2192
2193 SetLT(fToffset,y,d,s,ns,ps);
2194}
2195///////////////////////////////////////////////////////////////////////////
2196Double_t AliAstrolab::GetDifference(Int_t j,TString au,Double_t& dt,TString tu,Int_t mode,Int_t* ia,Int_t* it)
2197{
2198// Provide space and time difference between the j-th reference signal
2199// (j=1 indicates first) and the stored measurement.
2200//
2201// The return value of this memberfunction provides the positional angular
2202// difference, whereas the output argument "dt" provides the time difference.
2203//
2204// The units of the angular difference can be specified via the the "au"
2205// input argument, where
2206//
2207// au = "rad" --> Angular difference in (fractional) radians
2208// "deg" --> Angular difference in (fractional) degrees
2209//
2210// The units of the time difference can be specified via the "tu" and "mode"
2211// input arguments. For details please refer to AliTimestamp::GetDifference().
2212// Also here mode=1 is the default value.
2213//
2214// For the time difference the reference signal is used as the standard.
2215// This means that in case of a positive time difference, the stored
2216// measurement occurred later than the reference signal.
2217//
2218// In case j=0, the stored measurement will be compared with each
2219// reference signal and the returned angular and time differences are
2220// the minimal differences which were encountered.
2221// In this case the user may obtain the indices of the two stored reference signals
2222// which had the minimal angular and minimal time difference via the output
2223// arguments "ia" and "it" as follows :
2224//
2225// ia = Index of the stored reference signal with minimial angular difference
2226// it = Index of the stored reference signal with minimial time difference
2227//
2228// In case these indices are the same, there obviously was 1 single reference signal
2229// which showed both the minimal angular and time difference.
2230//
2231// The default values are mode=1, ia=0 and it=0;
2232
2233 Double_t dang=999;
2234 dt=1.e20;
2235 if (ia) *ia=0;
2236 if (it) *it=0;
2237
2238 if (!fRefs) return dang;
2239
2240 Ali3Vector rx; // Position of the measurement
2241 Ali3Vector r0; // Position of the reference signal
2242
2243 AliSignal* sx=GetSignal(rx,"icr","M",0);
2244 if (!sx) return dang;
2245
2246 AliTimestamp* tx=sx->GetTimestamp();
2247 if (!tx) return dang;
2248
2249 // Space and time difference w.r.t. a specific reference signal
2250 if (j>0)
2251 {
2252 AliSignal* s0=GetSignal(r0,"icr","M",0,j);
2253 if (!s0) return dang;
2254 AliTimestamp* t0=s0->GetTimestamp();
2255
2256 if (!t0) return dang;
2257
2258 dang=r0.GetOpeningAngle(rx,au);
2259 dt=t0->GetDifference(tx,tu,mode);
2260 return dang;
2261 }
2262
2263 // Minimal space and time difference encountered over all reference signals
2264 Double_t dangmin=dang;
2265 Double_t dtmin=dt;
2266 for (Int_t i=1; i<=fRefs->GetSize(); i++)
2267 {
2268 AliSignal* s0=GetSignal(r0,"icr","M",0,i);
2269 if (!s0) continue;
2270 AliTimestamp* t0=s0->GetTimestamp();
2271 if (!t0) continue;
2272 dang=r0.GetOpeningAngle(rx,au);
2273 dt=t0->GetDifference(tx,tu,mode);
2274 if (fabs(dang)<dangmin)
2275 {
2276 dangmin=fabs(dang);
2277 *ia=i;
2278 }
2279 if (fabs(dt)<dtmin)
2280 {
2281 dtmin=fabs(dt);
2282 *it=i;
2283 }
2284 }
2285
2286 dt=dtmin;
2287 return dangmin;
2288}
2289///////////////////////////////////////////////////////////////////////////
2290Double_t AliAstrolab::GetDifference(TString name,TString au,Double_t& dt,TString tu,Int_t mode)
2291{
2292// Provide space and time difference between the reference signal
2293// with the specified name and the stored measurement.
2294//
2295// The return value of this memberfunction provides the positional angular
2296// difference, whereas the output argument "dt" provides the time difference.
2297//
2298// The units of the angular difference can be specified via the the "au"
2299// input argument, where
2300//
2301// au = "rad" --> Angular difference in (fractional) radians
2302// "deg" --> Angular difference in (fractional) degrees
2303//
2304// The units of the time difference can be specified via the "tu" and "mode"
2305// input arguments. For details please refer to AliTimestamp::GetDifference().
2306// Also here mode=1 is the default value.
2307//
2308// For the time difference the reference signal is used as the standard.
2309// This means that in case of a positive time difference, the stored
2310// measurement occurred later than the reference signal.
2311
2312 Double_t dang=999;
2313 dt=1.e20;
2314
2315 Int_t j=GetSignalIndex(name);
2316 if (j>0) dang=GetDifference(j,au,dt,tu,mode);
2317 return dang;
2318}
2319///////////////////////////////////////////////////////////////////////////
2320TArrayI* AliAstrolab::MatchRefSignal(Double_t da,TString au,Double_t dt,TString tu,Int_t mode)
2321{
2322// Provide the storage indices of the reference signals which match in space
2323// and time with the stored measurement.
2324// The indices are returned via a pointer to a TArrayI object.
2325// In case no matches were found, the null pointer is returned.
2326// A reference signal is regarded as matching with the stored measurement
2327// if the positional angular difference doesn't exceed "da" and the absolute
2328// value of the time difference doesn't exceed "dt".
2329//
2330// The units of the angular difference "da" can be specified via the the "au"
2331// input argument, where
2332//
2333// au = "rad" --> Angular difference in (fractional) radians
2334// "deg" --> Angular difference in (fractional) degrees
2335//
2336// The units of the time difference "dt" can be specified via the "tu" and "mode"
2337// input arguments. For details please refer to AliTimestamp::GetDifference().
2338// Also here mode=1 is the default value.
2339
2340 if (!fXsig || !fRefs) return 0;
2341
2342 Int_t nrefs=fRefs->GetEntries();
2343
2344 if (fIndices) delete fIndices;
2345 fIndices=new TArrayI(nrefs);
2346
2347 Double_t dang,dtime;
2348 Int_t jfill=0;
2349 for (Int_t i=1; i<=fRefs->GetSize(); i++)
2350 {
2351 dang=GetDifference(i,au,dtime,tu,mode);
2352 if (fabs(dang)<=da && fabs(dtime)<=dt)
2353 {
2354 fIndices->AddAt(i,jfill);
2355 jfill++;
2356 }
2357 }
2358
2359 fIndices->Set(jfill);
2360 return fIndices;
2361}
2362///////////////////////////////////////////////////////////////////////////
b867da20 2363void AliAstrolab::DisplaySignal(TString frame,TString mode,AliTimestamp* ts,Int_t jref,TString proj,Int_t clr)
2364{
2365// Display a stored signal in a user specified coordinate projection
2366// at the specific timestamp ts.
2367//
2368// In case no stored signal was available or one of the input arguments was
2369// invalid, no display is produced.
2370//
2371// Note : In case ts=0 the current timestamp of the lab will be taken.
2372//
2373// The input parameter "frame" allows the user to specify the frame to which
2374// the coordinates refer. Available options are :
2375//
2376// frame = "equ" ==> Equatorial coordinates with right ascension (a) and declination (d).
2377//
2378// "gal" ==> Galactic coordinates with longitude (l) and latitude (b).
2379//
2380// "ecl" ==> Ecliptic coordinates with longitude (l) and latitude (b).
2381//
2382// "hor" ==> Horizontal azimuth and altitude coordinates at the AliAstrolab location.
2383//
2384// "icr" ==> ICRS coordinates with longitude (l) and latitude (b).
2385//
2386// "loc" ==> Local spherical angles theta and phi at the AliAstrolab location.
2387//
2388// In case the coordinates are the equatorial right ascension and declination (a,d),
2389// they can represent so-called "mean" and "true" values.
2390// The distinction between these two representations is the following :
2391//
2392// mean values : (a,d) are only corrected for precession and not for nutation
2393// true values : (a,d) are corrected for both precession and nutation
2394//
2395// The input parameter "mode" allows the user to specifiy either "mean" or "true"
2396// values for the input in case of equatorial (a,d) coordinates.
2397//
2398// mode = "M" --> Input coordinates are the mean values
2399// "T" --> Input coordinates are the true values
2400//
2401// The input parameter "jref" allows display of a so-called "reference" signal.
2402// These reference signals may serve to check space-time event coincidences with the
2403// stored measurement (e.g. coincidence of the measurement with transient phenomena).
2404//
2405// jref = 0 --> Display of the measurement
2406// j --> Display of the j-th reference signal
2407//
2408// Default value is jref=0.
2409//
2410// The input parameter "proj" allows the user to specify the desired projection.
2411// The available projection modes are :
2412//
2413// cyl : Cylindrical projection plotted with colored markers
2414// cylh : Cylindrical projection plotted in a 2-D histogram
2415// ham : Hammer equal area projection plotted with colored markers
2416// hamh : Hammer equal area projection plotted in a 2-D histogram
2417// ait : Aitoff projection plotted with colored markers
2418// aith : Aitoff projection plotted in a 2-D histogram
2419// mer : Mercator projection plotted with colored markers
2420// merh : Mercator projection plotted in a 2-D histogram
2421// ang : Straight cos(b) vs. l plot with colored markers
2422// angh : Straight cos(b) vs. l plot in a 2-D histogram
2423//
2424// Note : The ang(h) plot allows for easy identification of a homogeneous distribution.
2425//
2426// The input argument "clr" allows to clear (1) the display before drawing or not (0).
2427//
2428// The default values are : jref=0, proj="ham" and clr=0.
2429//
2430// This routine is based on the work by Garmt de Vries-Uiterweerd.
2431
2432 Ali3Vector r;
2433 AliSignal* sx=GetSignal(r,frame,mode,ts,jref);
2434
2435 if (!sx) return;
2436
2437 // The generic input angles (in rad) for the projections
2438 Double_t theta=0;
2439 Double_t phi=0;
2440
2441 Double_t pi=acos(-1.);
2442
2443 if (frame=="equ" || frame=="gal" || frame=="icr" || frame=="ecl" || frame=="loc")
2444 {
2445 theta=(pi/2.)-r.GetX(2,"sph","rad");
2446 phi=r.GetX(3,"sph","rad");
2447 }
2448
2449 if (frame=="hor")
2450 {
2451 theta=(pi/2.)-r.GetX(2,"sph","rad");
2452 phi=pi-r.GetX(3,"sph","rad");
2453 }
2454
2455 // Automatic choice of central meridian if not selected by the user
7f4551ca 2456 if (fMeridian<-pi)
b867da20 2457 {
2458 if (frame=="gal")
2459 {
2460 fMeridian=0;
2461 }
2462 else
2463 {
2464 fMeridian=pi;
2465 }
2466 }
2467
2468 // Obtain the projected (x,y) position
2469 Double_t x=0;
2470 Double_t y=0;
2471 Project(phi,theta,proj,x,y);
2472
2473 Int_t hist=0;
2474 if (proj=="hamh" || proj=="aith" || proj=="merh" || proj=="cylh" || proj=="angh") hist=1;
2475
2476 // Update the display for this signal position
2477
2478 // Create a new canvas if needed
2479 if (!fCanvas) fCanvas=new TCanvas("AliAstrolab","Skymap");
2480
2481 // Construct the title string for this map
2482 TString title="Projection : ";
2483 title+=frame;
2484 title+=" ";
2485 title+=proj;
2486 title+=" Center : ";
2487 Int_t ang,h,m,s,d;
2488 if (frame=="equ" || frame=="icr")
2489 {
2490 ang=int(ConvertAngle(fMeridian,"rad","hms"));
2491 h=ang/10000;
2492 ang=ang%10000;
2493 m=ang/100;
2494 s=ang%100;
2495 title+=h;
2496 title+="h ";
2497 title+=m;
2498 title+="m ";
2499 title+=s;
2500 title+="s";
2501 }
2502 else
2503 {
2504 ang=int(ConvertAngle(fMeridian,"rad","dms"));
2505 d=ang/10000;
2506 ang=ang%10000;
2507 m=ang/100;
2508 s=ang%100;
2509 title+=d;
2510 title+="d ";
2511 title+=m;
2512 title+="' ";
2513 title+=s;
2514 title+="\"";
2515 }
2516
2517 if (!hist) // 2-D Marker display (i.e. not a histogram)
2518 {
2519 // Remove existing markers, grid and outline from display if needed
2520 if (clr==1 || proj!=fProj)
2521 {
2522 if (fMarkers)
2523 {
2524 delete fMarkers;
2525 fMarkers=0;
2526 }
2527 fCanvas->Clear();
2528 fProj=proj;
2529 }
2530
2531 if (!fMarkers)
2532 {
2533 fMarkers=new TObjArray();
2534 fMarkers->SetOwner();
2535 // Set canvas range, header and axes
2536 if (proj=="mer")
2537 {
2538 fCanvas->Range(-2.2,-6.,2.2,6.);
2539 TText* header=new TText;
2540 fMarkers->Add(header);
2541 header->DrawText(-1.4,5.5,title.Data());
2542 TLine* line=new TLine(-2,0,2,0);
2543 fMarkers->Add(line);
2544 line->Draw();
2545 line=new TLine(0,5.5,0,-5.5);
2546 fMarkers->Add(line);
2547 line->Draw();
2548 }
2549 else
2550 {
2551 fCanvas->Range(-2.2,-1.2,2.2,1.2);
2552 TText* header=new TText;
2553 fMarkers->Add(header);
2554 header->DrawText(-1.4,1.1,title.Data());
2555 TLine* line=new TLine(-2,0,2,0);
2556 fMarkers->Add(line);
2557 line->Draw();
2558 line=new TLine(0,1,0,-1);
2559 fMarkers->Add(line);
2560 line->Draw();
2561 }
2562 // Draw the outline
2563 if (proj=="ham" || proj=="ait")
2564 {
2565 // Draw ellips outline with axes
2566 TEllipse* outline=new TEllipse(0,0,2,1);
2567 fMarkers->Add(outline);
2568 outline->Draw();
2569 }
2570 }
2571 TMarker* marker=0;
2572 if (!jref) // The measurement
2573 {
2574 marker=new TMarker(x,y,29);
2575 marker->SetMarkerColor(kRed);
2576 }
2577 else // The reference signal(s)
2578 {
2579 marker=new TMarker(x,y,20);
2580 marker->SetMarkerColor(kBlue);
2581 }
2582 marker->SetMarkerSize(1);
2583 fMarkers->Add(marker);
2584 marker->Draw();
2585 }
2586 else if (hist==1) // 2-D display via histogram
2587 {
2588 // Reset the histogram if needed
2589 if (clr==1 || proj!=fProj)
2590 {
2591 fCanvas->Clear();
2592 if (!fHist) fHist=new TH2F();
2593 fHist->Reset();
2594 fHist->SetMarkerStyle(20);
2595 fHist->SetMarkerSize(1);
2596 fHist->SetMarkerColor(kBlue);
2597 fHist->SetNameTitle("SkyMap",title.Data());
2598 if (proj=="merh")
2599 {
2600 fHist->SetBins(100,-2.2,2.2,100,-5.5,5.5);
2601 }
2602 else
2603 {
2604 fHist->SetBins(100,-2.2,2.2,100,-1.1,1.1);
2605 }
2606 fProj=proj;
2607 }
2608 fHist->Fill(x,y);
2609 fHist->Draw();
2610 }
2611}
2612///////////////////////////////////////////////////////////////////////////
2613void AliAstrolab::DisplaySignal(TString frame,TString mode,AliTimestamp* ts,TString name,TString proj,Int_t clr)
2614{
2615// Display the stored signal with the specified name in a user specified
2616// coordinate projection at the specific timestamp ts.
2617//
2618// Note : In case ts=0 the current timestamp of the lab will be taken.
2619//
2620// In case no such stored signal was available or one of the input arguments was
2621// invalid, no display is produced.
2622//
2623// The input parameter "frame" allows the user to specify the frame to which
2624// the coordinates refer. Available options are :
2625//
2626// frame = "equ" ==> Equatorial coordinates with right ascension (a) and declination (d).
2627//
2628// "gal" ==> Galactic coordinates with longitude (l) and latitude (b).
2629//
2630// "ecl" ==> Ecliptic coordinates with longitude (l) and latitude (b).
2631//
2632// "hor" ==> Horizontal azimuth and altitude coordinates at the AliAstrolab location.
2633//
2634// "icr" ==> ICRS coordinates with longitude (l) and latitude (b).
2635//
2636// "loc" ==> Local spherical angles theta and phi at the AliAstrolab location.
2637//
2638// In case the coordinates are the equatorial right ascension and declination (a,d),
2639// they can represent so-called "mean" and "true" values.
2640// The distinction between these two representations is the following :
2641//
2642// mean values : (a,d) are only corrected for precession and not for nutation
2643// true values : (a,d) are corrected for both precession and nutation
2644//
2645// The input parameter "mode" allows the user to specifiy either "mean" or "true"
2646// values for the input in case of equatorial (a,d) coordinates.
2647//
2648// mode = "M" --> Input coordinates are the mean values
2649// "T" --> Input coordinates are the true values
2650//
2651// The input parameter "proj" allows the user to specify the desired projection.
2652// The available projection modes are :
2653//
2654// cyl : Cylindrical projection plotted with colored markers
2655// cylh : Cylindrical projection plotted in a 2-D histogram
2656// ham : Hammer equal area projection plotted with colored markers
2657// hamh : Hammer equal area projection plotted in a 2-D histogram
2658// ait : Aitoff projection plotted with colored markers
2659// aith : Aitoff projection plotted in a 2-D histogram
2660// mer : Mercator projection plotted with colored markers
2661// merh : Mercator projection plotted in a 2-D histogram
2662// ang : Straight cos(b) vs. l plot with colored markers
2663// angh : Straight cos(b) vs. l plot in a 2-D histogram
2664//
2665// Note : The ang(h) plot allows for easy identification of a homogeneous distribution.
2666//
2667// The input argument "clr" allows to clear (1) the display before drawing or not (0).
2668//
2669// The default values are : proj="ham" and clr=0.
2670//
2671// This routine is based on the work by Garmt de Vries-Uiterweerd.
2672
2673 Int_t j=GetSignalIndex(name);
2674 if (j>=0) DisplaySignal(frame,mode,ts,j,proj,clr);
2675}
2676///////////////////////////////////////////////////////////////////////////
2677void AliAstrolab::DisplaySignals(TString frame,TString mode,AliTimestamp* ts,TString proj,Int_t clr)
2678{
2679// Display of all stored signals in user specified coordinate projection
2680// at the specific timestamp ts.
2681// In case ts=0, the timestamp of the actual recording of the stored measurement
2682// under investigation will be used.
2683// In case no (timestamp of the) actual measurement is available,
2684// the current timestamp of the lab will be taken.
2685// In case no stored signal is available or one of the input arguments is
2686// invalid, no display is produced.
2687//
2688// The input parameter "frame" allows the user to specify the frame to which
2689// the coordinates refer. Available options are :
2690//
2691// frame = "equ" ==> Equatorial coordinates with right ascension (a) and declination (d).
2692//
2693// "gal" ==> Galactic coordinates with longitude (l) and latitude (b).
2694//
2695// "ecl" ==> Ecliptic coordinates with longitude (l) and latitude (b).
2696//
2697// "hor" ==> Horizontal azimuth and altitude coordinates at the AliAstrolab location.
2698//
2699// "icr" ==> ICRS coordinates with longitude (l) and latitude (b).
2700//
2701// "loc" ==> Local spherical angles theta and phi at the AliAstrolab location.
2702//
2703// In case the coordinates are the equatorial right ascension and declination (a,d),
2704// they can represent so-called "mean" and "true" values.
2705// The distinction between these two representations is the following :
2706//
2707// mean values : (a,d) are only corrected for precession and not for nutation
2708// true values : (a,d) are corrected for both precession and nutation
2709//
2710// The input parameter "mode" allows the user to specifiy either "mean" or "true"
2711// values for the input in case of equatorial (a,d) coordinates.
2712//
2713// mode = "M" --> Input coordinates are the mean values
2714// "T" --> Input coordinates are the true values
2715//
2716// The input parameter "proj" allows the user to specify the desired projection.
2717// The available projection modes are :
2718//
2719// cyl : Cylindrical projection plotted with colored markers
2720// cylh : Cylindrical projection plotted in a 2-D histogram
2721// ham : Hammer equal area projection plotted with colored markers
2722// hamh : Hammer equal area projection plotted in a 2-D histogram
2723// ait : Aitoff projection plotted with colored markers
2724// aith : Aitoff projection plotted in a 2-D histogram
2725// mer : Mercator projection plotted with colored markers
2726// merh : Mercator projection plotted in a 2-D histogram
2727// ang : Straight cos(b) vs. l plot with colored markers
2728// angh : Straight cos(b) vs. l plot in a 2-D histogram
2729//
2730// Note : The ang(h) plot allows for easy identification of a homogeneous distribution.
2731//
2732// The input argument "clr" allows to clear (1) the display before drawing or not (0).
2733//
2734// The default values are : proj="ham" and clr=0.
2735//
2736// This routine is based on the work by Garmt de Vries-Uiterweerd.
2737
2738 AliTimestamp* tx=ts;
2739 if (fXsig && !tx) tx=fXsig->GetTimestamp();
2740 if (!tx) tx=(AliTimestamp*)this;
2741
2742 // Display all stored reference signals
2743 if (fRefs)
2744 {
2745 for (Int_t i=1; i<=fRefs->GetSize(); i++)
2746 {
2747 DisplaySignal(frame,mode,tx,i,proj,clr);
2748 clr=0; // No display clear for subsequent signals
2749 }
2750 }
2751
2752 // Display the measurement
2753 DisplaySignal(frame,mode,tx,0,proj,clr);
2754}
2755///////////////////////////////////////////////////////////////////////////
2756void AliAstrolab::SetCentralMeridian(Double_t phi,TString u)
2757{
2758// Set the central meridian for the sky display.
7f4551ca 2759// Setting a value smaller than -pi will induce automatic meridian setting
b867da20 2760// in the display.
2761// By default the central meridian is set at -999 in the constructor.
2762//
2763// The string argument "u" allows to choose between different angular units
2764// u = "rad" : angle provided in radians
2765// "deg" : angle provided in degrees
2766// "dms" : angle provided in dddmmss.sss
2767// "hms" : angle provided in hhmmss.sss
2768//
2769// The default is u="deg".
2770//
2771// This routine is based on the work by Garmt de Vries-Uiterweerd.
2772
2773 fMeridian=ConvertAngle(phi,u,"rad");
2774}
2775///////////////////////////////////////////////////////////////////////////
2776void AliAstrolab::Project(Double_t l,Double_t b,TString proj,Double_t& x,Double_t& y)
2777{
2778// Generic interface for projection of a (long,lat) pair onto a (x,y) pair.
2779//
2780// Meaning of the arguments :
2781// --------------------------
2782// l : Longitude (e.g. right ascension)
2783// b : Latitude (e.g. declination)
2784// proj : Projection mode (e.g. "ham")
2785// x : The resulting x coordinate for the selected projection
2786// y : The resulting x coordinate for the selected projection
2787//
2788// The available projection modes are :
2789//
2790// cyl : Cylindrical projection plotted with colored markers
2791// cylh : Cylindrical projection plotted in a 2-D histogram
2792// ham : Hammer equal area projection plotted with colored markers
2793// hamh : Hammer equal area projection plotted in a 2-D histogram
2794// ait : Aitoff projection plotted with colored markers
2795// aith : Aitoff projection plotted in a 2-D histogram
2796// mer : Mercator projection plotted with colored markers
2797// merh : Mercator projection plotted in a 2-D histogram
2798// ang : Straight cos(b) vs. l plot with colored markers
2799// angh : Straight cos(b) vs. l plot in a 2-D histogram
2800//
2801// Note : The ang(h) plot allows for easy identification of a homogeneous distribution.
2802//
2803// This routine is based on the work by Garmt de Vries-Uiterweerd.
2804
2805 Double_t pi=acos(-1.);
2806
2807 // Subtract central meridian from longitude
2808 l-=fMeridian;
2809
2810 // Take l between -180 and 180 degrees
2811 while (l>pi)
2812 {
2813 l-=2*pi;
2814 }
2815 while (l<-pi)
2816 {
2817 l+=2*pi;
2818 }
2819
2820 x=0;
2821 y=0;
2822
2823 // Convert (l,b) to (x,y) with -2 < x <= 2
2824 if (proj=="cyl" || proj=="cylh") ProjectCylindrical(l,b,x,y);
2825 if (proj=="ham" || proj=="hamh") ProjectHammer(l,b,x,y);
2826 if (proj=="ait" || proj=="aith") ProjectAitoff(l,b,x,y);
2827 if (proj=="mer" || proj=="merh") ProjectMercator(l,b,x,y);
2828 if (proj=="ang" || proj=="angh")
2829 {
2830 x=2*l/pi;
2831 y=cos(b);
2832 }
2833}
2834///////////////////////////////////////////////////////////////////////////
2835void AliAstrolab::ProjectCylindrical(Double_t l,Double_t b,Double_t& x, Double_t& y)
2836{
2837// Cylindrical projection of a (long,lat) coordinate pair
2838//
2839// This routine is based on the work by Garmt de Vries-Uiterweerd.
2840
2841 Double_t pi=acos(-1.);
2842 x=2*l/pi;
2843 y=2*b/pi;
2844}
2845///////////////////////////////////////////////////////////////////////////
2846void AliAstrolab::ProjectHammer(Double_t l,Double_t b,Double_t& x,Double_t& y)
2847{
2848// Hammer-Aitoff projection of a (long,lat) coordinate pair.
2849// This is an equal-area projection.
2850//
2851// This routine is based on the work by Garmt de Vries-Uiterweerd.
2852
2853 Double_t k=1./sqrt(1.+cos(b)*cos(l/2.));
2854 x=2.*k*cos(b)*sin(l/2.);
2855 y=k*sin(b);
2856}
2857///////////////////////////////////////////////////////////////////////////
2858void AliAstrolab::ProjectAitoff(Double_t l,Double_t b,Double_t& x,Double_t& y)
2859{
2860// Aitoff projection of a (long,lat) coordinate pair.
2861//
2862// This routine is based on the work by Garmt de Vries-Uiterweerd.
2863
2864 Double_t pi=acos(-1.);
2865 x=0;
2866 y=0;
2867 Double_t k=acos(cos(b)*cos(l/2.));
2868 if(sin(k)!=0)
2869 {
2870 x=4.*k*cos(b)*sin(l/2.)/(pi*sin(k));
2871 y=2.*k*sin(b)/(pi*sin(k));
2872 }
2873}
2874///////////////////////////////////////////////////////////////////////////
2875void AliAstrolab::ProjectMercator(Double_t l,Double_t b,Double_t& x,Double_t& y)
2876{
2877// Mercator projection of a (long,lat) coordinate pair
2878//
2879// This routine is based on the work by Garmt de Vries-Uiterweerd.
2880
2881 Double_t pi=acos(-1.);
2882 x=2.*l/pi;
2883 y=0;
2884 if (b >= 89.*pi/180.) b=89.*pi/180.;
2885 if (b <= -89.*pi/180.) y=-89.*pi/180.;
2886 if (fabs(y) < 1) y=log((1.+sin(b))/(1.-sin(b)))/2.;
2887}
2888///////////////////////////////////////////////////////////////////////////
8bde545d 2889TObject* AliAstrolab::Clone(const char* name) const
2890{
2891// Make a deep copy of the current object and provide the pointer to the copy.
2892// This memberfunction enables automatic creation of new objects of the
2893// correct type depending on the object type, a feature which may be very useful
2894// for containers when adding objects in case the container owns the objects.
2895
2896 AliAstrolab* lab=new AliAstrolab(*this);
2897 if (name)
2898 {
2899 if (strlen(name)) lab->SetName(name);
2900 }
2901 return lab;
2902}
2903///////////////////////////////////////////////////////////////////////////