16 #include "GeoModelKernel/GeoElement.h"
17 #include "GeoModelKernel/GeoMaterial.h"
18 #include "GeoModelKernel/GeoFullPhysVol.h"
19 #include "GeoModelKernel/GeoPhysVol.h"
20 #include "GeoModelKernel/GeoVPhysVol.h"
21 #include "GeoModelKernel/GeoLogVol.h"
22 #include "GeoModelKernel/GeoBox.h"
23 #include "GeoModelKernel/GeoCons.h"
24 #include "GeoModelKernel/GeoPcon.h"
25 #include "GeoModelKernel/GeoGenericTrap.h"
26 #include "GeoModelKernel/GeoNameTag.h"
27 #include "GeoModelKernel/GeoTransform.h"
28 #include "GeoModelKernel/GeoIdentifierTag.h"
29 #include "GeoModelKernel/GeoPublisher.h"
30 #include "GeoModelKernel/Units.h"
37 #include "GaudiKernel/MsgStream.h"
38 #include "GaudiKernel/ISvcLocator.h"
39 #include "GaudiKernel/PhysicalConstants.h"
40 #include "GaudiKernel/StatusCode.h"
45 #define SI GeoModelKernelUnits
53 ISvcLocator *svcLocator = Gaudi::svcLocator();
55 if(svcLocator->service(
"DetectorStore",
detStore,
false)==StatusCode::FAILURE) {
56 throw std::runtime_error(
"Error in EndcapCryostatConstruction, cannot access DetectorStore");
63 StatusCode sc = svcLocator->service(
"RDBAccessSvc",rdbAccess);
64 if(
sc != StatusCode::SUCCESS){
65 throw std::runtime_error(
"EMECConstruction: cannot locate RDBAccessSvc!");
68 sc = svcLocator->service (
"GeoModelSvc",geoModelSvc);
69 if(
sc != StatusCode::SUCCESS){
70 throw std::runtime_error(
"EMECAccordionConstruction: cannot locate GeoModelSvc!");
75 if(DB_EmecGeometry->size() == 0){
76 DB_EmecGeometry = rdbAccess->
getRecordsetPtr(
"EmecGeometry",
"EmecGeometry-00");
77 std::cout<<
"Building NEW EMEC ACCORDION STRUCTURE" <<std::endl;
81 if(emecWheelParameters->size() == 0){
82 emecWheelParameters = rdbAccess->
getRecordsetPtr(
"EmecWheelParameters",
"EmecWheelParameters-00");
83 std::cout<<
"EmecWheelParameters" <<std::endl;
88 if(emecMagicNumbers->size() == 0){
89 emecMagicNumbers = rdbAccess->
getRecordsetPtr(
"EmecMagicNumbers",
"EmecMagicNumbers-00");
90 std::cout<<
"EmecMagicNumbers" <<std::endl;
94 if(coldContraction->size() == 0){
95 coldContraction = rdbAccess->
getRecordsetPtr(
"ColdContraction",
"ColdContraction-00");
96 std::cout<<
"ColdContraction" <<std::endl;
100 if(emecFan->size() == 0){
102 std::cout<<
"EmecFan" <<std::endl;
120 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setWheelParameters: wrong number of absorbers. (NABS = " +
std::to_string(
m_innerNoAbsorbes) +
") for Inner Wheel, expected 256!");
123 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setWheelParameters: wrong number of waves. (NACC = " +
std::to_string(
m_innerNoAbsorbes ) +
") for Inner Wheel, expected 6!");
126 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setWheelParameters: wrong width of absorber lips. (STRAIGHTSTARTSECTION = " +
std::to_string(
m_innerNoAbsorbes/
SI::mm) +
"), expected 2 mm!" );
129 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setWheelParameters: wrong width of absorber active zone. (ACTIVELENGTH = " +
std::to_string(
m_innerWaveZoneWidth/
SI::mm) +
"), expected 510 mm!");
146 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setWheelParameters: wrong number of absorbers. (NABS = " +
std::to_string (
m_outerNoAbsorbes) +
") for Outer Wheel, expected 768!");
149 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setWheelParameters: wrong number of waves. (NACC = " +
std::to_string(
m_outerNoAbsorbes) +
") for Outer Wheel, expected 9!" );
176 m_kContraction = (*coldContraction)[0]->getDouble(
"ABSORBERCONTRACTION");
190 double eleInvContraction = (*coldContraction)[0]->getDouble(
"ELECTRODEINVCONTRACTION");
201 m_innerWheel = innerWheel;
202 const GeoShape* shape = innerWheel->getLogVol()->getShape();
203 if (shape->type() !=
"Pcon") {
204 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setInnerWheel: unexpected shape type '"+ shape->type() +
"', expected 'Pcon'!");
206 const GeoPcon* pcon = (GeoPcon *)shape;
207 auto nplanes = pcon->getNPlanes();
209 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setInnerWheel: wrong number of Z planes '" +
std::to_string(nplanes) +
"', expected '2'!");
211 for (
unsigned int i = 0;
i < nplanes; ++
i)
213 m_zWheelInner[
i] = pcon->getZPlane(
i);
214 m_rMinInner[
i] = pcon->getRMinPlane(
i);
215 m_rMaxInner[
i] = pcon->getRMaxPlane(
i);
218 m_nameInnerWheel = innerWheel->getLogVol()->getName();
227 m_outerWheel = outerWheel;
228 const GeoShape* shape = outerWheel->getLogVol()->getShape();
229 if (shape->type() !=
"Pcon") {
230 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setOuterWheel: unexpected shape type '"+ shape->type() +
"', expected 'Pcon'!");
233 const GeoPcon* pcon = (GeoPcon *)shape;
234 auto nplanes = pcon->getNPlanes();
236 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setOuterWheel: wrong number of Z planes" +
std::to_string(nplanes) +
"', expected '3'!" );
238 for (
unsigned int i = 0;
i < nplanes; ++
i)
240 m_zWheelOuter[
i] = pcon->getZPlane(
i);
241 m_rMinOuter[
i] = pcon->getRMinPlane(
i);
242 m_rMaxOuter[
i] = pcon->getRMaxPlane(
i);
245 m_nameOuterWheel = outerWheel->getLogVol()->getName();
256 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setInnerWheelSlices: Inner Wheel volume is not set!" );
259 m_innerWheelRminIncrement = (m_rMinInner[1] - m_rMinInner[0])/(m_zWheelInner[1] - m_zWheelInner[0]);
260 m_innerWheelRmaxIncrement = (m_rMaxInner[1] - m_rMaxInner[0])/(m_zWheelInner[1] - m_zWheelInner[0]);
261 m_innerWheelZmin = m_zWheelInner[0];
262 m_innerWheelZmax = m_zWheelInner[1];
264 m_innerWheelZ[0] = m_innerWheelZmin;
265 m_innerWheelZ[1] = m_innerWheelZ[0] + m_innerLipWidth;
266 m_innerWheelZ[2] = m_innerWheelZ[1] + m_innerQuaterWaveWidth;
267 for (
int i = 3;
i < s_innerNoBlades - 1; ++
i)
269 m_innerWheelZ[
i] = m_innerWheelZ[
i - 1] + m_innerHalfWaveWidth;
271 m_innerWheelZ[s_innerNoBlades] = m_innerWheelZmax;
272 m_innerWheelZ[s_innerNoBlades - 1] = m_innerWheelZ[s_innerNoBlades] - m_innerLipWidth;
273 for (
int i = 0;
i < s_innerNoBlades + 1; ++
i)
275 m_innerWheelRmin[
i] = m_rMinInner[0] + (m_innerWheelZ[
i] - m_innerWheelZ[0])*m_innerWheelRminIncrement;
276 m_innerWheelRmax[
i] = m_rMaxInner[0] + (m_innerWheelZ[
i] - m_innerWheelZ[0])*m_innerWheelRmaxIncrement;
288 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setOuterWheelSlices: Outer Wheel volume is not set!");
291 m_outerWheelRminIncrement[0] = (m_rMinOuter[1] - m_rMinOuter[0])/(m_zWheelOuter[1] - m_zWheelOuter[0]);
292 m_outerWheelRminIncrement[1] = (m_rMinOuter[2] - m_rMinOuter[1])/(m_zWheelOuter[2] - m_zWheelOuter[1]);
293 m_outerWheelRmaxIncrement[0] = (m_rMaxOuter[1] - m_rMaxOuter[0])/(m_zWheelOuter[1] - m_zWheelOuter[0]);
294 m_outerWheelRmaxIncrement[1] = (m_rMaxOuter[2] - m_rMaxOuter[1])/(m_zWheelOuter[2] - m_zWheelOuter[1]);
295 m_outerWheelZmin = m_zWheelOuter[0];
296 m_outerWheelZmax = m_zWheelOuter[2];
298 m_outerWheelZ[0] = m_outerWheelZmin;
299 m_outerWheelZ[1] = m_outerWheelZ[0] + m_outerLipWidth;
300 m_outerWheelZ[2] = m_outerWheelZ[1] + m_outerQuaterWaveWidth;
301 for (
int i = 3;
i < s_outerNoBlades - 1; ++
i)
303 m_outerWheelZ[
i] = m_outerWheelZ[
i - 1] + m_outerHalfWaveWidth;
305 m_outerWheelZ[s_outerNoBlades] = m_outerWheelZmax;
306 m_outerWheelZ[s_outerNoBlades - 1] = m_outerWheelZ[s_outerNoBlades] - m_outerLipWidth;
307 for (
int i = 0;
i < s_outerNoBlades + 1; ++
i)
309 m_outerWheelRmin[
i] = m_rMinOuter[0] + (m_outerWheelZ[
i] - m_outerWheelZ[0])*m_outerWheelRminIncrement[0];
310 m_outerWheelRmax[
i] = m_rMaxOuter[0] + (m_outerWheelZ[
i] - m_outerWheelZ[0])*m_outerWheelRmaxIncrement[0];
311 if (m_outerWheelRmax[
i] > m_rMaxOuter[2]) m_outerWheelRmax[
i] = m_rMaxOuter[2];
321 const GeoMaterial* material)
323 if (
name ==
"LiquidArgon") m_materialLiquidArgon = material;
324 else if (
name ==
"Kapton") m_materialKapton = material;
325 else if (
name ==
"Lead" ) m_materialLead = material;
326 else if (
name ==
"Steel" ) m_materialSteel = material;
327 else if (
name ==
"Glue" ) m_materialGlue = material;
330 throw std::runtime_error(
"LArGeo::EMECAccordionConstruction::setMaterial: unexpected material name '" +
name +
"'!");
340 double& llip1,
double& ylip1,
341 double& llip2,
double& ylip2)
const
390 double cosa = A[k1].dot(A[k2])/(A[k1].norm()*A[k2].norm());
391 double ang = std::acos(cosa)/(k2 - k1);
394 double rmin = B[1].norm();
395 double rmax = A[14].norm();
400 llip1 = (C[2] - D[2]).
norm();
401 ylip1 = (D[2] - B[1]).
norm() + llip1/2.;
404 llip2 = (C[3] - D[3]).
norm();
405 ylip2 = (D[3] - B[14]).
norm() + llip2/2.;
414 double& llip1,
double& ylip1,
415 double& llip2,
double& ylip2)
const
476 double cosa = A[k1].dot(A[k2])/(A[k1].norm()*A[k2].norm());
477 double ang = std::acos(cosa)/(k2 - k1);
480 double rmin = B[1].norm();
481 double rmax = A[19].norm();
486 llip1 = (C[2] - D[2]).
norm();
487 ylip1 = (D[2] - B[1]).
norm() + llip1/2.;
490 llip2 = (C[3] - D[3]).
norm();
491 ylip2 = (D[3] - B[20]).
norm() + llip2/2.;
500 double rmin,
double rmax,
double zdel,
505 double xmin = std::sqrt(wmin*wmin - zdel*zdel)/2.;
506 double dxmin = (thickness/2.)*(wmin/zdel);
509 double xmax = std::sqrt(wmax*wmax - zdel*zdel)/2.;
510 double dxmax = (thickness/2.)*(wmax/zdel);
511 double xtmp = (
xmax + dxmax);
512 double ymax = std::sqrt(rmax*rmax - xtmp*xtmp);
531 double zmax,
double rmax)
const
539 plane.
m_d = -plane.
m_n.dot(pmin);
549 double zmax,
double rmax,
556 double d =
v.x()*pbot.y() -
v.y()*pbot.x();
557 double r = ptop.norm();
558 double l = std::sqrt(
r*
r -
d*
d);
559 double wmin = std::sqrt(rmin*rmin -
d*
d);
560 double wmax = std::sqrt(rmax*rmax -
d*
d);
561 double ymin = ptop.y() -
v.y()*(
l - wmin);
562 double ymax = ptop.y() -
v.y()*(
l - wmax);
566 v = (pmax - pmin).normalized();
570 plane.
m_d = -plane.
m_n.dot(pmin);
599 double pz1,
double pr1min,
double pr1max,
600 double pz2,
double pr2min,
double pr2max)
const
602 double z1 = pz1, r1min = pr1min, r1max = pr1max;
603 double z2 = pz2, r2min = pr2min, r2max = pr2max;
607 r1min -= (r2min - r1min);
608 r1max -= (r2max - r1max);
613 r2min += (r2min - r1min);
614 r2max += (r2max - r1max);
618 std::vector<GeoThreeVector> v3(8);
619 double kx = (icase == 2) ? 1 : -1;
622 for (
int i = 0;
i < 8; ++
i)
638 v3[0] = IntersectionPoint(v3[0], v3[3], botPlane);
639 v3[1] = IntersectionPoint(v3[1], v3[2], botPlane);
640 v3[4] = IntersectionPoint(v3[4], v3[7], botPlane);
641 v3[5] = IntersectionPoint(v3[5], v3[6], botPlane);
645 v3[3] = IntersectionPoint(v3[0], v3[3], topPlane);
646 v3[2] = IntersectionPoint(v3[1], v3[2], topPlane);
647 v3[7] = IntersectionPoint(v3[4], v3[7], topPlane);
648 v3[6] = IntersectionPoint(v3[5], v3[6], topPlane);
652 v3[0] = (v3[0] + v3[4])/2.;
653 v3[1] = (v3[1] + v3[5])/2.;
654 v3[2] = (v3[2] + v3[6])/2.;
655 v3[3] = (v3[3] + v3[7])/2.;
660 v3[4] = (v3[0] + v3[4])/2.;
661 v3[5] = (v3[1] + v3[5])/2.;
662 v3[6] = (v3[2] + v3[6])/2.;
663 v3[7] = (v3[3] + v3[7])/2.;
675 std::vector<GeoTwoVector>
v2(8);
676 for (
int i = 0;
i < 8;
i += 2)
678 double xmid = (v3[
i + 1].x() + v3[
i].x())/2.;
679 double xdel = (v3[
i + 1].x() - v3[
i].x())*xscale/2.;
683 return new GeoGenericTrap((pz2 - pz1)/2.,
v2);
694 for (
int islice = 0; islice < s_innerNoBlades; ++islice)
696 name = m_nameInnerWheel + m_nameSlice + m_nameSuffix[islice];
697 double dz = 0.5*(m_innerWheelZ[islice+1] - m_innerWheelZ[islice]);
698 solid =
new GeoCons(m_innerWheelRmin[islice], m_innerWheelRmin[islice+1],
699 m_innerWheelRmax[islice], m_innerWheelRmax[islice+1],
701 m_innerSlice[islice] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialLiquidArgon));
702 m_innerSliceOffset[islice] =
GeoThreeVector(0., 0., m_innerWheelZ[islice] + dz);
714 for (
int islice = 0; islice < s_outerNoBlades; ++islice)
716 name = m_nameOuterWheel + m_nameSlice + m_nameSuffix[islice];
717 double dz = 0.5*(m_outerWheelZ[islice+1] - m_outerWheelZ[islice]);
718 solid =
new GeoCons(m_outerWheelRmin[islice], m_outerWheelRmin[islice+1],
719 m_outerWheelRmax[islice], m_outerWheelRmax[islice+1],
721 m_outerSlice[islice] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialLiquidArgon));
722 m_outerSliceOffset[islice] =
GeoThreeVector(0., 0., m_outerWheelZ[islice] + dz);
733 double innerLipPosition1,
734 double innerLipLength2,
735 double innerLipPosition2)
737 double dx,
dy, dz, xoffset, yoffset, zoffset;
743 dx = 0.5*m_innerAbsorberThickness;
744 dy = 0.5*innerLipLength1;
745 dz = 0.5*m_innerLipWidth;
746 name = m_nameInnerWheel + m_nameAbsorber + m_nameSuffix[iblade];
747 solid =
new GeoBox(
dx,
dy, dz);
748 m_innerAbsorber[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialSteel));
750 name = m_nameInnerWheel + m_nameGlue + m_nameSuffix[iblade];
751 solid =
new GeoBox(
dx*m_innerGlueRatio,
dy, dz);
752 m_innerGlue[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialGlue));
754 name = m_nameInnerWheel + m_nameLead + m_nameSuffix[iblade];
755 solid =
new GeoBox(
dx*m_innerLeadRatio,
dy, dz);
756 m_innerLead[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialLead));
758 name = m_nameInnerWheel + m_nameElectrode + m_nameSuffix[iblade];
759 dx = 0.5*m_innerElectrodeThickness;
760 solid =
new GeoBox(
dx,
dy, dz);
761 m_innerElectrode[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialKapton));
765 yoffset = m_innerWheelRmin[1] + innerLipPosition1;
766 zoffset = m_innerWheelZmin + dz;
767 m_innerAbsorberOffset[iblade] =
GeoThreeVector(xoffset, yoffset, zoffset);
768 m_innerElectrodeOffset[iblade] =
GeoThreeVector(xoffset, yoffset, zoffset);
771 iblade = s_innerNoBlades - 1;
772 dx = 0.5*m_innerAbsorberThickness;
773 dy = 0.5*innerLipLength2;
774 dz = 0.5*m_innerLipWidth;
775 name = m_nameInnerWheel + m_nameAbsorber + m_nameSuffix[iblade];
776 solid =
new GeoBox(
dx,
dy, dz);
777 m_innerAbsorber[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialSteel));
779 name = m_nameInnerWheel + m_nameGlue + m_nameSuffix[iblade];
780 solid =
new GeoBox(
dx*m_innerGlueRatio,
dy, dz);
781 m_innerGlue[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialGlue));
783 name = m_nameInnerWheel + m_nameLead + m_nameSuffix[iblade];
784 solid =
new GeoBox(
dx*m_innerLeadRatio,
dy, dz);
785 m_innerLead[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialLead));
787 name = m_nameInnerWheel + m_nameElectrode + m_nameSuffix[iblade];
788 dx = 0.5*m_innerElectrodeThickness;
789 solid =
new GeoBox(
dx,
dy, dz);
790 m_innerElectrode[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialKapton));
794 yoffset = m_innerWheelRmin[s_innerNoBlades - 1] + innerLipPosition2;
795 zoffset = m_innerWheelZmax - dz;
796 m_innerAbsorberOffset[iblade] =
GeoThreeVector(xoffset, yoffset, zoffset);
797 m_innerElectrodeOffset[iblade] =
GeoThreeVector(xoffset, yoffset, zoffset);
806 double outerLipPosition1,
807 double outerLipLength2,
808 double outerLipPosition2)
810 double dx,
dy, dz, xoffset, yoffset, zoffset;
816 dx = 0.5*m_outerAbsorberThickness;
817 dy = 0.5*outerLipLength1;
818 dz = 0.5*m_outerLipWidth;
819 name = m_nameOuterWheel + m_nameAbsorber + m_nameSuffix[iblade];
820 solid =
new GeoBox(
dx,
dy, dz);
821 m_outerAbsorber[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialSteel));
823 name = m_nameOuterWheel + m_nameGlue + m_nameSuffix[iblade];
824 solid =
new GeoBox(
dx*m_outerGlueRatio,
dy, dz);
825 m_outerGlue[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialGlue));
827 name = m_nameOuterWheel + m_nameLead + m_nameSuffix[iblade];
828 solid =
new GeoBox(
dx*m_outerLeadRatio,
dy, dz);
829 m_outerLead[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialLead));
831 name = m_nameOuterWheel + m_nameElectrode + m_nameSuffix[iblade];
832 dx = 0.5*m_outerElectrodeThickness;
833 solid =
new GeoBox(
dx,
dy, dz);
834 m_outerElectrode[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialKapton));
838 yoffset = m_outerWheelRmin[1] + outerLipPosition1;
839 zoffset = m_outerWheelZmin + dz;
840 m_outerAbsorberOffset[iblade] =
GeoThreeVector(xoffset, yoffset, zoffset);
841 m_outerElectrodeOffset[iblade] =
GeoThreeVector(xoffset, yoffset, zoffset);
844 iblade = s_outerNoBlades - 1;
845 dx = 0.5*m_outerAbsorberThickness;
846 dy = 0.5*outerLipLength2;
847 dz = 0.5*m_outerLipWidth;
848 name = m_nameOuterWheel + m_nameAbsorber + m_nameSuffix[iblade];
849 solid =
new GeoBox(
dx,
dy, dz);
850 m_outerAbsorber[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialSteel));
852 name = m_nameOuterWheel + m_nameGlue + m_nameSuffix[iblade];
853 solid =
new GeoBox(
dx*m_outerGlueRatio,
dy, dz);
854 m_outerGlue[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialGlue));
856 name = m_nameOuterWheel + m_nameLead + m_nameSuffix[iblade];
857 solid =
new GeoBox(
dx*m_outerLeadRatio,
dy, dz);
858 m_outerLead[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialLead));
860 name = m_nameOuterWheel + m_nameElectrode + m_nameSuffix[iblade];
861 dx = 0.5*m_outerElectrodeThickness;
862 solid =
new GeoBox(
dx,
dy, dz);
863 m_outerElectrode[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialKapton));
867 yoffset = m_outerWheelRmin[s_outerNoBlades -1] + outerLipPosition2;
868 zoffset = m_outerWheelZmax - dz;
869 m_outerAbsorberOffset[iblade] =
GeoThreeVector(xoffset, yoffset, zoffset);
870 m_outerElectrodeOffset[iblade] =
GeoThreeVector(xoffset, yoffset, zoffset);
885 for (
int iblade = 1; iblade < s_innerNoBlades - 1; ++iblade)
887 int icase = (iblade%2 == 0) ? 2 : 3;
888 if (iblade == 1) icase = 1;
889 if (iblade == s_innerNoBlades - 2) icase = 4;
891 double z1 = m_innerWheelZ[iblade];
892 double r1min = m_innerWheelRmin[iblade];
893 double r1max = m_innerWheelRmax[iblade];
894 double z2 = m_innerWheelZ[iblade + 1];
895 double r2min = m_innerWheelRmin[iblade + 1];
896 double r2max = m_innerWheelRmax[iblade + 1];
899 name = m_nameInnerWheel + m_nameAbsorber + m_nameSuffix[iblade];
900 solid = constructBlade(icase, innerCorners, 1., z1, r1min, r1max, z2, r2min, r2max);
901 m_innerAbsorber[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialSteel));
903 name = m_nameInnerWheel + m_nameGlue + m_nameSuffix[iblade];
904 solid = constructBlade(icase, innerCorners, m_innerGlueRatio, z1, r1min, r1max, z2, r2min, r2max);
905 m_innerGlue[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialGlue));
907 name = m_nameInnerWheel + m_nameLead + m_nameSuffix[iblade];
908 solid = constructBlade(icase, innerCorners, m_innerLeadRatio, z1, r1min, r1max, z2, r2min, r2max);
909 m_innerLead[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialLead));
911 name = m_nameInnerWheel + m_nameElectrode + m_nameSuffix[iblade];
912 solid = constructBlade(icase, innerElectrodeCorners, 1., z1, r1min, r1max, z2, r2min, r2max);
913 m_innerElectrode[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialKapton));
916 m_innerAbsorberOffset[iblade] =
GeoThreeVector(0., 0., (z1 + z2)/2.);
917 m_innerElectrodeOffset[iblade] =
GeoThreeVector(0., 0., (z1 + z2)/2.);
933 for (
int iblade = 1; iblade < s_outerNoBlades - 1; ++iblade)
935 int icase = (iblade%2 == 0) ? 2 : 3;
936 if (iblade == 1) icase = 1;
937 if (iblade == s_outerNoBlades - 2) icase = 4;
939 double z1 = m_outerWheelZ[iblade];
940 double r1min = m_outerWheelRmin[iblade];
941 double r1max = m_outerWheelRmax[iblade];
942 double z2 = m_outerWheelZ[iblade + 1];
943 double r2min = m_outerWheelRmin[iblade + 1];
944 double r2max = m_outerWheelRmax[iblade + 1];
947 name = m_nameOuterWheel + m_nameAbsorber + m_nameSuffix[iblade];
948 solid = constructBlade(icase, outerCorners, 1., z1, r1min, r1max, z2, r2min, r2max);
949 m_outerAbsorber[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialSteel));
951 name = m_nameOuterWheel + m_nameGlue + m_nameSuffix[iblade];
952 solid = constructBlade(icase, outerCorners, m_outerGlueRatio, z1, r1min, r1max, z2, r2min, r2max);
953 m_outerGlue[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialGlue));
955 name = m_nameOuterWheel + m_nameLead + m_nameSuffix[iblade];
956 solid = constructBlade(icase, outerCorners, m_outerLeadRatio, z1, r1min, r1max, z2, r2min, r2max);
957 m_outerLead[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialLead));
960 name = m_nameOuterWheel + m_nameElectrode + m_nameSuffix[iblade];
961 solid = constructBlade(icase, outerElectrodeCorners, 1., z1, r1min, r1max, z2, r2min, r2max);
962 m_outerElectrode[iblade] =
new GeoPhysVol(
new GeoLogVol(
name, solid, m_materialKapton));
965 m_outerAbsorberOffset[iblade] =
GeoThreeVector(0., 0., (z1 + z2)/2.);
966 m_outerElectrodeOffset[iblade] =
GeoThreeVector(0., 0., (z1 + z2)/2.);
976 for (
int iblade = 0; iblade < s_innerNoBlades; ++iblade)
978 m_innerGlue[iblade]->add(m_innerLead[iblade]);
979 m_innerAbsorber[iblade]->add(m_innerGlue[iblade]);
989 for (
int iblade = 0; iblade < s_outerNoBlades; ++iblade)
991 m_outerGlue[iblade]->add(m_outerLead[iblade]);
992 m_outerAbsorber[iblade]->add(m_outerGlue[iblade]);
1002 if (!makeSlices)
return;
1003 for (
int islice = 0; islice < s_innerNoBlades; ++islice)
1005 double x = m_innerSliceOffset[islice].x();
1006 double y = m_innerSliceOffset[islice].y();
1007 double z = m_innerSliceOffset[islice].z();
1008 m_innerWheel->add(
new GeoTransform(GeoTrf::Translate3D(
x,
y,
z)));
1009 m_innerWheel->add(m_innerSlice[islice]);
1019 if (!makeSlices)
return;
1020 for (
int islice = 0; islice < s_outerNoBlades; ++islice)
1022 double x = m_outerSliceOffset[islice].x();
1023 double y = m_outerSliceOffset[islice].y();
1024 double z = m_outerSliceOffset[islice].z();
1025 m_outerWheel->add(
new GeoTransform(GeoTrf::Translate3D(
x,
y,
z)));
1026 m_outerWheel->add(m_outerSlice[islice]);
1039 int nphi = (makeSectors) ? m_innerNoElectrodes/innerNoSectors : m_innerNoElectrodes;
1040 double dphi =
SI::twopi/m_innerNoElectrodes;
1041 GeoPhysVol* mother =
nullptr;
1044 for (
int iphi = 0; iphi < nphi; ++iphi)
1047 int copyNo = iphi + 1;
1048 for (
int iblade = 0; iblade < s_innerNoBlades; ++iblade)
1050 if (makeSlices) mother = m_innerSlice[iblade];
1051 if (makeSectors) mother = m_innerSector[iblade];
1052 if (makeSlices || makeSectors)
1054 double x = m_innerElectrodeOffset[iblade].x();
1055 double y = m_innerElectrodeOffset[iblade].y();
1057 GeoTrf::Translate3D translation(
x,
y,
z);
1058 mother->add(
new GeoIdentifierTag(copyNo));
1059 mother->add(
new GeoTransform(
rotation*translation));
1060 mother->add(m_innerElectrode[iblade]);
1064 double x = m_innerElectrodeOffset[iblade].x();
1065 double y = m_innerElectrodeOffset[iblade].y();
1066 double z = m_innerElectrodeOffset[iblade].z();
1067 GeoTrf::Translate3D translation(
x,
y,
z);
1068 m_innerWheel->add(
new GeoIdentifierTag(copyNo));
1069 m_innerWheel->add(
new GeoTransform(
rotation*translation));
1070 m_innerWheel->add(m_innerElectrode[iblade]);
1076 for (
int iphi = 0; iphi < nphi; ++iphi)
1079 int copyNo = iphi + 1;
1080 for (
int iblade = 0; iblade < s_innerNoBlades; ++iblade)
1082 if (makeSlices) mother = m_innerSlice[iblade];
1083 if (makeSectors) mother = m_innerSector[iblade];
1084 if (makeSlices || makeSectors)
1086 double x = m_innerAbsorberOffset[iblade].x();
1087 double y = m_innerAbsorberOffset[iblade].y();
1089 GeoTrf::Translate3D translation(
x,
y,
z);
1090 mother->add(
new GeoIdentifierTag(copyNo));
1091 mother->add(
new GeoTransform(
rotation*translation));
1092 mother->add(m_innerAbsorber[iblade]);
1096 double x = m_innerAbsorberOffset[iblade].x();
1097 double y = m_innerAbsorberOffset[iblade].y();
1098 double z = m_innerAbsorberOffset[iblade].z();
1099 GeoTrf::Translate3D translation(
x,
y,
z);
1100 m_innerWheel->add(
new GeoIdentifierTag(copyNo));
1101 m_innerWheel->add(
new GeoTransform(
rotation*translation));
1102 m_innerWheel->add(m_innerAbsorber[iblade]);
1117 int nphi = (makeSectors) ? m_outerNoElectrodes/outerNoSectors : m_outerNoElectrodes;
1118 double dphi =
SI::twopi/m_outerNoElectrodes;
1119 GeoPhysVol* mother =
nullptr;
1122 for (
int iphi = 0; iphi < nphi; ++iphi)
1125 int copyNo = iphi + 1;
1126 for (
int iblade = 0; iblade < s_outerNoBlades; ++iblade)
1128 if (makeSlices) mother = m_outerSlice[iblade];
1129 if (makeSectors) mother = m_outerSector[iblade];
1130 if (makeSlices || makeSectors)
1132 double x = m_outerElectrodeOffset[iblade].x();
1133 double y = m_outerElectrodeOffset[iblade].y();
1135 GeoTrf::Translate3D translation(
x,
y,
z);
1136 mother->add(
new GeoIdentifierTag(copyNo));
1137 mother->add(
new GeoTransform(
rotation*translation));
1138 mother->add(m_outerElectrode[iblade]);
1142 double x = m_outerElectrodeOffset[iblade].x();
1143 double y = m_outerElectrodeOffset[iblade].y();
1144 double z = m_outerElectrodeOffset[iblade].z();
1145 GeoTrf::Translate3D translation(
x,
y,
z);
1146 m_outerWheel->add(
new GeoIdentifierTag(copyNo));
1147 m_outerWheel->add(
new GeoTransform(
rotation*translation));
1148 m_outerWheel->add(m_outerElectrode[iblade]);
1154 for (
int iphi = 0; iphi < nphi; ++iphi)
1157 int copyNo = iphi + 1;
1158 for (
int iblade = 0; iblade < s_outerNoBlades; ++iblade)
1160 if (makeSlices) mother = m_outerSlice[iblade];
1161 if (makeSectors) mother = m_outerSector[iblade];
1162 if (makeSlices || makeSectors)
1164 double x = m_outerAbsorberOffset[iblade].x();
1165 double y = m_outerAbsorberOffset[iblade].y();
1167 GeoTrf::Translate3D translation(
x,
y,
z);
1168 mother->add(
new GeoIdentifierTag(copyNo));
1169 mother->add(
new GeoTransform(
rotation*translation));
1170 mother->add(m_outerAbsorber[iblade]);
1174 double x = m_outerAbsorberOffset[iblade].x();
1175 double y = m_outerAbsorberOffset[iblade].y();
1176 double z = m_outerAbsorberOffset[iblade].z();
1177 GeoTrf::Translate3D translation(
x,
y,
z);
1178 m_outerWheel->add(
new GeoIdentifierTag(copyNo));
1179 m_outerWheel->add(
new GeoTransform(
rotation*translation));
1180 m_outerWheel->add(m_outerAbsorber[iblade]);
1193 bool makeSectors =
false;
1194 int innerNoSectors = 0;
1198 setInnerWheelSlices();
1201 double innerUncutBladeWidthMin, innerUncutBladeWidthMax;
1202 double innerLipLength1, innerLipPosition1;
1203 double innerLipLength2, innerLipPosition2;
1204 getInnerAbsorberData(innerUncutBladeWidthMin, innerUncutBladeWidthMax,
1205 innerLipLength1, innerLipPosition1,
1206 innerLipLength2, innerLipPosition2);
1207 innerUncutBladeWidthMin *= m_kContraction;
1208 innerUncutBladeWidthMax *= m_kContraction;
1209 innerLipLength1 *= m_kContraction;
1210 innerLipPosition1 *= m_kContraction;
1211 innerLipLength2 *= m_kContraction;
1212 innerLipPosition2 *= m_kContraction;
1216 double wmin, wmax, thickness, rmin, rmax, zdel;
1220 wmin = innerUncutBladeWidthMin;
1221 wmax = innerUncutBladeWidthMax;
1222 thickness = m_innerAbsorberThickness;
1223 rmin = m_innerWheelRmin[1];
1224 rmax = m_innerWheelRmax[s_innerNoBlades - 1];
1225 zdel = m_innerHalfWaveWidth;
1226 getBladeCorners(wmin, wmax, thickness, rmin, rmax, zdel, innerCorners);
1230 thickness = m_innerElectrodeThickness;
1231 getBladeCorners(wmin, wmax, thickness, rmin, rmax, zdel, innerElectrodeCorners);
1237 m_innerGlueRatio = (m_innerLeadThickness + 2*m_innerGlueThickness)/m_innerAbsorberThickness;
1238 m_innerLeadRatio = m_innerLeadThickness/m_innerAbsorberThickness;
1241 constructInnerLips(innerLipLength1, innerLipPosition1, innerLipLength2, innerLipPosition2);
1244 constructInnerBlades(innerCorners, innerElectrodeCorners);
1247 constructInnerSlices();
1254 placeInnerGlueAndLead();
1255 placeInnerSlices(makeSlices);
1257 placeInnerAccordion(innerNoSectors, makeSlices, makeSectors);
1267 bool makeSectors =
false;
1268 int outerNoSectors = 0;
1272 setOuterWheelSlices();
1275 double outerUncutBladeWidthMin, outerUncutBladeWidthMax;
1276 double outerLipLength1, outerLipPosition1;
1277 double outerLipLength2, outerLipPosition2;
1278 getOuterAbsorberData(outerUncutBladeWidthMin, outerUncutBladeWidthMax,
1279 outerLipLength1, outerLipPosition1,
1280 outerLipLength2, outerLipPosition2);
1281 outerUncutBladeWidthMin *= m_kContraction;
1282 outerUncutBladeWidthMax *= m_kContraction;
1283 outerLipLength1 *= m_kContraction;
1284 outerLipPosition1 *= m_kContraction;
1285 outerLipLength2 *= m_kContraction;
1286 outerLipPosition2 *= m_kContraction;
1290 double wmin, wmax, thickness, rmin, rmax, zdel;
1294 wmin = outerUncutBladeWidthMin;
1295 wmax = outerUncutBladeWidthMax;
1296 thickness = m_outerAbsorberThickness;
1297 rmin = m_outerWheelRmin[1];
1298 rmax = m_outerWheelRmax[s_outerNoBlades - 1];
1299 zdel = m_outerHalfWaveWidth;
1300 getBladeCorners(wmin, wmax, thickness, rmin, rmax, zdel, outerCorners);
1304 thickness = m_outerElectrodeThickness;
1305 getBladeCorners(wmin, wmax, thickness, rmin, rmax, zdel, outerElectrodeCorners);
1311 m_outerGlueRatio = (m_outerLeadThickness + 2*m_outerGlueThickness)/m_outerAbsorberThickness;
1312 m_outerLeadRatio = m_outerLeadThickness/m_outerAbsorberThickness;
1315 constructOuterLips(outerLipLength1, outerLipPosition1, outerLipLength2, outerLipPosition2);
1318 constructOuterBlades(outerCorners, outerElectrodeCorners);
1321 constructOuterSlices();
1328 placeOuterGlueAndLead();
1329 placeOuterSlices(makeSlices);
1331 placeOuterAccordion(outerNoSectors, makeSlices, makeSectors);