ECCE @ EIC Software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
G4TheRayTracer.cc
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file G4TheRayTracer.cc
1 //
2 // ********************************************************************
3 // * License and Disclaimer *
4 // * *
5 // * The Geant4 software is copyright of the Copyright Holders of *
6 // * the Geant4 Collaboration. It is provided under the terms and *
7 // * conditions of the Geant4 Software License, included in the file *
8 // * LICENSE and available at http://cern.ch/geant4/license . These *
9 // * include a list of copyright holders. *
10 // * *
11 // * Neither the authors of this software system, nor their employing *
12 // * institutes,nor the agencies providing financial support for this *
13 // * work make any representation or warranty, express or implied, *
14 // * regarding this software system or assume any liability for its *
15 // * use. Please see the license in the file LICENSE and URL above *
16 // * for the full disclaimer and the limitation of liability. *
17 // * *
18 // * This code implementation is the result of the scientific and *
19 // * technical work of the GEANT4 collaboration. *
20 // * By using, copying, modifying or distributing the software (or *
21 // * any work based on the software) you agree to acknowledge its *
22 // * use in resulting scientific publications, and indicate your *
23 // * acceptance of all terms of the Geant4 Software license. *
24 // ********************************************************************
25 //
26 //
27 //
28 //
29 //
30 
31 
32 #include "G4TheRayTracer.hh"
33 #include "G4SystemOfUnits.hh"
34 #include "G4EventManager.hh"
35 #include "G4RTMessenger.hh"
36 #include "G4RayShooter.hh"
37 #include "G4VFigureFileMaker.hh"
38 #include "G4RTTrackingAction.hh"
39 #include "G4RTSteppingAction.hh"
40 #include "G4RayTrajectory.hh"
41 #include "G4RayTrajectoryPoint.hh"
42 #include "G4RTJpegMaker.hh"
43 #include "G4RTSimpleScanner.hh"
44 #include "G4GeometryManager.hh"
45 #include "G4SDManager.hh"
46 #include "G4StateManager.hh"
47 #include "G4Event.hh"
48 #include "G4TrajectoryContainer.hh"
49 #include "G4Colour.hh"
50 #include "G4VisAttributes.hh"
51 #include "G4UImanager.hh"
53 #include "G4RegionStore.hh"
54 #include "G4ProductionCutsTable.hh"
55 #include "G4VVisManager.hh"
56 
58  G4VRTScanner* scanner)
59 {
60  theFigMaker = figMaker;
62  theScanner = scanner;
73  colorR = 0;
74  colorG = 0;
75  colorB = 0;
76 
79 
80  nColumn = 640;
81  nRow = 640;
82 
83  eyePosition = G4ThreeVector(1.*m,1.*m,1.*m);
84  targetPosition = G4ThreeVector(0.,0.,0.);
85  lightDirection = G4ThreeVector(-0.1,-0.2,-0.3).unit();
86  up = G4ThreeVector(0,1,0);
87  viewSpan = 5.0*deg;
88  headAngle = 0.;
89  attenuationLength = 1.0*m;
90 
91  distortionOn = false;
92  antialiasingOn = false;
93 
94  backgroundColour = G4Colour(1.,1.,1.);
95 }
96 
98 {
99  delete theRayShooter;
102  delete theMessenger;
103  delete theScanner;
104  delete theFigMaker;
105 }
106 
107 void G4TheRayTracer::Trace(const G4String& fileName)
108 {
110  G4ApplicationState currentState = theStateMan->GetCurrentState();
111  if(currentState!=G4State_Idle)
112  {
113  G4cerr << "Illegal application state - Trace() ignored." << G4endl;
114  return;
115  }
116 
117  if(!theFigMaker)
118  {
119  G4cerr << "Figure file maker class is not specified - Trace() ignored." << G4endl;
120  return;
121  }
122 
124  G4int storeTrajectory = UI->GetCurrentIntValue("/tracking/storeTrajectory");
125  if(storeTrajectory==0) UI->ApplyCommand("/tracking/storeTrajectory 1");
126 
127 
129  eyeDirection = tmpVec.unit();
130  colorR = new unsigned char[nColumn*nRow];
131  colorG = new unsigned char[nColumn*nRow];
132  colorB = new unsigned char[nColumn*nRow];
133 
135  G4bool succeeded = CreateBitMap();
136  if(succeeded)
137  { CreateFigureFile(fileName); }
138  else
139  { G4cerr << "Could not create figure file" << G4endl;
140  G4cerr << "You might set the eye position outside of the world volume" << G4endl; }
142 
143  if(storeTrajectory==0) UI->ApplyCommand("/tracking/storeTrajectory 0");
144 
145  delete [] colorR;
146  delete [] colorG;
147  delete [] colorB;
148 }
149 
151 {
156 
159 
164 
166  if(theSDMan)
167  { theSDMan->Activate("/",false); }
168 
170  theGeomMan->OpenGeometry();
171  theGeomMan->CloseGeometry(true);
172 }
173 
175 {
180 
182  if(theSDMan)
183  { theSDMan->Activate("/",true); }
184 }
185 
186 #include "G4ProcessManager.hh"
187 #include "G4ProcessVector.hh"
188 #include "G4Geantino.hh"
189 
191 {
192  G4int iEvent = 0;
193  G4double stepAngle = viewSpan/100.;
194  G4double viewSpanX = stepAngle*nColumn;
195  G4double viewSpanY = stepAngle*nRow;
196  G4bool succeeded;
197 
199  visMan->IgnoreStateChanges(true);
200 
201 // Confirm process(es) of Geantino is initialized
202  G4VPhysicalVolume* pWorld =
204  GetNavigatorForTracking()->GetWorldVolume();
207  G4ProcessVector* pVector
209  for (std::size_t j=0; j < pVector->size(); ++j) {
210  (*pVector)[j]->BuildPhysicsTable(*(G4Geantino::GeantinoDefinition()));
211  }
212 
213 // Close geometry and set the application state
215  geomManager->OpenGeometry();
216  geomManager->CloseGeometry(1,0);
217 
218  G4ThreeVector center(0,0,0);
221  navigator->LocateGlobalPointAndSetup(center,0,false);
222 
224  theStateMan->SetNewState(G4State_GeomClosed);
225 
226 // Event loop
227  theScanner->Initialize(nRow,nColumn);
228  G4int iRow, iColumn;
229  while (theScanner->Coords(iRow,iColumn)) {
230  G4int iCoord = iRow * nColumn + iColumn;
231  G4double dRow = 0, dColumn = 0; // Antialiasing increments.
232  G4Event* anEvent = new G4Event(iEvent++);
233  G4double angleX = -(viewSpanX/2. - (iColumn+dColumn)*stepAngle);
234  G4double angleY = viewSpanY/2. - (iRow+dRow)*stepAngle;
235  G4ThreeVector rayDirection;
236  if(distortionOn)
237  {
238  rayDirection = G4ThreeVector(-std::tan(angleX)/std::cos(angleY),std::tan(angleY)/std::cos(angleX),1.0);
239  }
240  else
241  {
242  rayDirection = G4ThreeVector(-std::tan(angleX),std::tan(angleY),1.0);
243  }
244  G4double cp = std::cos(eyeDirection.phi());
245  G4double sp = std::sqrt(1.-cp*cp);
246  G4double ct = std::cos(eyeDirection.theta());
247  G4double st = std::sqrt(1.-ct*ct);
248  G4double gamma = std::atan2(ct*cp*up.x()+ct*sp*up.y()-st*up.z(), -sp*up.x()+cp*up.y());
249  rayDirection.rotateZ(-gamma);
250  rayDirection.rotateZ(headAngle);
251  rayDirection.rotateUz(eyeDirection);
252  G4ThreeVector rayPosition(eyePosition);
253  G4bool interceptable = true;
254  // Check if rayPosition is in the world.
255  EInside whereisit =
256  pWorld->GetLogicalVolume()->GetSolid()->Inside(rayPosition);
257  if (whereisit != kInside) {
258  // It's outside the world, so move it inside.
259  G4double outsideDistance =
260  pWorld->GetLogicalVolume()->GetSolid()->
261  DistanceToIn(rayPosition,rayDirection);
262  if (outsideDistance != kInfinity) {
263  // Borrowing from geometry, where 1e-8 < epsilon < 1e-3, in
264  // absolute/internal length units, is used for ensuring good
265  // behaviour, choose to add 0.001 to ensure rayPosition is
266  // definitely inside the world volume (JA 16/9/2005)...
267  rayPosition = rayPosition+(outsideDistance+0.001)*rayDirection;
268  }
269  else {
270  interceptable = false;
271  }
272  }
273  if (interceptable) {
274  theRayShooter->Shoot(anEvent,rayPosition,rayDirection.unit());
276  succeeded = GenerateColour(anEvent);
277  colorR[iCoord] = (unsigned char)(G4int(255*rayColour.GetRed()));
278  colorG[iCoord] = (unsigned char)(G4int(255*rayColour.GetGreen()));
279  colorB[iCoord] = (unsigned char)(G4int(255*rayColour.GetBlue()));
280  } else { // Ray does not intercept world at all.
281  // Store background colour...
282  colorR[iCoord] = (unsigned char)(G4int(255*backgroundColour.GetRed()));
283  colorG[iCoord] = (unsigned char)(G4int(255*backgroundColour.GetGreen()));
284  colorB[iCoord] = (unsigned char)(G4int(255*backgroundColour.GetBlue()));
285  succeeded = true;
286  }
287 
288  theScanner->Draw(colorR[iCoord],colorG[iCoord],colorB[iCoord]);
289 
290  delete anEvent;
291  if(!succeeded) return false;
292  }
293 
294  theStateMan->SetNewState(G4State_Idle);
295  visMan->IgnoreStateChanges(false);
296  return true;
297 }
298 
300 {
301  //G4cout << nColumn << " " << nRow << G4endl;
303 }
304 
306 {
307  G4TrajectoryContainer * trajectoryContainer = anEvent->GetTrajectoryContainer();
308 
309  G4RayTrajectory* trajectory = (G4RayTrajectory*)( (*trajectoryContainer)[0] );
310  if(!trajectory) return false;
311 
312  G4int nPoint = trajectory->GetPointEntries();
313  if(nPoint==0) return false;
314 
315  G4Colour initialColour(backgroundColour);
316  if( trajectory->GetPointC(nPoint-1)->GetPostStepAtt() )
317  { initialColour = GetSurfaceColour(trajectory->GetPointC(nPoint-1)); }
318  rayColour = Attenuate(trajectory->GetPointC(nPoint-1),initialColour);
319 
320  for(G4int i=nPoint-2;i>=0;--i)
321  {
322  G4Colour surfaceColour = GetSurfaceColour(trajectory->GetPointC(i));
323  G4double weight = 1.0 - surfaceColour.GetAlpha();
324  G4Colour mixedColour = GetMixedColour(rayColour,surfaceColour,weight);
325  rayColour = Attenuate(trajectory->GetPointC(i),mixedColour);
326  }
327 
328  return true;
329 }
330 
332 (const G4Colour& surfCol,const G4Colour& transCol,G4double weight)
333 {
334  G4double red = weight*surfCol.GetRed() + (1.-weight)*transCol.GetRed();
335  G4double green = weight*surfCol.GetGreen() + (1.-weight)*transCol.GetGreen();
336  G4double blue = weight*surfCol.GetBlue() + (1.-weight)*transCol.GetBlue();
337  G4double alpha = weight*surfCol.GetAlpha() + (1.-weight)*transCol.GetAlpha();
338  return G4Colour(red,green,blue,alpha);
339 }
340 
342 {
343  const G4VisAttributes* preAtt = point->GetPreStepAtt();
344  const G4VisAttributes* postAtt = point->GetPostStepAtt();
345 
346  G4bool preVis = ValidColour(preAtt);
347  G4bool postVis = ValidColour(postAtt);
348 
349  G4Colour transparent(1.,1.,1.,0.);
350 
351  if(!preVis&&!postVis) return transparent;
352 
354 
355  G4Colour preCol(1.,1.,1.);
356  G4Colour postCol(1.,1.,1.);
357 
358  if(preVis)
359  {
360  const G4Colour& preAttColour = preAtt->GetColour();
361  G4double brill = (1.0-(-lightDirection).dot(normal))/2.0;
362  G4double red = preAttColour.GetRed();
363  G4double green = preAttColour.GetGreen();
364  G4double blue = preAttColour.GetBlue();
365  preCol = G4Colour
366  (red*brill,green*brill,blue*brill,preAttColour.GetAlpha());
367  }
368  else
369  { preCol = transparent; }
370 
371  if(postVis)
372  {
373  const G4Colour& postAttColour = postAtt->GetColour();
374  G4double brill = (1.0-(-lightDirection).dot(-normal))/2.0;
375  G4double red = postAttColour.GetRed();
376  G4double green = postAttColour.GetGreen();
377  G4double blue = postAttColour.GetBlue();
378  postCol = G4Colour
379  (red*brill,green*brill,blue*brill,postAttColour.GetAlpha());
380  }
381  else
382  { postCol = transparent; }
383 
384  if(!preVis) return postCol;
385  if(!postVis) return preCol;
386 
387  G4double weight = 0.5;
388  return GetMixedColour(preCol,postCol,weight);
389 }
390 
393 {
394  const G4VisAttributes* preAtt = point->GetPreStepAtt();
395 
396  G4bool visible = ValidColour(preAtt);
397  if(!visible) return sourceCol;
398 
399  G4Colour objCol = preAtt->GetColour();
400  G4double stepRed = objCol.GetRed();
401  G4double stepGreen = objCol.GetGreen();
402  G4double stepBlue = objCol.GetBlue();
403  G4double stepAlpha = objCol.GetAlpha();
404  G4double stepLength = point->GetStepLength();
405 
406  G4double attenuationFuctor;
407  if(stepAlpha > 0.9999999){ stepAlpha = 0.9999999; } // patch to the next line
408  attenuationFuctor = -stepAlpha/(1.0-stepAlpha)*stepLength/attenuationLength;
409 
410  G4double KtRed = std::exp((1.0-stepRed)*attenuationFuctor);
411  G4double KtGreen = std::exp((1.0-stepGreen)*attenuationFuctor);
412  G4double KtBlue = std::exp((1.0-stepBlue)*attenuationFuctor);
413  if(KtRed>1.0){KtRed=1.0;}
414  if(KtGreen>1.0){KtGreen=1.0;}
415  if(KtBlue>1.0){KtBlue=1.0;}
416  return G4Colour(sourceCol.GetRed()*KtRed,
417  sourceCol.GetGreen()*KtGreen,sourceCol.GetBlue()*KtBlue);
418 }
419 
421 {
422  G4bool val = true;
423  if(!visAtt)
424  { val = false; }
425  else if(!(visAtt->IsVisible()))
426  { val = false; }
427  else if(visAtt->IsForceDrawingStyle()
429  { val = false; }
430  return val;
431 }
432