134 TGeoMedium* medSi = gGeoManager->GetMedium(
"TF3_SILICON$");
135 TGeoMedium* medAir = gGeoManager->GetMedium(
"TF3_AIR$");
136 LOGP(info,
"Media: {} {}", (
void*)medSi, (
void*)medAir);
144 TGeoVolume* sensVol =
new TGeoVolume(sensName, sensor, medSi);
145 TGeoVolume* chipVol =
new TGeoVolume(chipName, chip, medSi);
146 TGeoVolume* layerVol =
new TGeoVolume(
mLayerName.c_str(),
layer, medAir);
151 LOGP(info,
"Inserting Barrel {} in {} ", sensVol->GetName(), chipVol->GetName());
153 chipVol->AddNode(sensVol, 1,
nullptr);
155 LOGP(info,
"Inserting Barrel {} in {} ", chipVol->GetName(), layerVol->GetName());
156 layerVol->AddNode(chipVol, 1,
nullptr);
158 LOGP(info,
"Inserting Barrel {} in {} ", layerVol->GetName(), motherVolume->GetName());
159 motherVolume->AddNode(layerVol, 1,
nullptr);
165 const double staveSizeX =
mStaves.second;
171 const double u0 = -avgRadius * std::cos(
alpha);
172 const double v0 = avgRadius * std::sin(
alpha);
173 const double uClamped = std::max(-0.5 * staveSizeY, std::min(0.5 * staveSizeY, u0));
174 const double vClamped = std::max(-0.5 * staveSizeX, std::min(0.5 * staveSizeX,
v0));
175 const double radiusMin = std::hypot(uClamped - u0, vClamped -
v0);
177 const double uCorners[4] = {-0.5 * staveSizeY, 0.5 * staveSizeY, 0.5 * staveSizeY, -0.5 * staveSizeY};
178 const double vCorners[4] = {-0.5 * staveSizeX, -0.5 * staveSizeX, 0.5 * staveSizeX, 0.5 * staveSizeX};
179 double radiusMax = 0.0;
180 for (
int i = 0;
i < 4; ++
i) {
181 radiusMax = std::max(radiusMax, std::hypot(uCorners[
i] - u0, vCorners[
i] -
v0));
183 TGeoTube*
layer =
new TGeoTube(radiusMin, radiusMax,
mZLength / 2);
184 TGeoVolume* layerVol =
new TGeoVolume(
mLayerName.c_str(),
layer, medAir);
188 TGeoBBox* stave =
new TGeoBBox(staveSizeX * 0.5, staveSizeY * 0.5, staveSizeZ * 0.5);
189 TGeoVolume* staveVol =
new TGeoVolume(staveName, stave, medAir);
193 const int modulesPerStaveX = 1;
194 const double moduleSizeX = staveSizeX / modulesPerStaveX;
195 const double moduleSizeY = staveSizeY;
197 TGeoBBox*
module = new TGeoBBox(moduleSizeX * 0.5, moduleSizeY * 0.5, moduleSizeZ * 0.5);
198 TGeoVolume* moduleVol =
new TGeoVolume(moduleName, module, medAir);
202 const int chipsPerModuleX = 2;
203 const int chipsPerModuleZ = 4;
204 const double chipSizeX = moduleSizeX / chipsPerModuleX;
205 const double chipSizeY = moduleSizeY;
206 const double chipSizeZ = moduleSizeZ / chipsPerModuleZ;
207 TGeoBBox* chip =
new TGeoBBox(chipSizeX * 0.5, chipSizeY * 0.5, chipSizeZ * 0.5);
208 TGeoVolume* chipVol =
new TGeoVolume(chipName, chip, medSi);
212 const int sensorsPerChipX = 1;
213 const int sensorsPerChipZ = 1;
214 const double sensorSizeX = chipSizeX / sensorsPerChipX;
216 const double sensorSizeZ = chipSizeZ / sensorsPerChipZ;
217 TGeoBBox* sensor =
new TGeoBBox(sensorSizeX * 0.5, sensorSizeY * 0.5, sensorSizeZ * 0.5);
218 TGeoVolume* sensVol =
new TGeoVolume(sensName, sensor, medSi);
223 for (
int i = 0;
i < sensorsPerChipX; ++
i) {
224 for (
int j = 0;
j < sensorsPerChipZ; ++
j) {
225 LOGP(info,
"iTOF: Creating sensor {}/{} for chip {}/{}",
i + 1, sensorsPerChipX,
j + 1, sensorsPerChipZ);
226 auto* translation =
new TGeoTranslation((
i + 0.5) * sensorSizeX - 0.5 * chipSizeX,
227 0.5 * chipSizeY - 0.5 * sensorSizeY,
228 (
j + 0.5) * sensorSizeZ - 0.5 * chipSizeZ);
229 chipVol->AddNode(sensVol, 1 +
i * sensorsPerChipZ +
j, translation);
234 for (
int i = 0;
i < chipsPerModuleX; ++
i) {
235 for (
int j = 0;
j < chipsPerModuleZ; ++
j) {
236 LOGP(info,
"iTOF: Creating chip {}/{} for module {}/{}",
i + 1, chipsPerModuleX,
j + 1, chipsPerModuleZ);
237 auto* translation =
new TGeoTranslation((
i + 0.5) * chipSizeX - 0.5 * moduleSizeX, 0, (
j + 0.5) * chipSizeZ - 0.5 * moduleSizeZ);
238 moduleVol->AddNode(chipVol, 1 +
i * chipsPerModuleZ +
j, translation);
243 for (
int i = 0;
i < modulesPerStaveX; ++
i) {
245 LOGP(info,
"iTOF: Creating module {}/{} for stave {}/{}",
i + 1, modulesPerStaveX,
j + 1,
mModulesPerStave);
246 auto* translation =
new TGeoTranslation((
i + 0.5) * moduleSizeX - 0.5 * staveSizeX, 0, (
j + 0.5) * moduleSizeZ - 0.5 * staveSizeZ);
253 LOGP(info,
"iTOF: Creating stave {}/{} for layer {}",
i + 1,
mStaves.first, layerVol->GetName());
254 const double phi = TMath::TwoPi() *
i /
mStaves.first;
255 const double x = avgRadius * TMath::Cos(phi);
256 const double y = avgRadius * TMath::Sin(phi);
257 auto* rotation =
new TGeoRotation(Form(
"segmentRot%d",
i + 1), phi * TMath::RadToDeg() + 90 +
mTiltAngle, 0, 0);
260 LOGP(info,
"Inserting Barrel {} in {} ", chipVol->GetName(), layerVol->GetName());
263 LOGP(info,
"Inserting Barrel {} in {} at r={} cm", layerVol->GetName(), motherVolume->GetName(), avgRadius);
264 motherVolume->AddNode(layerVol, 1,
nullptr);
281 TGeoMedium* medSi = gGeoManager->GetMedium(
"TF3_SILICON$");
282 TGeoMedium* medAir = gGeoManager->GetMedium(
"TF3_AIR$");
283 LOGP(info,
"Media: {} {}", (
void*)medSi, (
void*)medAir);
291 TGeoVolume* sensVol =
new TGeoVolume(sensName, sensor, medSi);
292 TGeoVolume* chipVol =
new TGeoVolume(chipName, chip, medSi);
293 TGeoVolume* layerVol =
new TGeoVolume(
mLayerName.c_str(),
layer, medAir);
298 LOGP(info,
"Inserting {} in {} ", sensVol->GetName(), chipVol->GetName());
300 chipVol->AddNode(sensVol, 1,
nullptr);
302 LOGP(info,
"Inserting {} in {} ", chipVol->GetName(), layerVol->GetName());
303 layerVol->AddNode(chipVol, 1,
nullptr);
305 LOGP(info,
"Inserting {} in {} ", layerVol->GetName(), motherVolume->GetName());
306 motherVolume->AddNode(layerVol, 1,
nullptr);
311 const double subStavesDistanceY = 0.3;
312 const double subStavesOverlapX = 1.1;
316 const double staveSizeX =
mStaves.second;
319 const double subStaveSizeX = 0.5 *
mStaves.second + 0.5 * subStavesOverlapX;
321 const double subStaveSizeZ =
mZLength;
325 const double u0 = -avgRadius * std::cos(
alpha);
326 const double v0 = avgRadius * std::sin(
alpha);
327 const double uClamped = std::max(-0.5 * staveSizeY, std::min(0.5 * staveSizeY, u0));
328 const double vClamped = std::max(-0.5 * staveSizeX, std::min(0.5 * staveSizeX,
v0));
329 const double radiusMin = std::hypot(uClamped - u0, vClamped -
v0);
331 const double uCorners[4] = {-0.5 * staveSizeY, 0.5 * staveSizeY, 0.5 * staveSizeY, -0.5 * staveSizeY};
332 const double vCorners[4] = {-0.5 * staveSizeX, -0.5 * staveSizeX, 0.5 * staveSizeX, 0.5 * staveSizeX};
333 double radiusMax = 0.0;
334 for (
int i = 0;
i < 4; ++
i) {
335 radiusMax = std::max(radiusMax, std::hypot(uCorners[
i] - u0, vCorners[
i] -
v0));
337 TGeoTube*
layer =
new TGeoTube(radiusMin, radiusMax,
mZLength / 2);
338 TGeoVolume* layerVol =
new TGeoVolume(
mLayerName.c_str(),
layer, medAir);
342 TGeoBBox* stave =
new TGeoBBox(staveSizeX * 0.5, staveSizeY * 0.5, staveSizeZ * 0.5);
343 TGeoVolume* staveVol =
new TGeoVolume(staveName, stave, medAir);
347 TGeoBBox* subStave =
new TGeoBBox(subStaveSizeX * 0.5, subStaveSizeY * 0.5, subStaveSizeZ * 0.5);
348 TGeoVolume* subStaveVol =
new TGeoVolume(subStaveName, subStave, medAir);
354 const int modulesPerSubStaveX = 1;
355 if (modulesPerSubStave % modulesPerSubStaveX != 0) {
356 LOG(fatal) <<
"Invalid oTOF module layout: total modules per stave " << modulesPerSubStave
357 <<
" is not divisible by modulesPerStaveX=" << modulesPerSubStaveX;
359 const int modulesPerSubStaveZ = modulesPerSubStave / modulesPerSubStaveX;
360 const double moduleSizeX = subStaveSizeX / modulesPerSubStaveX;
361 const double moduleSizeY = subStaveSizeY;
362 const double moduleSizeZ = subStaveSizeZ / modulesPerSubStaveZ;
363 TGeoBBox*
module = new TGeoBBox(moduleSizeX * 0.5, moduleSizeY * 0.5, moduleSizeZ * 0.5);
364 TGeoVolume* moduleVol =
new TGeoVolume(moduleName, module, medAir);
368 const int chipsPerModuleX = 2;
369 const int chipsPerModuleZ = 4;
370 const double chipSizeX = moduleSizeX / chipsPerModuleX;
371 const double chipSizeY = moduleSizeY;
372 const double chipSizeZ = moduleSizeZ / chipsPerModuleZ;
373 TGeoBBox* chip =
new TGeoBBox(chipSizeX * 0.5, chipSizeY * 0.5, chipSizeZ * 0.5);
374 TGeoVolume* chipVol =
new TGeoVolume(chipName, chip, medSi);
378 const int sensorsPerChipX = 1;
379 const int sensorsPerChipZ = 1;
380 const double sensorSizeX = chipSizeX / sensorsPerChipX;
382 const double sensorSizeZ = chipSizeZ / sensorsPerChipZ;
383 TGeoBBox* sensor =
new TGeoBBox(sensorSizeX * 0.5, sensorSizeY * 0.5, sensorSizeZ * 0.5);
384 TGeoVolume* sensVol =
new TGeoVolume(sensName, sensor, medSi);
389 for (
int i = 0;
i < sensorsPerChipX; ++
i) {
390 for (
int j = 0;
j < sensorsPerChipZ; ++
j) {
391 LOGP(info,
"oTOF: Creating sensor {}/{} for chip {}/{}",
i + 1, sensorsPerChipX,
j + 1, sensorsPerChipZ);
392 auto* translation =
new TGeoTranslation((
i + 0.5) * sensorSizeX - 0.5 * chipSizeX,
393 0.5 * chipSizeY - 0.5 * sensorSizeY,
394 (
j + 0.5) * sensorSizeZ - 0.5 * chipSizeZ);
395 chipVol->AddNode(sensVol, 1 +
i * sensorsPerChipZ +
j, translation);
400 for (
int i = 0;
i < chipsPerModuleX; ++
i) {
401 for (
int j = 0;
j < chipsPerModuleZ; ++
j) {
402 LOGP(info,
"oTOF: Creating chip {}/{} for module {}/{}",
i + 1, chipsPerModuleX,
j + 1, chipsPerModuleZ);
403 auto* translation =
new TGeoTranslation((
i + 0.5) * chipSizeX - 0.5 * moduleSizeX, 0, (
j + 0.5) * chipSizeZ - 0.5 * moduleSizeZ);
404 moduleVol->AddNode(chipVol, 1 +
i * chipsPerModuleZ +
j, translation);
409 for (
int i = 0;
i < modulesPerSubStaveX; ++
i) {
410 for (
int j = 0;
j < modulesPerSubStaveZ; ++
j) {
411 LOGP(info,
"oTOF: Creating module {}/{} for substave {}/{}",
i + 1, modulesPerSubStaveX,
j + 1, modulesPerSubStaveZ);
412 const double tx = (
i + 0.5) * moduleSizeX - 0.5 * subStaveSizeX;
413 const double tz = -0.5 * subStaveSizeZ + (
j + 0.5) * moduleSizeZ;
414 auto* translation =
new TGeoTranslation(tx, 0, tz);
415 subStaveVol->AddNode(moduleVol, 1 +
i * modulesPerSubStaveZ +
j, translation);
420 for (
int i = 0;
i < 2; ++
i) {
421 LOGP(info,
"oTOF: Creating substave {}/{} for stave {}/{}",
i + 1, 2, 1, 1);
422 int sign =
i > 0 ? 1 : -1;
423 auto* translation2 =
new TGeoTranslation(sign * 0.5 * (subStaveSizeX)-sign * 0.5 * subStavesOverlapX, -sign * 0.5 * subStavesDistanceY, 0);
424 staveVol->AddNode(subStaveVol,
i + 1, translation2);
429 LOGP(info,
"oTOF: Creating stave {}/{} for layer {}",
i + 1,
mStaves.first, layerVol->GetName());
430 const double phi = TMath::TwoPi() *
i /
mStaves.first;
431 const double x = avgRadius * TMath::Cos(phi);
432 const double y = avgRadius * TMath::Sin(phi);
433 auto* rotation =
new TGeoRotation(Form(
"segmentRot%d",
i + 1), phi * TMath::RadToDeg() + 90 +
mTiltAngle, 0, 0);
436 LOGP(info,
"Inserting Barrel {} in {} ", chipVol->GetName(), layerVol->GetName());
439 LOGP(info,
"Inserting Barrel {} in {} at r={} cm", layerVol->GetName(), motherVolume->GetName(), avgRadius);
440 motherVolume->AddNode(layerVol, 1,
nullptr);