source: branches/AddingGoogleTestEnvironment/mgeom/MGeomPix.cc@ 19779

Last change on this file since 19779 was 9863, checked in by tbretz, 14 years ago
Moved MGeomCamDwarf::CalcXY to MGeomPix::CalcXY. Removed some obsolete includes.
File size: 11.3 KB
Line 
1/* ======================================================================== *\
2!
3! *
4! * This file is part of CheObs, the Modular Analysis and Reconstruction
5! * Software. It is distributed to you in the hope that it can be a useful
6! * and timesaving tool in analysing Data of imaging Cerenkov telescopes.
7! * It is distributed WITHOUT ANY WARRANTY.
8! *
9! * Permission to use, copy, modify and distribute this software and its
10! * documentation for any purpose is hereby granted without fee,
11! * provided that the above copyright notice appears in all copies and
12! * that both that copyright notice and this permission notice appear
13! * in supporting documentation. It is provided "as is" without express
14! * or implied warranty.
15! *
16!
17!
18! Author(s): Thomas Bretz, 12/2000 <mailto:tbretz@astro.uni-wuerzburg.de>
19!
20! Copyright: MAGIC Software Development, 2000-2009
21!
22!
23\* ======================================================================== */
24
25//////////////////////////////////////////////////////////////////////////////
26//
27// MGeomPix
28//
29// This container stores the geometry (position) information of
30// a single pixel together with the information about next neighbors.
31//
32//
33// Version 1:
34// ----------
35// - first implementation
36//
37// Version 2:
38// ----------
39// - added fA
40//
41// Version 3:
42// ----------
43// - added fAidx
44//
45// Version 4:
46// ----------
47// - added fUserBits
48//
49// Version 5:
50// ----------
51// - now derives from MGeom to which some data members have been moved
52//
53////////////////////////////////////////////////////////////////////////////
54#include "MGeomPix.h"
55
56#include <TMath.h>
57#include <TVector2.h>
58#include <TVirtualPad.h>
59
60#include "MLog.h"
61#include "MLogManip.h"
62
63#include "MGeomCam.h"
64#include "MHexagon.h"
65
66ClassImp(MGeomPix);
67
68using namespace std;
69
70const Float_t MGeomPix::gsTan30 = TMath::Sqrt(3)/3; //TMath::Tan(TMath::DegToRad()*30);
71const Float_t MGeomPix::gsTan60 = TMath::Sqrt(3); //TMath::Tan(TMath::DegToRad()*60);
72
73const Float_t MGeomPix::gsCos60 = 0.5; //TMath::Cos(TMath::DegToRad()*60);
74const Float_t MGeomPix::gsSin60 = TMath::Sqrt(3)/2; //TMath::Sin(TMath::DegToRad()*60);
75
76// --------------------------------------------------------------------------
77//
78// Initializes one pixel
79//
80MGeomPix::MGeomPix(Float_t x, Float_t y, Float_t r, UInt_t s, UInt_t a)
81 : MGeom(x, y, s, a), fCosPhi(1), fSinPhi(0)
82{
83 SetD(r);
84 SetNeighbors();
85}
86
87void MGeomPix::SetPhi(Double_t phi)
88{
89 fCosPhi = TMath::Cos(phi);
90 fSinPhi = TMath::Sin(phi);
91}
92
93// --------------------------------------------------------------------------
94//
95// Print the geometry information of one pixel.
96//
97void MGeomPix::Print(Option_t *opt) const
98{
99 MGeom::Print(opt);
100 gLog << " d=" << fD << "mm" << endl;
101}
102
103// ------------------------------------------------------------------------
104//
105// Implementation of PaintPrimitive drwaing a hexagonal pixel
106//
107void MGeomPix::PaintPrimitive(const TAttLine &line, const TAttFill &fill, Double_t scalexy, Double_t scaled) const
108{
109 const_cast<TAttLine&>(line).Modify(); //Change line attributes only if necessary
110 const_cast<TAttFill&>(fill).Modify(); //Change fill area attributes only if necessary
111
112 const Double_t fx = fX*scalexy;
113 const Double_t fy = fY*scalexy;
114 const Double_t fd = fD*scaled;
115
116 const Double_t c = fd*fCosPhi;
117 const Double_t s = fd*fSinPhi;
118
119 const Double_t gsCos60c = gsCos60*c;
120 const Double_t gsCos60s = gsCos60*s;
121
122 const Double_t gsSin60c = gsSin60*c/3;
123 const Double_t gsSin60s = gsSin60*s/3;
124
125 const Double_t gsTan30c = gsTan30*c;
126 const Double_t gsTan30s = gsTan30*s;
127
128
129 Double_t x[7] = {
130 gsCos60c-gsSin60s, -gsTan30s, -gsCos60c-gsSin60s,
131 -gsCos60c+gsSin60s, gsTan30s, gsCos60c+gsSin60s
132 };
133
134 Double_t y[7] = {
135 gsCos60s+gsSin60c, gsTan30c, -gsCos60s+gsSin60c,
136 -gsCos60s-gsSin60c, -gsTan30c, gsCos60s-gsSin60c,
137 };
138
139 for (Int_t i=0; i<6; i++)
140 {
141 // FIXME: Do not rotate fX/fY.
142 // Instead implement MGeomCam::Rotate or similar.
143 x[i] += fx;
144 y[i] += fy;
145 }
146
147 x[6] = x[0];
148 y[6] = y[0];
149
150 //
151 // paint the pixel
152 //
153 if (fill.GetFillColor())
154 gPad->PaintFillArea(6, x, y);
155
156 if (line.GetLineStyle())
157 gPad->PaintPolyLine(7, x, y);
158}
159
160// ------------------------------------------------------------------------
161//
162// compute the distance of a point (px,py) to the Hexagon center in
163// MGeomPix coordinates. Return kTRUE if inside.
164//
165Bool_t MGeomPix::IsInside(Float_t px, Float_t py) const
166{
167
168 //const Double_t disthex = 999999;//TMath::Sqrt(dx*dx + dy*dy);
169
170 const Double_t dh = fD/2;
171
172 //
173 // compute the distance of the Point to the center of the Hexagon
174 //
175 const Double_t dx = px-fX;
176 const Double_t dy = py-fY;
177
178 // FIXME: Derotate
179
180 // DX = dx*cos(-phi) - dy*sin(-phi)
181 // DY = dx*sin(-phi) + dy*cos(-phi)
182
183 const Double_t x = dx*fCosPhi + dy*fSinPhi;
184
185 if (TMath::Abs(x) > dh)
186 return kFALSE; // return disthex
187
188 const Double_t y = -dx*fSinPhi + dy*fCosPhi;
189
190 const Double_t xc = x*gsCos60; // 1/2
191 const Double_t ys = y*gsSin60; // sqrt(3)/2
192
193 //
194 // Now check if point is outside of hexagon; just check x coordinate
195 // in three coordinate systems: the default one, in which two sides of
196 // the hexagon are paralel to the y axis (see camera displays) and two
197 // more, rotated with respect to that one by +- 60 degrees.
198 //
199
200 if (TMath::Abs(xc + ys) > dh)
201 return kFALSE; // return disthex
202
203 if (TMath::Abs(xc - ys) > dh)
204 return kFALSE; // return disthex
205
206 return kTRUE; // return -1
207
208
209}
210
211// --------------------------------------------------------------------------
212//
213// Calculate in the direction 0-5 (kind of sector) in the ring-th ring
214// the x and y coordinate of the i-th pixel. The unitx are unity,
215// distance to (0,0) is retruned.
216//
217Double_t MGeomPix::CalcXY(Int_t dir, Int_t ring, Int_t i, Double_t &x, Double_t &y)
218{
219 switch (dir)
220 {
221 case kDirCenter: // Center
222 x = 0;
223 y = 0;
224 break;
225
226 case kDirNE: // Direction North East
227 x = ring-i*0.5;
228 y = i*gsSin60;
229 break;
230
231 case kDirN: // Direction North
232 x = ring*0.5-i;
233 y = ring*gsSin60;
234 break;
235
236 case kDirNW: // Direction North West
237 x = -(ring+i)*0.5;
238 y = (ring-i)*gsSin60;
239 break;
240
241 case kDirSW: // Direction South West
242 x = 0.5*i-ring;
243 y = -i*gsSin60;
244 break;
245
246 case kDirS: // Direction South
247 x = i-ring*0.5;
248 y = -ring*gsSin60;
249 break;
250
251 case kDirSE: // Direction South East
252 x = (ring+i)*0.5;
253 y = (-ring+i)*gsSin60;
254 break;
255 }
256 return x*x + y*y;
257}
258
259// ==============================================================================
260/*
261#include <TOrdCollection.h>
262#include "MMath.h"
263#include "../mgui/MHexagon.h" // MHexagon::fgDx
264
265// ------------------------------------------------------------------------
266//
267// Small helper class to allow fast sorting of TVector2 by angle
268//
269class HVector2 : public TVector2
270{
271 Double_t fAngle;
272public:
273 HVector2() : TVector2() { }
274 HVector2(const TVector2 &v) : TVector2(v) { }
275 HVector2(Double_t x, Double_t y) : TVector2 (x, y) { }
276 void CalcAngle() { fAngle = Phi(); }
277 Bool_t IsSortable() const { return kTRUE; }
278 Int_t Compare(const TObject *obj) const { return ((HVector2*)obj)->fAngle>fAngle ? 1 : -1; }
279 Double_t GetAngle() const { return fAngle; }
280};
281
282// ------------------------------------------------------------------------
283//
284// Calculate the edge points of the intersection area of two hexagons.
285// The points are added as TVector2 to the TOrdCollection.
286// The user is responsible of delete the objects.
287//
288void MGeomPix::GetIntersectionBorder(TOrdCollection &col, const MGeomPix &hex) const
289{
290// if (fPhi!=0)
291// {
292// gLog << warn << "MGeomPix::GetIntersectionBorder: Only phi=0 supported yet." << endl;
293// return;
294// }
295
296 Bool_t inside0[6], inside1[6];
297
298 HVector2 v0[6];
299 HVector2 v1[6];
300
301 Int_t cnt0=0;
302 Int_t cnt1=0;
303
304 // Calculate teh edges of each hexagon and whether this edge
305 // is inside the other hexgon or not
306 for (int i=0; i<6; i++)
307 {
308 const Double_t x0 = fX+MHexagon::fgDx[i]*fD;
309 const Double_t y0 = fY+MHexagon::fgDy[i]*fD;
310
311 const Double_t x1 = hex.fX+MHexagon::fgDx[i]*hex.fD;
312 const Double_t y1 = hex.fY+MHexagon::fgDy[i]*hex.fD;
313
314 v0[i].Set(x0, y0);
315 v1[i].Set(x1, y1);
316
317 inside0[i] = hex.DistanceToPrimitive(x0, y0) < 0;
318 inside1[i] = DistanceToPrimitive(x1, y1) < 0;
319
320 if (inside0[i])
321 {
322 col.Add(new HVector2(v0[i]));
323 cnt0++;
324 }
325 if (inside1[i])
326 {
327 col.Add(new HVector2(v1[i]));
328 cnt1++;
329 }
330 }
331
332 if (cnt0==0 || cnt1==0)
333 return;
334
335 // No calculate which vorder lines intersect
336 Bool_t iscross0[6], iscross1[6];
337 for (int i=0; i<6; i++)
338 {
339 iscross0[i] = (inside0[i] && !inside0[(i+1)%6]) || (!inside0[i] && inside0[(i+1)%6]);
340 iscross1[i] = (inside1[i] && !inside1[(i+1)%6]) || (!inside1[i] && inside1[(i+1)%6]);
341 }
342
343 // Calculate the border points of our intersection area
344 for (int i=0; i<6; i++)
345 {
346 // Skip non intersecting lines
347 if (!iscross0[i])
348 continue;
349
350 for (int j=0; j<6; j++)
351 {
352 // Skip non intersecting lines
353 if (!iscross1[j])
354 continue;
355
356 const TVector2 p = MMath::GetIntersectionPoint(v0[i], v0[(i+1)%6], v1[j], v1[(j+1)%6]);
357 if (hex.DistanceToPrimitive(p.X(), p.Y())<1e-9)
358 col.Add(new HVector2(p));
359 }
360 }
361}
362
363// ------------------------------------------------------------------------
364//
365// Calculate the overlapping area of the two hexagons.
366//
367Double_t MGeomPix::CalcOverlapArea(const MGeomPix &cam) const
368{
369// if (fPhi!=0)
370// {
371// gLog << warn << "MGeomPix::CalcOverlapArea: Only phi=0 supported yet." << endl;
372// return -1;
373// }
374
375 TOrdCollection col;
376 col.SetOwner();
377
378 GetIntersectionBorder(col, cam);
379
380 // Check if there is an intersection to proceed with
381 const Int_t n = col.GetEntries();
382 if (n==0)
383 return 0;
384
385 // Calculate the center of gravity
386 TVector2 cog;
387
388 TIter Next(&col);
389 HVector2 *v=0;
390 while ((v=(HVector2*)Next()))
391 cog += *v;
392 cog /= n;
393
394 // Shift the figure to its center-og-gravity and
395 // calculate the angle of the connection line between the
396 // border points of our intersesction area and its cog
397 Next.Reset();
398 while ((v=(HVector2*)Next()))
399 {
400 *v -= cog;
401 v->CalcAngle();
402 }
403
404 // Sort these points by this angle
405 col.Sort();
406
407 // Now sum up the area of all the triangles between two
408 // following points and the cog.
409 Double_t A = 0;
410 for (int i=0; i<n; i++)
411 {
412 // Vectors from cog to two nearby border points
413 const HVector2 *v1 = (HVector2*)col.At(i);
414 const HVector2 *v2 = (HVector2*)col.At((i+1)%n);
415
416 // Angle between both vectors
417 const Double_t a = fmod(v1->GetAngle()-v2->GetAngle()+TMath::TwoPi(), TMath::TwoPi());
418
419 // Length of both vectors
420 const Double_t d1 = v1->Mod();
421 const Double_t d2 = v2->Mod();
422
423 A += d1*d2/2*sin(a);
424 }
425 return A;
426}
427*/
Note: See TracBrowser for help on using the repository browser.