Skip to content

Commit b6c63a0

Browse files
sadekrRita Sadek
andauthored
[FT3] Modular structure for OT disks - first version of modules structure with dynamic disks paving for ALICE 3 sensors and initial material estimations (#14816)
Co-authored-by: Rita Sadek <rsadek@Ritas-MBP.dhcp.lbl.gov>
1 parent 348e9b1 commit b6c63a0

File tree

6 files changed

+967
-8
lines changed

6 files changed

+967
-8
lines changed

Detectors/Upgrades/ALICE3/FT3/simulation/CMakeLists.txt

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,14 +10,18 @@
1010
# or submit itself to any jurisdiction.
1111

1212
o2_add_library(FT3Simulation
13-
SOURCES src/FT3Layer.cxx
13+
SOURCES
14+
src/FT3Module.cxx
15+
src/FT3Layer.cxx
1416
src/Detector.cxx
1517
PUBLIC_LINK_LIBRARIES O2::FT3Base
1618
O2::ITSMFTSimulation
1719
ROOT::Physics)
1820

1921
o2_target_root_dictionary(FT3Simulation
20-
HEADERS include/FT3Simulation/Detector.h
22+
HEADERS
23+
include/FT3Simulation/FT3Module.h
24+
include/FT3Simulation/Detector.h
2125
include/FT3Simulation/FT3Layer.h)
2226

2327
o2_data_file(COPY data DESTINATION Detectors/FT3/simulation)

Detectors/Upgrades/ALICE3/FT3/simulation/include/FT3Simulation/FT3Layer.h

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
#include <TGeoManager.h> // for gGeoManager
1919
#include "Rtypes.h" // for Double_t, Int_t, Bool_t, etc
2020
#include "FT3Simulation/Detector.h" // for Detector, Detector::Model
21+
#include "FT3Simulation/FT3Module.h"
2122

2223
class TGeoVolume;
2324

@@ -57,6 +58,24 @@ class FT3Layer : public TObject
5758
/// \param motherVolume the TGeoVolume owing the volume structure
5859
virtual void createLayer(TGeoVolume* motherVolume);
5960

61+
static void initialize_mat();
62+
63+
// create layer for disk support
64+
void createSeparationLayer(TGeoVolume* motherVolume, const std::string& separationLayerName);
65+
void createSeparationLayer_waterCooling(TGeoVolume* motherVolume, const std::string& separationLayerName);
66+
67+
static TGeoMaterial* carbonFiberMat;
68+
static TGeoMedium* medCarbonFiber;
69+
70+
static TGeoMaterial* kaptonMat;
71+
static TGeoMedium* kaptonMed;
72+
73+
static TGeoMaterial* waterMat;
74+
static TGeoMedium* waterMed;
75+
76+
static TGeoMaterial* foamMat;
77+
static TGeoMedium* medFoam;
78+
6079
private:
6180
Int_t mLayerNumber = -1; ///< Current layer number
6281
Int_t mDirection; ///< Layer direction 0=Forward 1 = Backward
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
// Copyright 2019-2020 CERN and copyright holders of ALICE O2.
2+
// See https://alice-o2.web.cern.ch/copyright for details of the copyright holders.
3+
// All rights not expressly granted are reserved.
4+
//
5+
// This software is distributed under the terms of the GNU General Public
6+
// License v3 (GPL Version 3), copied verbatim in the file "COPYING".
7+
//
8+
// In applying this license CERN does not waive the privileges and immunities
9+
// granted to it by virtue of its status as an Intergovernmental Organization
10+
// or submit itself to any jurisdiction.
11+
12+
/// \file FT3Module.h
13+
/// \brief Definition of the FT3Module class
14+
15+
#ifndef FT3MODULE_H
16+
#define FT3MODULE_H
17+
18+
#include <TGeoVolume.h>
19+
#include <string>
20+
21+
class FT3Module
22+
{
23+
24+
public:
25+
static void initialize_materials();
26+
static TGeoMaterial* siliconMat;
27+
static TGeoMedium* siliconMed;
28+
static TGeoMaterial* copperMat;
29+
static TGeoMedium* copperMed;
30+
static TGeoMaterial* kaptonMat;
31+
static TGeoMedium* kaptonMed;
32+
static TGeoMaterial* epoxyMat;
33+
static TGeoMedium* epoxyMed;
34+
static TGeoMaterial* AluminumMat;
35+
static TGeoMedium* AluminumMed;
36+
37+
const char* mDetName;
38+
39+
static void createModule(double mZ, int layerNumber, int direction, double Rin, double Rout, double overlap, const std::string& face, const std::string& layout_type, TGeoVolume* motherVolume);
40+
41+
private:
42+
static void create_layout(double mZ, int layerNumber, int direction, double Rin, double Rout, double overlap, const std::string& face, const std::string& layout_type, TGeoVolume* motherVolume);
43+
};
44+
45+
#endif // FT3MODULE_H

Detectors/Upgrades/ALICE3/FT3/simulation/src/Detector.cxx

Lines changed: 19 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,8 @@
4040

4141
#include <cstdio> // for NULL, snprintf
4242

43+
#define MAX_SENSORS 2000
44+
4345
class FairModule;
4446

4547
class TGeoMedium;
@@ -729,9 +731,23 @@ void Detector::defineSensitiveVolumes()
729731
for (int direction : {0, 1}) {
730732
for (int iLayer = 0; iLayer < mNumberOfLayers; iLayer++) {
731733
volumeName = o2::ft3::GeometryTGeo::getFT3SensorPattern() + std::to_string(iLayer);
732-
v = geoManager->GetVolume(Form("%s_%d_%d", GeometryTGeo::getFT3SensorPattern(), direction, iLayer));
733-
LOG(info) << "Adding FT3 Sensitive Volume => " << v->GetName();
734-
AddSensitiveVolume(v);
734+
if (iLayer < 3) { // ML disks
735+
v = geoManager->GetVolume(Form("%s_%d_%d", GeometryTGeo::getFT3SensorPattern(), direction, iLayer));
736+
AddSensitiveVolume(v);
737+
} else { // OT disks
738+
for (int sensor_count = 0; sensor_count < MAX_SENSORS; ++sensor_count) {
739+
std::string sensor_name_front = "FT3sensor_front_" + std::to_string(iLayer) + "_" + std::to_string(direction) + "_" + std::to_string(sensor_count);
740+
std::string sensor_name_back = "FT3sensor_back_" + std::to_string(iLayer) + "_" + std::to_string(direction) + "_" + std::to_string(sensor_count);
741+
v = geoManager->GetVolume(sensor_name_front.c_str());
742+
if (v) {
743+
AddSensitiveVolume(v);
744+
}
745+
v = geoManager->GetVolume(sensor_name_back.c_str());
746+
if (v) {
747+
AddSensitiveVolume(v);
748+
}
749+
}
750+
}
735751
}
736752
}
737753
}

Detectors/Upgrades/ALICE3/FT3/simulation/src/FT3Layer.cxx

Lines changed: 179 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,10 @@
2828
#include "TMathBase.h" // for Abs
2929
#include <TMath.h> // for Sin, RadToDeg, DegToRad, Cos, Tan, etc
3030

31+
#include <TGeoBBox.h>
32+
#include <string>
3133
#include <cstdio> // for snprintf
34+
#include <cmath>
3235

3336
class TGeoMedium;
3437

@@ -40,6 +43,18 @@ ClassImp(FT3Layer);
4043

4144
FT3Layer::~FT3Layer() = default;
4245

46+
TGeoMaterial* FT3Layer::carbonFiberMat = nullptr;
47+
TGeoMedium* FT3Layer::medCarbonFiber = nullptr;
48+
49+
TGeoMaterial* FT3Layer::kaptonMat = nullptr;
50+
TGeoMedium* FT3Layer::kaptonMed = nullptr;
51+
52+
TGeoMaterial* FT3Layer::waterMat = nullptr;
53+
TGeoMedium* FT3Layer::waterMed = nullptr;
54+
55+
TGeoMaterial* FT3Layer::foamMat = nullptr;
56+
TGeoMedium* FT3Layer::medFoam = nullptr;
57+
4358
FT3Layer::FT3Layer(Int_t layerDirection, Int_t layerNumber, std::string layerName, Float_t z, Float_t rIn, Float_t rOut, Float_t Layerx2X0)
4459
{
4560
// Creates a simple parametrized EndCap layer covering the given
@@ -59,10 +74,157 @@ FT3Layer::FT3Layer(Int_t layerDirection, Int_t layerNumber, std::string layerNam
5974
LOG(info) << " Layer z = " << mZ << " ; R_in = " << mInnerRadius << " ; R_out = " << mOuterRadius << " ; x2X0 = " << mx2X0 << " ; ChipThickness = " << mChipThickness;
6075
}
6176

77+
void FT3Layer::initialize_mat()
78+
{
79+
80+
if (carbonFiberMat) {
81+
return;
82+
}
83+
84+
carbonFiberMat = new TGeoMaterial("CarbonFiber", 12.0, 6.0, 1.6);
85+
medCarbonFiber = new TGeoMedium("CarbonFiber", 1, carbonFiberMat);
86+
87+
auto* itsC = new TGeoElement("FT3_C", "Carbon", 6, 12.0107);
88+
89+
auto* itsFoam = new TGeoMixture("FT3_Foam", 1);
90+
itsFoam->AddElement(itsC, 1);
91+
itsFoam->SetDensity(0.17);
92+
93+
medFoam = new TGeoMedium("FT3_Foam", 1, itsFoam);
94+
foamMat = medFoam->GetMaterial();
95+
96+
kaptonMat = new TGeoMaterial("Kapton (cooling pipe)", 13.84, 6.88, 1.346);
97+
kaptonMed = new TGeoMedium("Kapton (cooling pipe)", 1, kaptonMat);
98+
99+
waterMat = new TGeoMaterial("Water", 18.01528, 8.0, 1.064);
100+
waterMed = new TGeoMedium("Water", 2, waterMat);
101+
}
102+
103+
static double y_circle(double x, double radius)
104+
{
105+
return (x * x < radius * radius) ? std::sqrt(radius * radius - x * x) : 0;
106+
}
107+
108+
void FT3Layer::createSeparationLayer_waterCooling(TGeoVolume* motherVolume, const std::string& separationLayerName)
109+
{
110+
111+
FT3Layer::initialize_mat();
112+
113+
double carbonFiberThickness = 0.01;
114+
double foamSpacingThickness = 0.5;
115+
116+
TGeoTube* carbonFiberLayer = new TGeoTube(mInnerRadius, mOuterRadius, carbonFiberThickness / 2);
117+
118+
// volumes
119+
TGeoVolume* carbonFiberLayerVol1 = new TGeoVolume((separationLayerName + "_CarbonFiber1").c_str(), carbonFiberLayer, medCarbonFiber);
120+
TGeoVolume* carbonFiberLayerVol2 = new TGeoVolume((separationLayerName + "_CarbonFiber2").c_str(), carbonFiberLayer, medCarbonFiber);
121+
122+
carbonFiberLayerVol1->SetLineColor(kGray + 2);
123+
carbonFiberLayerVol2->SetLineColor(kGray + 2);
124+
125+
double zSeparation = foamSpacingThickness / 2.0 + carbonFiberThickness / 2.0;
126+
127+
motherVolume->AddNode(carbonFiberLayerVol1, 1, new TGeoTranslation(0, 0, mZ - zSeparation));
128+
motherVolume->AddNode(carbonFiberLayerVol2, 1, new TGeoTranslation(0, 0, mZ + zSeparation));
129+
130+
double pipeOuterRadius = 0.20;
131+
double kaptonThickness = 0.0025;
132+
double pipeInnerRadius = pipeOuterRadius - kaptonThickness;
133+
double pipeMaxLength = mOuterRadius * 2.0;
134+
135+
int name_it = 0;
136+
137+
// positions of the pipes depending on the overlap of the sensors inactive regions: (ALICE 3 dimensions)
138+
// partial:
139+
// std::vector<double> X_pos = {-63.2, -58.4, -53.6, -48.8, -44.0, -39.199999999999996, -34.4, -29.599999999999994, -24.799999999999997, -19.999999999999993, -15.199999999999998, -10.399999999999993, -5.599999999999998, -0.7999999999999936, 4.000000000000002, 8.800000000000006, 13.600000000000001, 18.400000000000006, 23.200000000000003, 28.000000000000007, 32.800000000000004, 37.60000000000001, 42.400000000000006, 47.20000000000001, 52.00000000000001, 56.80000000000001, 61.60000000000001, 66.4};
140+
// complete:
141+
// std::vector<double> X_pos = {-63.4, -58.8, -54.199999999999996, -49.599999999999994, -44.99999999999999, -40.39999999999999, -35.79999999999999, -31.199999999999992, -26.59999999999999, -21.999999999999993, -17.39999999999999, -12.799999999999994, -8.199999999999992, -3.5999999999999934, 1.000000000000008, 5.600000000000007, 10.200000000000008, 14.800000000000008, 19.40000000000001, 24.000000000000007, 28.60000000000001, 33.20000000000001, 37.80000000000001, 42.40000000000001, 47.000000000000014, 51.600000000000016, 56.20000000000002, 60.80000000000002, 65.40000000000002};
142+
std::vector<double> X_pos = {-62.3168, -57.9836, -53.650400000000005, -49.317200000000014, -44.984000000000016, -40.65080000000002, -36.31760000000002, -31.984400000000026, -27.65120000000003, -23.318000000000037, -18.98480000000004, -14.651600000000043, -10.318400000000047, -5.98520000000005, -1.6520000000000519, 2.6811999999999445, 7.014399999999941, 11.347599999999936, 15.680799999999934, 20.01399999999993, 24.347199999999926, 28.68039999999992, 33.013599999999926, 37.34679999999992, 41.980000000000004, 46.613200000000006, 51.246399999999994, 55.87960000000001, 60.5128};
143+
144+
for (double xPos : X_pos) {
145+
146+
double pipeLength = pipeMaxLength;
147+
double yMax = 0.0;
148+
149+
TGeoRotation* rotation = new TGeoRotation();
150+
rotation->RotateX(90);
151+
152+
if (std::abs(xPos) < mInnerRadius) {
153+
double yInner = std::abs(y_circle(xPos, mInnerRadius));
154+
double yOuter = std::abs(y_circle(xPos, mOuterRadius));
155+
156+
yMax = 2 * yOuter;
157+
pipeLength = yMax;
158+
159+
double positiveYLength = yOuter - yInner;
160+
161+
TGeoVolume* kaptonPipePos = new TGeoVolume((separationLayerName + "_KaptonPipePos_" + std::to_string(name_it)).c_str(), new TGeoTube(pipeInnerRadius, pipeOuterRadius, positiveYLength / 2), kaptonMed);
162+
kaptonPipePos->SetLineColor(kGray);
163+
TGeoVolume* waterVolumePos = new TGeoVolume((separationLayerName + "_WaterVolumePos_" + std::to_string(name_it)).c_str(), new TGeoTube(0.0, pipeInnerRadius, positiveYLength / 2), waterMed);
164+
waterVolumePos->SetLineColor(kBlue);
165+
166+
motherVolume->AddNode(waterVolumePos, 1, new TGeoCombiTrans(xPos, (yInner + yOuter) / 2.0, mZ, rotation));
167+
168+
TGeoVolume* kaptonPipeNeg = new TGeoVolume((separationLayerName + "_KaptonPipeNeg_" + std::to_string(name_it)).c_str(), new TGeoTube(pipeInnerRadius, pipeOuterRadius, positiveYLength / 2), kaptonMed);
169+
kaptonPipeNeg->SetLineColor(kGray);
170+
TGeoVolume* waterVolumeNeg = new TGeoVolume((separationLayerName + "_WaterVolumeNeg_" + std::to_string(name_it)).c_str(), new TGeoTube(0.0, pipeInnerRadius, positiveYLength / 2), waterMed);
171+
waterVolumeNeg->SetLineColor(kBlue);
172+
173+
motherVolume->AddNode(waterVolumeNeg, 1, new TGeoCombiTrans(xPos, -(yInner + yOuter) / 2.0, mZ, rotation));
174+
175+
motherVolume->AddNode(kaptonPipePos, 1, new TGeoCombiTrans(xPos, (yInner + yOuter) / 2.0, mZ, rotation));
176+
motherVolume->AddNode(kaptonPipeNeg, 1, new TGeoCombiTrans(xPos, -(yInner + yOuter) / 2.0, mZ, rotation));
177+
178+
} else {
179+
180+
double yOuter = std::abs(y_circle(xPos, mOuterRadius));
181+
yMax = 2 * yOuter;
182+
pipeLength = yMax;
183+
184+
TGeoVolume* kaptonPipe = new TGeoVolume((separationLayerName + "_KaptonPipe_" + std::to_string(name_it)).c_str(), new TGeoTube(pipeInnerRadius, pipeOuterRadius, pipeLength / 2), kaptonMed);
185+
kaptonPipe->SetLineColor(kGray);
186+
TGeoVolume* waterVolume = new TGeoVolume((separationLayerName + "_WaterVolume_" + std::to_string(name_it)).c_str(), new TGeoTube(0.0, pipeInnerRadius, pipeLength / 2), waterMed);
187+
waterVolume->SetLineColor(kBlue);
188+
189+
motherVolume->AddNode(waterVolume, 1, new TGeoCombiTrans(xPos, 0, mZ, rotation));
190+
motherVolume->AddNode(kaptonPipe, 1, new TGeoCombiTrans(xPos, 0, mZ, rotation));
191+
}
192+
193+
name_it++;
194+
}
195+
}
196+
197+
void FT3Layer::createSeparationLayer(TGeoVolume* motherVolume, const std::string& separationLayerName)
198+
{
199+
200+
FT3Layer::initialize_mat();
201+
202+
double carbonFiberThickness = 0.01;
203+
double foamSpacingThickness = 1.0;
204+
205+
TGeoTube* carbonFiberLayer = new TGeoTube(mInnerRadius, mOuterRadius, carbonFiberThickness / 2);
206+
TGeoTube* foamLayer = new TGeoTube(mInnerRadius, mOuterRadius, foamSpacingThickness / 2);
207+
208+
// volumes
209+
TGeoVolume* carbonFiberLayerVol1 = new TGeoVolume((separationLayerName + "_CarbonFiber1").c_str(), carbonFiberLayer, medCarbonFiber);
210+
TGeoVolume* foamLayerVol = new TGeoVolume((separationLayerName + "_Foam").c_str(), foamLayer, medFoam);
211+
TGeoVolume* carbonFiberLayerVol2 = new TGeoVolume((separationLayerName + "_CarbonFiber2").c_str(), carbonFiberLayer, medCarbonFiber);
212+
213+
carbonFiberLayerVol1->SetLineColor(kGray + 2);
214+
foamLayerVol->SetLineColor(kBlack);
215+
foamLayerVol->SetFillColorAlpha(kBlack, 1.0);
216+
carbonFiberLayerVol2->SetLineColor(kGray + 2);
217+
218+
double zSeparation = foamSpacingThickness / 2.0 + carbonFiberThickness / 2.0;
219+
220+
motherVolume->AddNode(carbonFiberLayerVol1, 1, new TGeoTranslation(0, 0, mZ - zSeparation));
221+
motherVolume->AddNode(foamLayerVol, 1, new TGeoTranslation(0, 0, mZ));
222+
motherVolume->AddNode(carbonFiberLayerVol2, 1, new TGeoTranslation(0, 0, mZ + zSeparation));
223+
}
224+
62225
void FT3Layer::createLayer(TGeoVolume* motherVolume)
63226
{
64-
if (mLayerNumber >= 0) {
65-
// Create tube, set sensitive volume, add to mother volume
227+
if (mLayerNumber >= 0 && mLayerNumber < 3) {
66228

67229
std::string chipName = o2::ft3::GeometryTGeo::getFT3ChipPattern() + std::to_string(mLayerNumber),
68230
sensName = Form("%s_%d_%d", GeometryTGeo::getFT3SensorPattern(), mDirection, mLayerNumber);
@@ -93,6 +255,20 @@ void FT3Layer::createLayer(TGeoVolume* motherVolume)
93255
LOG(info) << "Inserting " << layerVol->GetName() << " inside " << motherVolume->GetName();
94256
motherVolume->AddNode(layerVol, 1, FwdDiskCombiTrans);
95257

96-
return;
258+
} else if (mLayerNumber >= 3) {
259+
260+
FT3Module module;
261+
262+
// layer structure
263+
std::string frontLayerName = o2::ft3::GeometryTGeo::getFT3LayerPattern() + std::to_string(mDirection) + std::to_string(mLayerNumber) + "_Front";
264+
std::string backLayerName = o2::ft3::GeometryTGeo::getFT3LayerPattern() + std::to_string(mDirection) + std::to_string(mLayerNumber) + "_Back";
265+
std::string separationLayerName = "FT3SeparationLayer" + std::to_string(mDirection) + std::to_string(mLayerNumber);
266+
267+
// createSeparationLayer_waterCooling(motherVolume, separationLayerName);
268+
createSeparationLayer(motherVolume, separationLayerName);
269+
270+
// create disk faces
271+
module.createModule(mZ, mLayerNumber, mDirection, mInnerRadius, mOuterRadius, 0., "front", "rectangular", motherVolume);
272+
module.createModule(mZ, mLayerNumber, mDirection, mInnerRadius, mOuterRadius, 0., "back", "rectangular", motherVolume);
97273
}
98274
}

0 commit comments

Comments
 (0)