30 #include "GeoModelRead/ReadGeoModel.h"
31 #include "GeoModelKernel/GeoTube.h"
32 #include "GeoModelKernel/GeoLogVol.h"
33 #include "GeoModelKernel/GeoPhysVol.h"
34 #include "GeoModelKernel/GeoFullPhysVol.h"
35 #include "GeoModelKernel/GeoNameTag.h"
36 #include "GeoModelKernel/GeoIdentifierTag.h"
37 #include "GeoModelKernel/GeoTransform.h"
38 #include "GeoModelKernel/GeoAlignableTransform.h"
39 #include "GeoModelKernel/GeoMaterial.h"
40 #include "GeoModelKernel/GeoShapeShift.h"
41 #include "GeoModelKernel/GeoDefinitions.h"
42 #include "GaudiKernel/SystemOfUnits.h"
50 inline double sqr(
double x) {
return x*
x;}
54 const std::vector<SCT_FwdModule *> & modules,
59 GeoModelIO::ReadGeoModel* sqliteReader,
60 std::shared_ptr<std::map<std::string, GeoFullPhysVol*>> mapFPV,
61 std::shared_ptr<std::map<std::string, GeoAlignableTransform*>> mapAX)
83 for (
int iRing = 0; iRing <
m_numRings; iRing++) {
118 for (
int iLoc = 0; iLoc <
parameters->fwdNumCylinderServiceLocs(); iLoc++) {
120 if(
parameters->fwdCylinderServiceLocName(iLoc) ==
"NPipe") {
138 for (
int iRing = 0; iRing <
m_numRings; iRing++){
141 m_rings.push_back(std::make_unique<SCT_FwdRing>(ringName,
m_modules[
ringType],
m_iWheel, iRing,
m_endcap,
m_detectorManager,
m_geometryManager,
m_materials,
m_sqliteReader,
m_mapFPV,
m_mapAX));
148 for (
int iRing = 0; iRing <
m_numRings; iRing++){
165 m_pPConnector = std::make_unique<SCT_FwdPPConnector>(
"PPConnector",
169 m_pPCooling = std::make_unique<SCT_FwdPPCooling>(
"PPCooling",
173 m_discFixation = std::make_unique<SCT_FwdDiscFixation>(
"DiscFixation",
179 for (
unsigned int iFSI = 0; iFSI <
m_fsiVector->size(); iFSI++) {
180 int type = (*m_fsiVector)[iFSI]->simType();
191 double maxModuleThickness = 0.5 *
m_discSupport->thickness();
195 for (
int iRing = 0; iRing <
m_numRings; iRing++){
198 maxModuleThickness =
std::max(maxModuleThickness,
m_rings[iRing]->thicknessOuter() +
m_rings[iRing]->ringOffset());
215 maxOuterRadius =
std::max(ppCoolingOuterRadius, maxOuterRadius);
221 maxOuterRadius =
std::max(discFixationOuterRadius, maxOuterRadius);
249 const GeoShape & fwdWheelEnvelopeShape = *tmpShape << GeoTrf::Translate3D(0, 0, envelopeShift);
251 const GeoLogVol * fwdWheelLog =
265 for (
int iRing = 0; iRing <
m_numRings; iRing++){
276 GeoFullPhysVol * wheel=
new GeoFullPhysVol(
m_logVolume);
286 double powerTapeZMinusMax = -0.5 *
m_discSupport->thickness();
288 double maxZOfRingsFront = 0;
290 for (
int iRing = 0; iRing <
m_numRings; iRing++){
297 maxZOfRingsFront =
std::max(maxZOfRingsFront, ringOuterZ);
300 wheel->add(
new GeoNameTag(ringNameTag));
302 wheel->add(
new GeoTransform(GeoTrf::Translate3D(0, 0, ringZpos)));
311 wheel->add(
new GeoTransform(GeoTrf::TranslateZ3D(coolingZpos)));
326 double powerTapeZstart = powerTapeZpos - 0.5 * powerTape.
thickness();
327 if (powerTapeZstart < powerTapeZPlusMax) {
328 powerTapeZpos = powerTapeZPlusMax + 0.5 * powerTape.
thickness();
330 powerTapeZPlusMax = powerTapeZpos + 0.5 * powerTape.
thickness();
332 double powerTapeZstart = powerTapeZpos + 0.5 * powerTape.
thickness();
333 if (powerTapeZstart > powerTapeZMinusMax) {
334 powerTapeZpos = powerTapeZMinusMax - 0.5 * powerTape.
thickness();
336 powerTapeZMinusMax = powerTapeZpos - 0.5 * powerTape.
thickness();
339 std::cout <<
"ERROR: Power tapes clash with modules!!!" << std::endl;
341 wheel->add(
new GeoTransform(GeoTrf::TranslateZ3D(powerTapeZpos)));
357 double powerTapeZMax = 0;
358 if (patchPanelSide > 0) {
359 powerTapeZMax = powerTapeZPlusMax;
361 powerTapeZMax = -powerTapeZMinusMax;
373 if (ppType >=
m_numPatchPanelTypes) std::cout <<
"ERROR: Patch Panel type number out of range!" << std::endl;
374 for (
int iRepeat = 0; iRepeat < numRepeat; iRepeat++) {
378 double patchPanelZpos = patchPanelSide * (powerTapeZMax + 0.5*
m_patchPanel[ppType]->thickness() +
m_safety);
383 std::cout <<
"ERROR: Patch Panel clashes with middle ring" << std::endl;
384 std::cout <<
" PatchPanel inner radius: " <<
m_patchPanel[ppType]->innerRadius() << std::endl;
385 std::cout <<
" Ring outer radius: " <<
m_rings[1]->outerRadius() << std::endl;
389 wheel->add(
new GeoTransform(GeoTrf::RotateZ3D(patchPanelAngle)*GeoTrf::TranslateX3D(patchPanelR)*GeoTrf::TranslateZ3D(patchPanelZpos)));
395 double ppConnectorZpos = patchPanelSide * (powerTapeZMax + 0.5*
m_pPConnector->thickness() +
m_safety);
399 std::cout <<
"ERROR: Patch Panel Connector clashes outside wheel" << std::endl;
400 std::cout <<
" PatchPanel Connector outer radius: " << ppConnectorR + 0.5*
m_pPConnector->deltaR() << std::endl;
401 std::cout <<
" Wheel outer radius: " <<
m_outerRadius << std::endl;
404 wheel->add(
new GeoTransform(GeoTrf::RotateZ3D(patchPanelAngle)*GeoTrf::TranslateX3D(ppConnectorR)*GeoTrf::TranslateZ3D(ppConnectorZpos)));
411 double ppCoolingZpos = patchPanelSide * (powerTapeZMax + 0.5*
m_pPCooling->thickness() +
m_safety);
415 std::cout <<
"ERROR: Patch Panel Cooling clashes outside wheel" << std::endl;
416 std::cout <<
" PatchPanel Cooling outer radius: " << ppCoolingR + 0.5*
m_pPCooling->deltaR() << std::endl;
417 std::cout <<
" Wheel outer radius: " <<
m_outerRadius << std::endl;
420 wheel->add(
new GeoTransform(GeoTrf::RotateZ3D(patchPanelAngle)*GeoTrf::TranslateX3D(ppCoolingR)*GeoTrf::TranslateZ3D(ppCoolingZpos)));
432 std::string optoharnessName =
"OptoHarnessO";
438 wheel->add(
new GeoTransform(GeoTrf::TranslateZ3D(optoHarnessZpos)));
440 optoHarnessZMax = optoHarnessZpos + 0.5*optoharness.
thickness();
444 for (
unsigned int iFSI = 0; iFSI <
m_fsiVector->size(); iFSI++) {
445 int type = (*m_fsiVector)[iFSI]->simType();
446 double fsiRadius = (*m_fsiVector)[iFSI]->location().radius();
447 double fsiPhi = (*m_fsiVector)[iFSI]->location().phi();
448 int fsiUsualSide = (*m_fsiVector)[iFSI]->location().side();
453 if (fsiUsualSide < 0) {
454 double zMin = std::abs(fsiZpos) - 0.5*
m_fsiType[
type]->thickness();
455 if (maxZOfRingsFront > zMin) {
456 std::cout <<
"WARNING: FSI probably clashes with ring" << std::endl;
457 std::cout <<
" maxZOfRingsFront = " << maxZOfRingsFront << std::endl;
458 std::cout <<
" fsiZMin = " << zMin << std::endl;
465 double servicesZMax = (fsiRadius > diskMidRadius) ? powerTapeZMax : optoHarnessZMax;
466 double zMin = std::abs(fsiZpos) - 0.5*
m_fsiType[
type]->thickness();
467 if (servicesZMax > zMin) {
468 std::cout <<
"WARNING: FSI probably clashes with disc services" << std::endl;
469 std::cout <<
" servicesZMax = " << servicesZMax << std::endl;
470 std::cout <<
" fsiZMin = " << zMin << std::endl;
471 std::cout <<
" fsiRadius = " << fsiRadius << std::endl;
475 wheel->add(
new GeoTransform(GeoTrf::RotateZ3D(fsiPhi)*GeoTrf::TranslateX3D(fsiRadius)*GeoTrf::TranslateZ3D(fsiZpos)));
485 for (
int iRepeat = 0; iRepeat < 4; iRepeat++) {
491 std::cout <<
"ERROR: Disc Fixation outside wheel" << std::endl;
492 std::cout <<
"Disc fixation outer radius: " << discFixationR + 0.5*
m_discFixation->thickness() << std::endl;
493 std::cout <<
" Wheel outer radius: " <<
m_outerRadius << std::endl;
496 wheel->add(
new GeoTransform(GeoTrf::RotateY3D(90.*
Gaudi::Units::degree)*GeoTrf::RotateX3D(discFixationAngle)*GeoTrf::TranslateZ3D(discFixationR)));
504 xMat.
add(wheel,
"SCTDisc");
507 xMat.
add(wheel,
"SCTDiscA");
510 xMat.
add(wheel,
"SCTDiscC");