Geant4 11.2.2
Toolkit for the simulation of the passage of particles through matter
Loading...
Searching...
No Matches
G4TwistTrapParallelSide Class Reference

#include <G4TwistTrapParallelSide.hh>

+ Inheritance diagram for G4TwistTrapParallelSide:

Public Member Functions

 G4TwistTrapParallelSide (const G4String &name, G4double PhiTwist, G4double pDz, G4double pTheta, G4double pPhi, G4double pDy1, G4double pDx1, G4double pDx2, G4double pDy2, G4double pDx3, G4double pDx4, G4double pAlph, G4double AngleSide)
 
 ~G4TwistTrapParallelSide () override
 
G4ThreeVector GetNormal (const G4ThreeVector &xx, G4bool isGlobal=false) override
 
G4int DistanceToSurface (const G4ThreeVector &gp, const G4ThreeVector &gv, G4ThreeVector gxx[], G4double distance[], G4int areacode[], G4bool isvalid[], EValidate validate=kValidateWithTol) override
 
G4int DistanceToSurface (const G4ThreeVector &gp, G4ThreeVector gxx[], G4double distance[], G4int areacode[]) override
 
 G4TwistTrapParallelSide (__void__ &)
 
- Public Member Functions inherited from G4VTwistSurface
 G4VTwistSurface (const G4String &name)
 
 G4VTwistSurface (const G4String &name, const G4RotationMatrix &rot, const G4ThreeVector &tlate, G4int handedness, const EAxis axis1, const EAxis axis2, G4double axis0min=-kInfinity, G4double axis1min=-kInfinity, G4double axis0max=kInfinity, G4double axis1max=kInfinity)
 
virtual ~G4VTwistSurface ()
 
virtual G4int AmIOnLeftSide (const G4ThreeVector &me, const G4ThreeVector &vec, G4bool withTol=true)
 
virtual G4double DistanceToBoundary (G4int areacode, G4ThreeVector &xx, const G4ThreeVector &p)
 
virtual G4double DistanceToIn (const G4ThreeVector &gp, const G4ThreeVector &gv, G4ThreeVector &gxxbest)
 
virtual G4double DistanceToOut (const G4ThreeVector &gp, const G4ThreeVector &gv, G4ThreeVector &gxxbest)
 
virtual G4double DistanceTo (const G4ThreeVector &gp, G4ThreeVector &gxx)
 
void DebugPrint () const
 
virtual G4String GetName () const
 
virtual void GetBoundaryParameters (const G4int &areacode, G4ThreeVector &d, G4ThreeVector &x0, G4int &boundarytype) const
 
virtual G4ThreeVector GetBoundaryAtPZ (G4int areacode, const G4ThreeVector &p) const
 
G4double DistanceToPlaneWithV (const G4ThreeVector &p, const G4ThreeVector &v, const G4ThreeVector &x0, const G4ThreeVector &n0, G4ThreeVector &xx)
 
G4double DistanceToPlane (const G4ThreeVector &p, const G4ThreeVector &x0, const G4ThreeVector &n0, G4ThreeVector &xx)
 
G4double DistanceToPlane (const G4ThreeVector &p, const G4ThreeVector &x0, const G4ThreeVector &t1, const G4ThreeVector &t2, G4ThreeVector &xx, G4ThreeVector &n)
 
G4double DistanceToLine (const G4ThreeVector &p, const G4ThreeVector &x0, const G4ThreeVector &d, G4ThreeVector &xx)
 
G4bool IsAxis0 (G4int areacode) const
 
G4bool IsAxis1 (G4int areacode) const
 
G4bool IsOutside (G4int areacode) const
 
G4bool IsInside (G4int areacode, G4bool testbitmode=false) const
 
G4bool IsBoundary (G4int areacode, G4bool testbitmode=false) const
 
G4bool IsCorner (G4int areacode, G4bool testbitmode=false) const
 
G4bool IsValidNorm () const
 
G4bool IsSameBoundary (G4VTwistSurface *surface1, G4int areacode1, G4VTwistSurface *surface2, G4int areacode2) const
 
G4int GetAxisType (G4int areacode, G4int whichaxis) const
 
G4ThreeVector ComputeGlobalPoint (const G4ThreeVector &lp) const
 
G4ThreeVector ComputeLocalPoint (const G4ThreeVector &gp) const
 
G4ThreeVector ComputeGlobalDirection (const G4ThreeVector &lp) const
 
G4ThreeVector ComputeLocalDirection (const G4ThreeVector &gp) const
 
void SetAxis (G4int i, const EAxis axis)
 
void SetNeighbours (G4VTwistSurface *ax0min, G4VTwistSurface *ax1min, G4VTwistSurface *ax0max, G4VTwistSurface *ax1max)
 
G4int GetNode (G4int i, G4int j, G4int m, G4int n, G4int iside)
 
G4int GetFace (G4int i, G4int j, G4int m, G4int n, G4int iside)
 
G4int GetEdgeVisibility (G4int i, G4int j, G4int m, G4int n, G4int number, G4int orientation)
 
 G4VTwistSurface (__void__ &)
 

Additional Inherited Members

- Public Types inherited from G4VTwistSurface
enum  EValidate { kDontValidate = 0 , kValidateWithTol = 1 , kValidateWithoutTol = 2 , kUninitialized = 3 }
 
- Static Public Attributes inherited from G4VTwistSurface
static const G4int sOutside = 0x00000000
 
static const G4int sInside = 0x10000000
 
static const G4int sBoundary = 0x20000000
 
static const G4int sCorner = 0x40000000
 
static const G4int sC0Min1Min = 0x40000101
 
static const G4int sC0Max1Min = 0x40000201
 
static const G4int sC0Max1Max = 0x40000202
 
static const G4int sC0Min1Max = 0x40000102
 
static const G4int sAxisMin = 0x00000101
 
static const G4int sAxisMax = 0x00000202
 
static const G4int sAxisX = 0x00000404
 
static const G4int sAxisY = 0x00000808
 
static const G4int sAxisZ = 0x00000C0C
 
static const G4int sAxisRho = 0x00001010
 
static const G4int sAxisPhi = 0x00001414
 
static const G4int sAxis0 = 0x0000FF00
 
static const G4int sAxis1 = 0x000000FF
 
static const G4int sSizeMask = 0x00000303
 
static const G4int sAxisMask = 0x0000FCFC
 
static const G4int sAreaMask = 0XF0000000
 
- Protected Member Functions inherited from G4VTwistSurface
G4VTwistSurface ** GetNeighbours ()
 
G4int GetNeighbours (G4int areacode, G4VTwistSurface *surfaces[])
 
G4ThreeVector GetCorner (G4int areacode) const
 
void GetBoundaryAxis (G4int areacode, EAxis axis[]) const
 
void GetBoundaryLimit (G4int areacode, G4double limit[]) const
 
virtual void SetBoundary (const G4int &axiscode, const G4ThreeVector &direction, const G4ThreeVector &x0, const G4int &boundarytype)
 
void SetCorner (G4int areacode, G4double x, G4double y, G4double z)
 
- Protected Attributes inherited from G4VTwistSurface
EAxis fAxis [2]
 
G4double fAxisMin [2]
 
G4double fAxisMax [2]
 
CurrentStatus fCurStatWithV
 
CurrentStatus fCurStat
 
G4RotationMatrix fRot
 
G4ThreeVector fTrans
 
G4int fHandedness
 
G4SurfCurNormal fCurrentNormal
 
G4bool fIsValidNorm
 
G4double kCarTolerance
 

Detailed Description

Definition at line 41 of file G4TwistTrapParallelSide.hh.

Constructor & Destructor Documentation

◆ G4TwistTrapParallelSide() [1/2]

G4TwistTrapParallelSide::G4TwistTrapParallelSide ( const G4String & name,
G4double PhiTwist,
G4double pDz,
G4double pTheta,
G4double pPhi,
G4double pDy1,
G4double pDx1,
G4double pDx2,
G4double pDy2,
G4double pDx3,
G4double pDx4,
G4double pAlph,
G4double AngleSide )

Definition at line 40 of file G4TwistTrapParallelSide.cc.

54 : G4VTwistSurface(name)
55{
56
57 fAxis[0] = kXAxis; // in local coordinate system
58 fAxis[1] = kZAxis;
59 fAxisMin[0] = -kInfinity ; // X Axis boundary
60 fAxisMax[0] = kInfinity ; // depends on z !!
61 fAxisMin[1] = -pDz ; // Z Axis boundary
62 fAxisMax[1] = pDz ;
63
64 fDx1 = pDx1 ;
65 fDx2 = pDx2 ;
66 fDx3 = pDx3 ;
67 fDx4 = pDx4 ;
68
69 fDy1 = pDy1 ;
70 fDy2 = pDy2 ;
71
72 fDz = pDz ;
73
74 fAlph = pAlph ;
75 fTAlph = std::tan(fAlph) ;
76
77 fTheta = pTheta ;
78 fPhi = pPhi ;
79
80 // precalculate frequently used parameters
81 //
82 fDx4plus2 = fDx4 + fDx2 ;
83 fDx4minus2 = fDx4 - fDx2 ;
84 fDx3plus1 = fDx3 + fDx1 ;
85 fDx3minus1 = fDx3 - fDx1 ;
86 fDy2plus1 = fDy2 + fDy1 ;
87 fDy2minus1 = fDy2 - fDy1 ;
88
89 fa1md1 = 2*fDx2 - 2*fDx1 ;
90 fa2md2 = 2*fDx4 - 2*fDx3 ;
91
92 fPhiTwist = PhiTwist ; // dphi
93 fAngleSide = AngleSide ; // 0,90,180,270 deg
94
95 fdeltaX = 2*fDz*std::tan(fTheta)*std::cos(fPhi); // dx in surface equation
96 fdeltaY = 2*fDz*std::tan(fTheta)*std::sin(fPhi); // dy in surface equation
97
98 fRot.rotateZ( AngleSide ) ;
99
100 fTrans.set(0, 0, 0); // No Translation
101 fIsValidNorm = false;
102
103 SetCorners() ;
104 SetBoundaries() ;
105}
void set(double x, double y, double z)
HepRotation & rotateZ(double delta)
Definition Rotation.cc:87
G4VTwistSurface(const G4String &name)
G4RotationMatrix fRot
G4ThreeVector fTrans
@ kXAxis
Definition geomdefs.hh:55
@ kZAxis
Definition geomdefs.hh:57

◆ ~G4TwistTrapParallelSide()

G4TwistTrapParallelSide::~G4TwistTrapParallelSide ( )
overridedefault

◆ G4TwistTrapParallelSide() [2/2]

G4TwistTrapParallelSide::G4TwistTrapParallelSide ( __void__ & a)

Definition at line 110 of file G4TwistTrapParallelSide.cc.

111 : G4VTwistSurface(a)
112{
113}

Member Function Documentation

◆ DistanceToSurface() [1/2]

G4int G4TwistTrapParallelSide::DistanceToSurface ( const G4ThreeVector & gp,
const G4ThreeVector & gv,
G4ThreeVector gxx[],
G4double distance[],
G4int areacode[],
G4bool isvalid[],
EValidate validate = kValidateWithTol )
overridevirtual

Implements G4VTwistSurface.

Definition at line 177 of file G4TwistTrapParallelSide.cc.

184{
185 static const G4double pihalf = pi/2 ;
186 const G4double ctol = 0.5 * kCarTolerance;
187
188 G4bool IsParallel = false ;
189 G4bool IsConverged = false ;
190
191 G4int nxx = 0 ; // number of physical solutions
192
193 fCurStatWithV.ResetfDone(validate, &gp, &gv);
194
195 if (fCurStatWithV.IsDone())
196 {
197 for (G4int i=0; i<fCurStatWithV.GetNXX(); ++i)
198 {
199 gxx[i] = fCurStatWithV.GetXX(i);
200 distance[i] = fCurStatWithV.GetDistance(i);
201 areacode[i] = fCurStatWithV.GetAreacode(i);
202 isvalid[i] = fCurStatWithV.IsValid(i);
203 }
204 return fCurStatWithV.GetNXX();
205 }
206 else // initialize
207 {
208 for (G4int i=0; i<G4VSURFACENXX ; ++i)
209 {
210 distance[i] = kInfinity;
211 areacode[i] = sOutside;
212 isvalid[i] = false;
213 gxx[i].set(kInfinity, kInfinity, kInfinity);
214 }
215 }
216
219
220#ifdef G4TWISTDEBUG
221 G4cout << "Local point p = " << p << G4endl ;
222 G4cout << "Local direction v = " << v << G4endl ;
223#endif
224
225 G4double phi,u ; // parameters
226
227 // temporary variables
228
229 G4double tmpdist = kInfinity ;
230 G4ThreeVector tmpxx;
231 G4int tmpareacode = sOutside ;
232 G4bool tmpisvalid = false ;
233
234 std::vector<Intersection> xbuf ;
235 Intersection xbuftmp ;
236
237 // prepare some variables for the intersection finder
238
239 G4double L = 2*fDz ;
240
241 G4double phixz = fPhiTwist * ( p.x() * v.z() - p.z() * v.x() ) ;
242 G4double phiyz = fPhiTwist * ( p.y() * v.z() - p.z() * v.y() ) ;
243
244 // special case vz = 0
245
246 if ( v.z() == 0. )
247 {
248 if ( std::fabs(p.z()) <= L ) // intersection possible in z
249 {
250 phi = p.z() * fPhiTwist / L ; // phi is determined by the z-position
251
252 u = (2*(fdeltaY*phi*v.x() - fPhiTwist*p.y()*v.x() - fdeltaX*phi*v.y()
253 + fPhiTwist*p.x()*v.y()) + (fDy2plus1*fPhiTwist
254 + 2*fDy2minus1*phi)*(v.x()*std::cos(phi) + v.y()*std::sin(phi)))
255 / (2.* fPhiTwist*(v.y()*std::cos(phi) - v.x()*std::sin(phi)));
256
257 xbuftmp.phi = phi ;
258 xbuftmp.u = u ;
259 xbuftmp.areacode = sOutside ;
260 xbuftmp.distance = kInfinity ;
261 xbuftmp.isvalid = false ;
262
263 xbuf.push_back(xbuftmp) ; // store it to xbuf
264 }
265 else // no intersection possible
266 {
267 distance[0] = kInfinity;
268 gxx[0].set(kInfinity,kInfinity,kInfinity);
269 isvalid[0] = false ;
270 areacode[0] = sOutside ;
271 fCurStatWithV.SetCurrentStatus(0, gxx[0], distance[0],
272 areacode[0], isvalid[0],
273 0, validate, &gp, &gv);
274
275 return 0;
276 } // end std::fabs(p.z() <= L
277 } // end v.z() == 0
278 else // general solution for non-zero vz
279 {
280 G4double c[9],srd[8],si[8] ;
281
282 c[8] = -3600*(-2*phiyz + fDy2plus1*fPhiTwist*v.z()) ;
283 c[7] = -7200*(phixz - 2*fDz*v.y() + (fdeltaY + fDy2minus1)*v.z()) ;
284 c[6] = 120*(-52*phiyz - 120*fDz*v.x() + 60*fdeltaX*v.z()
285 + 11*fDy2plus1*fPhiTwist*v.z()) ;
286 c[5] = 240*(16*phixz - 52*fDz*v.y() + 26*fdeltaY*v.z()
287 + 11*fDy2minus1*v.z()) ;
288 c[4] = 12*(127*phiyz + 640*fDz*v.x() - 320*fdeltaX*v.z()
289 + 4*fDy2plus1*fPhiTwist*v.z()) ;
290 c[3] = -404*phixz + 3048*fDz*v.y() - 1524*fdeltaY*v.z()
291 + 96*fDy2minus1*v.z() ;
292 c[2] = -72*phiyz + 404*(-2*fDz*v.x() + fdeltaX*v.z()) ;
293 c[1] = 12*(phixz - 12*fDz*v.y() + 6*fdeltaY*v.z()) ;
294 c[0] = 24*fDz*v.x() - 12*fdeltaX*v.z() ;
295
296
297#ifdef G4TWISTDEBUG
298 G4cout << "coef = " << c[0] << " "
299 << c[1] << " "
300 << c[2] << " "
301 << c[3] << " "
302 << c[4] << " "
303 << c[5] << " "
304 << c[6] << " "
305 << c[7] << " "
306 << c[8] << G4endl ;
307#endif
308
309 G4JTPolynomialSolver trapEq ;
310 G4int num = trapEq.FindRoots(c,8,srd,si);
311
312 for (G4int i = 0 ; i<num ; ++i ) // loop over all mathematical solutions
313 {
314 if ( si[i]==0.0 ) // only real solutions
315 {
316#ifdef G4TWISTDEBUG
317 G4cout << "Solution " << i << " : " << srd[i] << G4endl ;
318#endif
319 phi = std::fmod(srd[i] , pihalf) ;
320 u = (1/std::cos(phi)*(2*phixz + 4*fDz*phi*v.x()
321 - 2*fdeltaX*phi*v.z() + (fDy2plus1*fPhiTwist
322 + 2*fDy2minus1*phi)*v.z()* std::sin(phi)))/(2.*fPhiTwist*v.z()) ;
323
324 xbuftmp.phi = phi ;
325 xbuftmp.u = u ;
326 xbuftmp.areacode = sOutside ;
327 xbuftmp.distance = kInfinity ;
328 xbuftmp.isvalid = false ;
329
330 xbuf.push_back(xbuftmp) ; // store it to xbuf
331
332#ifdef G4TWISTDEBUG
333 G4cout << "solution " << i << " = " << phi << " , " << u << G4endl ;
334#endif
335
336 } // end if real solution
337 } // end loop i
338 } // end general case
339
340 nxx = (G4int)xbuf.size() ; // save the number of solutions
341
342 G4ThreeVector xxonsurface ; // point on surface
343 G4ThreeVector surfacenormal ; // normal vector
344 G4double deltaX ; // distance between intersection point and point on surface
345 G4double theta ; // angle between track and surfacenormal
346 G4double factor ; // a scaling factor
347 G4int maxint = 30 ; // number of iterations
348
349
350 for (auto & k : xbuf)
351 {
352#ifdef G4TWISTDEBUG
353 G4cout << "Solution " << k << " : "
354 << "reconstructed phiR = " << xbuf[k].phi
355 << ", uR = " << xbuf[k].u << G4endl ;
356#endif
357
358 phi = k.phi ; // get the stored values for phi and u
359 u = k.u ;
360
361 IsConverged = false ; // no convergence at the beginning
362
363 for ( G4int i = 1 ; i<maxint ; ++i )
364 {
365 xxonsurface = SurfacePoint(phi,u) ;
366 surfacenormal = NormAng(phi,u) ;
367 tmpdist = DistanceToPlaneWithV(p, v, xxonsurface, surfacenormal, tmpxx);
368 deltaX = ( tmpxx - xxonsurface ).mag() ;
369 theta = std::fabs(std::acos(v*surfacenormal) - pihalf) ;
370 if ( theta < 0.001 )
371 {
372 factor = 50 ;
373 IsParallel = true ;
374 }
375 else
376 {
377 factor = 1 ;
378 }
379
380#ifdef G4TWISTDEBUG
381 G4cout << "Step i = " << i << ", distance = "
382 << tmpdist << ", " << deltaX << G4endl ;
383 G4cout << "X = " << tmpxx << G4endl ;
384#endif
385
386 GetPhiUAtX(tmpxx, phi, u); // new point xx is accepted and phi/u replaced
387
388#ifdef G4TWISTDEBUG
389 G4cout << "approximated phi = " << phi << ", u = " << u << G4endl ;
390#endif
391
392 if ( deltaX <= factor*ctol ) { IsConverged = true ; break ; }
393 } // end iterative loop (i)
394
395 if ( std::fabs(tmpdist)<ctol ) tmpdist = 0 ;
396
397#ifdef G4TWISTDEBUG
398 G4cout << "refined solution " << phi << " , " << u << G4endl ;
399 G4cout << "distance = " << tmpdist << G4endl ;
400 G4cout << "local X = " << tmpxx << G4endl ;
401#endif
402
403 tmpisvalid = false ; // init
404
405 if ( IsConverged )
406 {
407 if (validate == kValidateWithTol)
408 {
409 tmpareacode = GetAreaCode(tmpxx);
410 if (!IsOutside(tmpareacode))
411 {
412 if (tmpdist >= 0) tmpisvalid = true;
413 }
414 }
415 else if (validate == kValidateWithoutTol)
416 {
417 tmpareacode = GetAreaCode(tmpxx, false);
418 if (IsInside(tmpareacode))
419 {
420 if (tmpdist >= 0) tmpisvalid = true;
421 }
422 }
423 else // kDontValidate
424 {
425 G4Exception("G4TwistTrapParallelSide::DistanceToSurface()",
426 "GeomSolids0001", FatalException,
427 "Feature NOT implemented !");
428 }
429 }
430 else
431 {
432 tmpdist = kInfinity; // no convergence after 10 steps
433 tmpisvalid = false ; // solution is not vaild
434 }
435
436 // store the found values
437 k.xx = tmpxx ;
438 k.distance = tmpdist ;
439 k.areacode = tmpareacode ;
440 k.isvalid = tmpisvalid ;
441 } // end loop over physical solutions (variable k)
442
443 std::sort(xbuf.begin() , xbuf.end(), DistanceSort ) ; // sorting
444
445#ifdef G4TWISTDEBUG
446 G4cout << G4endl << "list xbuf after sorting : " << G4endl ;
447 G4cout << G4endl << G4endl ;
448#endif
449
450 // erase identical intersection (within kCarTolerance)
451 xbuf.erase(std::unique(xbuf.begin(),xbuf.end(),EqualIntersection),xbuf.end());
452
453
454 // add guesses
455
456 auto nxxtmp = (G4int)xbuf.size() ;
457
458 if ( nxxtmp<2 || IsParallel )
459 {
460 // positive end
461#ifdef G4TWISTDEBUG
462 G4cout << "add guess at +z/2 .. " << G4endl ;
463#endif
464
465 phi = fPhiTwist/2 ;
466 u = 0 ;
467
468 xbuftmp.phi = phi ;
469 xbuftmp.u = u ;
470 xbuftmp.areacode = sOutside ;
471 xbuftmp.distance = kInfinity ;
472 xbuftmp.isvalid = false ;
473
474 xbuf.push_back(xbuftmp) ; // store it to xbuf
475
476#ifdef G4TWISTDEBUG
477 G4cout << "add guess at -z/2 .. " << G4endl ;
478#endif
479
480 phi = -fPhiTwist/2 ;
481 u = 0 ;
482
483 xbuftmp.phi = phi ;
484 xbuftmp.u = u ;
485 xbuftmp.areacode = sOutside ;
486 xbuftmp.distance = kInfinity ;
487 xbuftmp.isvalid = false ;
488
489 xbuf.push_back(xbuftmp) ; // store it to xbuf
490
491 for ( std::size_t k = nxxtmp ; k<xbuf.size() ; ++k )
492 {
493#ifdef G4TWISTDEBUG
494 G4cout << "Solution " << k << " : "
495 << "reconstructed phiR = " << xbuf[k].phi
496 << ", uR = " << xbuf[k].u << G4endl ;
497#endif
498
499 phi = xbuf[k].phi ; // get the stored values for phi and u
500 u = xbuf[k].u ;
501
502 IsConverged = false ; // no convergence at the beginning
503
504 for ( G4int i = 1 ; i<maxint ; ++i )
505 {
506 xxonsurface = SurfacePoint(phi,u) ;
507 surfacenormal = NormAng(phi,u) ;
508 tmpdist = DistanceToPlaneWithV(p, v, xxonsurface, surfacenormal, tmpxx);
509 deltaX = ( tmpxx - xxonsurface ).mag() ;
510 theta = std::fabs(std::acos(v*surfacenormal) - pihalf) ;
511 if ( theta < 0.001 )
512 {
513 factor = 50 ;
514 }
515 else
516 {
517 factor = 1 ;
518 }
519
520#ifdef G4TWISTDEBUG
521 G4cout << "Step i = " << i << ", distance = "
522 << tmpdist << ", " << deltaX << G4endl ;
523 G4cout << "X = " << tmpxx << G4endl ;
524#endif
525
526 GetPhiUAtX(tmpxx, phi, u) ; // new point xx accepted and phi/u replaced
527
528#ifdef G4TWISTDEBUG
529 G4cout << "approximated phi = " << phi << ", u = " << u << G4endl ;
530#endif
531
532 if ( deltaX <= factor*ctol ) { IsConverged = true ; break ; }
533 } // end iterative loop (i)
534
535 if ( std::fabs(tmpdist)<ctol ) tmpdist = 0 ;
536
537#ifdef G4TWISTDEBUG
538 G4cout << "refined solution " << phi << " , " << u << G4endl ;
539 G4cout << "distance = " << tmpdist << G4endl ;
540 G4cout << "local X = " << tmpxx << G4endl ;
541#endif
542
543 tmpisvalid = false ; // init
544
545 if ( IsConverged )
546 {
547 if (validate == kValidateWithTol)
548 {
549 tmpareacode = GetAreaCode(tmpxx);
550 if (!IsOutside(tmpareacode))
551 {
552 if (tmpdist >= 0) tmpisvalid = true;
553 }
554 }
555 else if (validate == kValidateWithoutTol)
556 {
557 tmpareacode = GetAreaCode(tmpxx, false);
558 if (IsInside(tmpareacode))
559 {
560 if (tmpdist >= 0) tmpisvalid = true;
561 }
562 }
563 else // kDontValidate
564 {
565 G4Exception("G4TwistedBoxSide::DistanceToSurface()",
566 "GeomSolids0001", FatalException,
567 "Feature NOT implemented !");
568 }
569
570 }
571 else
572 {
573 tmpdist = kInfinity; // no convergence after 10 steps
574 tmpisvalid = false ; // solution is not vaild
575 }
576
577 // store the found values
578 xbuf[k].xx = tmpxx ;
579 xbuf[k].distance = tmpdist ;
580 xbuf[k].areacode = tmpareacode ;
581 xbuf[k].isvalid = tmpisvalid ;
582
583 } // end loop over physical solutions
584 } // end less than 2 solutions
585
586 // sort again
587 std::sort(xbuf.begin() , xbuf.end(), DistanceSort ) ; // sorting
588
589 // erase identical intersection (within kCarTolerance)
590 xbuf.erase(std::unique(xbuf.begin(),xbuf.end(),EqualIntersection),xbuf.end());
591
592#ifdef G4TWISTDEBUG
593 G4cout << G4endl << "list xbuf after sorting : " << G4endl ;
594 G4cout << G4endl << G4endl ;
595#endif
596
597 nxx = (G4int)xbuf.size() ; // determine number of solutions again.
598
599 for ( G4int i = 0 ; i<(G4int)xbuf.size() ; ++i )
600 {
601 distance[i] = xbuf[i].distance;
602 gxx[i] = ComputeGlobalPoint(xbuf[i].xx);
603 areacode[i] = xbuf[i].areacode ;
604 isvalid[i] = xbuf[i].isvalid ;
605
606 fCurStatWithV.SetCurrentStatus(i, gxx[i], distance[i], areacode[i],
607 isvalid[i], nxx, validate, &gp, &gv);
608#ifdef G4TWISTDEBUG
609 G4cout << "element Nr. " << i
610 << ", local Intersection = " << xbuf[i].xx
611 << ", distance = " << xbuf[i].distance
612 << ", u = " << xbuf[i].u
613 << ", phi = " << xbuf[i].phi
614 << ", isvalid = " << xbuf[i].isvalid
615 << G4endl ;
616#endif
617 } // end for( i ) loop
618
619#ifdef G4TWISTDEBUG
620 G4cout << "G4TwistTrapParallelSide finished " << G4endl ;
621 G4cout << nxx << " possible physical solutions found" << G4endl ;
622 for ( G4int k= 0 ; k< nxx ; ++k )
623 {
624 G4cout << "global intersection Point found: " << gxx[k] << G4endl ;
625 G4cout << "distance = " << distance[k] << G4endl ;
626 G4cout << "isvalid = " << isvalid[k] << G4endl ;
627 }
628#endif
629
630 return nxx ;
631}
@ FatalException
void G4Exception(const char *originOfException, const char *exceptionCode, G4ExceptionSeverity severity, const char *description)
double G4double
Definition G4Types.hh:83
bool G4bool
Definition G4Types.hh:86
int G4int
Definition G4Types.hh:85
G4bool DistanceSort(const Intersection &a, const Intersection &b)
G4bool EqualIntersection(const Intersection &a, const Intersection &b)
#define G4VSURFACENXX
#define G4endl
Definition G4ios.hh:67
G4GLOB_DLL std::ostream G4cout
double z() const
double x() const
double y() const
G4int FindRoots(G4double *op, G4int degree, G4double *zeror, G4double *zeroi)
G4double GetDistance(G4int i) const
void SetCurrentStatus(G4int i, G4ThreeVector &xx, G4double &dist, G4int &areacode, G4bool &isvalid, G4int nxx, EValidate validate, const G4ThreeVector *p, const G4ThreeVector *v=nullptr)
G4ThreeVector GetXX(G4int i) const
void ResetfDone(EValidate validate, const G4ThreeVector *p, const G4ThreeVector *v=nullptr)
static const G4int sOutside
G4ThreeVector ComputeLocalDirection(const G4ThreeVector &gp) const
G4bool IsInside(G4int areacode, G4bool testbitmode=false) const
G4ThreeVector ComputeLocalPoint(const G4ThreeVector &gp) const
G4bool IsOutside(G4int areacode) const
CurrentStatus fCurStatWithV
G4double DistanceToPlaneWithV(const G4ThreeVector &p, const G4ThreeVector &v, const G4ThreeVector &x0, const G4ThreeVector &n0, G4ThreeVector &xx)
G4ThreeVector ComputeGlobalPoint(const G4ThreeVector &lp) const

◆ DistanceToSurface() [2/2]

G4int G4TwistTrapParallelSide::DistanceToSurface ( const G4ThreeVector & gp,
G4ThreeVector gxx[],
G4double distance[],
G4int areacode[] )
overridevirtual

Implements G4VTwistSurface.

Definition at line 636 of file G4TwistTrapParallelSide.cc.

640{
641 const G4double ctol = 0.5 * kCarTolerance;
642
644
645 if (fCurStat.IsDone())
646 {
647 for (G4int i=0; i<fCurStat.GetNXX(); ++i)
648 {
649 gxx[i] = fCurStat.GetXX(i);
650 distance[i] = fCurStat.GetDistance(i);
651 areacode[i] = fCurStat.GetAreacode(i);
652 }
653 return fCurStat.GetNXX();
654 }
655 else // initialize
656 {
657 for (G4int i=0; i<G4VSURFACENXX; ++i)
658 {
659 distance[i] = kInfinity;
660 areacode[i] = sOutside;
661 gxx[i].set(kInfinity, kInfinity, kInfinity);
662 }
663 }
664
666 G4ThreeVector xx; // intersection point
667 G4ThreeVector xxonsurface ; // interpolated intersection point
668
669 // the surfacenormal at that surface point
670 G4double phiR = 0 ; //
671 G4double uR = 0 ;
672
673 G4ThreeVector surfacenormal ;
674 G4double deltaX ;
675
676 G4int maxint = 20 ;
677
678 for ( G4int i = 1 ; i<maxint ; ++i )
679 {
680 xxonsurface = SurfacePoint(phiR,uR) ;
681 surfacenormal = NormAng(phiR,uR) ;
682 distance[0] = DistanceToPlane(p, xxonsurface, surfacenormal, xx); // new XX
683 deltaX = ( xx - xxonsurface ).mag() ;
684
685#ifdef G4TWISTDEBUG
686 G4cout << "i = " << i << ", distance = "
687 << distance[0] << ", " << deltaX << G4endl ;
688 G4cout << "X = " << xx << G4endl ;
689#endif
690
691 // the new point xx is accepted and phi/psi replaced
692 GetPhiUAtX(xx, phiR, uR) ;
693
694 if ( deltaX <= ctol ) { break ; }
695 }
696
697 // check validity of solution ( valid phi,psi )
698
699 G4double halfphi = 0.5*fPhiTwist ;
700 G4double uMax = GetBoundaryMax(phiR) ;
701 G4double uMin = GetBoundaryMin(phiR) ;
702
703 if ( phiR > halfphi ) phiR = halfphi ;
704 if ( phiR < -halfphi ) phiR = -halfphi ;
705 if ( uR > uMax ) uR = uMax ;
706 if ( uR < uMin ) uR = uMin ;
707
708 xxonsurface = SurfacePoint(phiR,uR) ;
709 distance[0] = ( p - xx ).mag() ;
710 if ( distance[0] <= ctol ) { distance[0] = 0 ; }
711
712 // end of validity
713
714#ifdef G4TWISTDEBUG
715 G4cout << "refined solution " << phiR << " , " << uR << " , " << G4endl ;
716 G4cout << "distance = " << distance[0] << G4endl ;
717 G4cout << "X = " << xx << G4endl ;
718#endif
719
720 G4bool isvalid = true;
721 gxx[0] = ComputeGlobalPoint(xx);
722
723#ifdef G4TWISTDEBUG
724 G4cout << "intersection Point found: " << gxx[0] << G4endl ;
725 G4cout << "distance = " << distance[0] << G4endl ;
726#endif
727
728 fCurStat.SetCurrentStatus(0, gxx[0], distance[0], areacode[0],
729 isvalid, 1, kDontValidate, &gp);
730 return 1;
731}
G4double DistanceToPlane(const G4ThreeVector &p, const G4ThreeVector &x0, const G4ThreeVector &n0, G4ThreeVector &xx)
CurrentStatus fCurStat

◆ GetNormal()

G4ThreeVector G4TwistTrapParallelSide::GetNormal ( const G4ThreeVector & xx,
G4bool isGlobal = false )
overridevirtual

Implements G4VTwistSurface.

Definition at line 123 of file G4TwistTrapParallelSide.cc.

125{
126 // GetNormal returns a normal vector at a surface (or very close
127 // to surface) point at tmpxx.
128 // If isGlobal=true, it returns the normal in global coordinate.
129 //
130
131 G4ThreeVector xx;
132 if (isGlobal)
133 {
134 xx = ComputeLocalPoint(tmpxx);
135 if ((xx - fCurrentNormal.p).mag() < 0.5 * kCarTolerance)
136 {
138 }
139 }
140 else
141 {
142 xx = tmpxx;
143 if (xx == fCurrentNormal.p)
144 {
145 return fCurrentNormal.normal;
146 }
147 }
148
149 G4double phi ;
150 G4double u ;
151
152 GetPhiUAtX(xx,phi,u) ; // phi,u for point xx close to surface
153
154 G4ThreeVector normal = NormAng(phi,u) ; // the normal vector at phi,u
155
156#ifdef G4TWISTDEBUG
157 G4cout << "normal vector = " << normal << G4endl ;
158 G4cout << "phi = " << phi << " , u = " << u << G4endl ;
159#endif
160
161 // normal = normal/normal.mag() ;
162
163 if (isGlobal)
164 {
166 }
167 else
168 {
169 fCurrentNormal.normal = normal.unit();
170 }
171 return fCurrentNormal.normal;
172}
Hep3Vector unit() const
G4ThreeVector ComputeGlobalDirection(const G4ThreeVector &lp) const
G4SurfCurNormal fCurrentNormal

The documentation for this class was generated from the following files: