19#include "BDSAcceleratorComponent.hh"
20#include "BDSBeamline.hh"
21#include "BDSBeamlineEndPieceBuilder.hh"
22#include "BDSBeamlineElement.hh"
23#include "BDSExtent.hh"
24#include "BDSGlobalConstants.hh"
25#include "BDSSimpleComponent.hh"
26#include "BDSTiltOffset.hh"
27#include "BDSUtilities.hh"
30#include "G4ThreeVector.hh"
33 const G4bool circularMachine)
39 if (beamline->
empty())
47 G4int currentIndex = 0;
48 for (
auto element : *beamline)
51 const auto accComponentTO = element->GetTiltOffset();
53 const auto endPieceAfter = accComponent->EndPieceAfter();
55 G4bool placeBefore =
true;
56 G4bool placeAfter =
true;
57 if (!endPieceBefore && !endPieceAfter)
62 else if (!endPieceBefore)
63 {placeBefore =
false;}
64 else if (!endPieceAfter)
67 G4double requiredBeforeLength = 0;
68 G4double requiredAfterLength = 0;
70 {requiredBeforeLength = endPieceBefore->
GetChordLength() + 2*lengthSafetyLarge;}
72 {requiredAfterLength = endPieceAfter->GetChordLength() + 2*lengthSafetyLarge;}
80 G4bool keepGoing =
true;
82 G4double availableLength = 0;
83 G4double previousNonDriftEndPieceL = 0;
84 G4bool driftIsFirstItem =
false;
85 BDSExtent endPieceInnerExtent = endPieceBefore->GetInnerExtent();
86 G4bool driftsAreTooBigBefore =
false;
89 inspectedElement = beamline->
GetPrevious(inspectedElement);
92 G4String inspectedElementType = inspectedElement->
GetType();
93 if (inspectedElementType ==
"drift" || inspectedElementType ==
"dipolefringe" || inspectedElementType ==
"element")
97 G4double tiltPipe = inspectedElement->
GetTilt();
99 {extPipe = extPipe.
Tilted(accComponentTO->GetTilt() - tiltPipe);}
103 if (inspectedElementType !=
"element")
104 {driftsAreTooBigBefore =
true;}
109 driftIsFirstItem = inspectedElement == firstItem;
116 if (previousNonDriftAccCompEndPiece)
117 {previousNonDriftEndPieceL = previousNonDriftAccCompEndPiece->
GetChordLength();}
125 if (requiredBeforeLength > (availableLength - previousNonDriftEndPieceL))
126 {placeBefore =
false;}
129 if (driftsAreTooBigBefore)
130 {placeBefore =
false;}
134 if ( (element == firstItem) || (driftIsFirstItem && !driftsAreTooBigBefore) )
135 {placeBefore =
true;}
140 if ( (element == firstItem) && circularMachine )
141 {placeBefore =
false;}
146 if (placeBefore && !endPieces->
empty() )
152 BDSExtent extOF = endPieceBefore->GetExtent();
154 G4ThreeVector oFNormal = endPieceBefore->InputFaceNormal();
157 G4double zSeparation = availableLength - requiredBeforeLength - lastEndPieceL;
158 G4bool willIntersect =
BDS::WillIntersect(iFNormal, oFNormal, zSeparation, extIF, extOF);
160 {placeBefore =
false;}
177 auto beforeEl = beamline->ProvideEndPieceElementBefore(endPieceBefore,
189 G4bool keepGoing =
true;
191 G4double availableLength = 0;
192 G4double nextNonDriftEndPieceL = 0;
193 G4bool driftIsLastItem =
false;
194 BDSExtent endPieceInnerExtent = endPieceAfter->GetInnerExtent();
195 G4bool driftsAreTooBigAfter =
false;
198 inspectedElement = beamline->GetNext(inspectedElement);
199 if (inspectedElement)
201 G4String inspectedElementType = inspectedElement->
GetType();
202 if (inspectedElementType ==
"drift" || inspectedElementType ==
"dipolefringe" || inspectedElementType ==
"element")
206 G4double tiltPipe = inspectedElement->
GetTilt();
208 {extPipe = extPipe.
Tilted(accComponentTO->GetTilt() - tiltPipe);}
212 if (inspectedElementType !=
"element")
213 {driftsAreTooBigAfter =
true;}
218 driftIsLastItem = inspectedElement == lastItem;
225 if (nextNonDriftAccCompEndPiece)
226 {nextNonDriftEndPieceL = nextNonDriftAccCompEndPiece->
GetChordLength();}
234 if (requiredAfterLength > (availableLength - nextNonDriftEndPieceL))
235 {placeAfter =
false;}
238 if (driftsAreTooBigAfter)
239 {placeAfter =
false;}
243 if ( (element == lastItem) || (driftIsLastItem && !driftsAreTooBigAfter) )
248 G4bool flip = endPieceAfter == endPieceBefore;
Abstract class that represents a component of an accelerator.
BDSSimpleComponent * EndPieceBefore() const
virtual G4double GetChordLength() const
G4ThreeVector OutputFaceNormal() const
A class that holds a fully constructed BDSAcceleratorComponent as well as any information relevant to...
G4double GetChordLength() const
Accessor.
BDSAcceleratorComponent * GetAcceleratorComponent() const
Accessor.
G4double GetTilt() const
Convenience accessor.
G4String GetType() const
Accessor.
A vector of BDSBeamlineElement instances - a beamline.
const BDSBeamlineElement * GetPrevious(const BDSBeamlineElement *element) const
BDSBeamlineElement * back() const
Return a reference to the last element.
const BDSBeamlineElement * GetLastItem() const
Return a reference to the last element.
BDSBeamlineElement * ProvideEndPieceElementAfter(BDSSimpleComponent *endPiece, G4int index, G4bool flip=false) const
const BDSBeamlineElement * GetFirstItem() const
Return a reference to the first element.
void AddBeamlineElement(BDSBeamlineElement *element)
G4bool empty() const
Iterator mechanics.
Holder for +- extents in 3 dimensions.
BDSExtent Tilted(G4double angle) const
Provide a new copy of this extent but rotated along Z by a given tilt angle.
G4bool TransverselyGreaterThan(const BDSExtent &r) const
Comparison operator for x,y only. Ignores z (length).
BDSExtent GetExtent() const
Accessor - see member for more info.
static BDSGlobalConstants * Instance()
Access method.
BDSBeamline * BuildEndPieceBeamline(const BDSBeamline *beamline, const G4bool circularMachine)
G4bool WillIntersect(const G4ThreeVector &incomingNormal, const G4ThreeVector &outgoingNormal, const G4double &zSeparation, const BDSExtent &incomingExtent, const BDSExtent &outgoingExtent)