Skip to content

Commit 9cbb000

Browse files
sawenzelclaude
andcommitted
Build the FT0 MCP stack and radiator wrap from running planes
This makes the FT0 photocathode reachable by a navigator other than TGeo's and puts the reflector strips inside their own mother. - The layer thicknesses are Float_t and each layer's z was summed in a different order, so 0MTO and 0REG were 0.075 nm apart and 0REG and 0MCP overlapped by 0.24 nm. VecGeom abandoned 0REG with DistanceToOut = -1, so no Cherenkov photon was ever registered. - The stack is now built from one running plane, mirroring the addition the box shape uses for its own half-length. - 0TRE was declared one micron wider than the radiator while each reflector strip is four microns thick, so three quarters of every strip lay outside its mother. The geometry doctor reports those strips at 23.9 to 27.2 percent reachable. The container is now derived from its contents. - The strips are seated against the radiator in double, closing a 0.33 nm gap. - Neither change moves the light yield: 41783 +- 564 hits per event before and 40995 +- 534 after, with the beam aimed into FT0-A. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
1 parent f01f9e6 commit 9cbb000

1 file changed

Lines changed: 38 additions & 18 deletions

File tree

‎Detectors/FIT/FT0/simulation/src/Detector.cxx‎

Lines changed: 38 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -203,10 +203,17 @@ void Detector::SetOneMCP(TGeoVolume* ins)
203203

204204
Double_t x, y, z;
205205

206-
Float_t ptop[3] = {1.324, 1.324, 1.}; // Cherenkov radiator
207-
Float_t ptopref[3] = {1.3241, 1.3241, 1.}; // Cherenkov radiator wrapped with reflector
208-
Double_t prfv[3] = {0.0002, 1.323, 1.}; // Vertical refracting layer bettwen radiators and between radiator and not optical Air
209-
Double_t prfh[3] = {1.323, 0.0002, 1.}; // Horizontal refracting layer bettwen radiators and ...
206+
Float_t ptop[3] = {1.324, 1.324, 1.}; // Cherenkov radiator
207+
Double_t prfv[3] = {0.0002, 1.323, 1.}; // Vertical refracting layer bettwen radiators and between radiator and not optical Air
208+
Double_t prfh[3] = {1.323, 0.0002, 1.}; // Horizontal refracting layer bettwen radiators and ...
209+
// Cherenkov radiator wrapped with reflector. The container has to hold the radiator plus one
210+
// reflector strip on each side, so its half-width is the radiator's plus the full strip
211+
// thickness. It was written as the radiator plus 1 um while a strip is 4 um thick, which left
212+
// each strip sticking 3 um out of its own mother. The clearance keeps the strips off the
213+
// container wall, so no daughter face sits exactly on the mother's.
214+
const double kWrapClearance = 1.e-4; // cm
215+
Float_t ptopref[3] = {static_cast<Float_t>(ptop[0] + 2 * prfv[0] + kWrapClearance),
216+
static_cast<Float_t>(ptop[1] + 2 * prfh[1] + kWrapClearance), 1.};
210217
Float_t pmcp[3] = {2.949, 2.949, 0.66}; // MCP
211218
Float_t pmcpinner[3] = {2.749, 2.749, 0.1};
212219
Float_t pmcpbase[3] = {2.949, 2.949, 0.675};
@@ -231,39 +238,52 @@ void Detector::SetOneMCP(TGeoVolume* ins)
231238
Int_t ntops = 0, nrfvs = 0, nrfhs = 0;
232239
x = y = z = 0;
233240
topref->AddNode(top, 1, new TGeoTranslation(0, 0, 0));
234-
float xinv = -ptop[0] - prfv[0];
241+
// Each reflector strip has to sit against the radiator with no gap: SetBorderSurface below
242+
// makes 0TOP/0RFV and 0TOP/0RFH mirrors, and a border surface only acts where the two
243+
// volumes actually touch. Rounding the offset to float left 0.33 nm of air between them, so
244+
// the mirrors never applied and the light left through the side.
245+
auto seat = [](Float_t half, Double_t strip) { return double(half) + strip; };
246+
double xinv = -seat(ptop[0], prfv[0]);
235247
topref->AddNode(rfv, 1, new TGeoTranslation(xinv, 0, 0));
236-
xinv = ptop[0] + prfv[0];
248+
xinv = seat(ptop[0], prfv[0]);
237249
topref->AddNode(rfv, 2, new TGeoTranslation(xinv, 0, 0));
238-
float yinv = -ptop[1] - prfh[1];
250+
double yinv = -seat(ptop[1], prfh[1]);
239251
topref->AddNode(rfh, 1, new TGeoTranslation(0, yinv, 0));
240-
yinv = ptop[1] + prfh[1];
252+
yinv = seat(ptop[1], prfh[1]);
241253
topref->AddNode(rfh, 2, new TGeoTranslation(0, yinv, 0));
242254

255+
// The wrapped radiator, the MCP top glass, the photocathode and the MCP are stacked along z
256+
// with no gap between them. Each layer's position is built here from the back face of the one
257+
// before it, using the same double addition the box shape uses for its own half-length, so
258+
// adjacent faces land on the same double. Summing the float thicknesses in a different order
259+
// for each layer, as this code did, left the faces up to 0.24 nm apart.
260+
const double zRadiatorCentre = -mInStart[2] + double(ptopref[2]);
261+
const double zRadiatorBack = zRadiatorCentre + double(ptopref[2]);
262+
const double zTopGlassCentre = zRadiatorBack + double(pmcptopglass[2]);
263+
const double zTopGlassBack = zTopGlassCentre + double(pmcptopglass[2]);
264+
const double zCathodeCentre = zTopGlassBack + double(preg[2]);
265+
const double zCathodeBack = zCathodeCentre + double(preg[2]);
266+
243267
// container for radiator, cathode
244268
for (Int_t ix = 0; ix < 2; ix++) {
245269
float xin = -mInStart[0] + 0.3 + (ix + 0.5) * 2 * ptopref[0];
246270
for (Int_t iy = 0; iy < 2; iy++) {
247271
float yin = -mInStart[1] + 0.3 + (iy + 0.5) * 2 * ptopref[1];
248272
ntops++;
249-
z = -mInStart[2] + ptopref[2];
250-
ins->AddNode(topref, ntops, new TGeoTranslation(xin, yin, z));
251-
LOG(debug) << " n " << ntops << " x " << xin << " y " << yin << " z radiator " << z;
252-
z += ptopref[2] + 2. * pmcptopglass[2] + preg[2];
253-
ins->AddNode(cat, ntops, new TGeoTranslation(xin, yin, z));
254-
LOG(debug) << " n " << ntops << " x " << xin << " y " << yin << " z cathod " << z;
273+
ins->AddNode(topref, ntops, new TGeoTranslation(xin, yin, zRadiatorCentre));
274+
LOG(debug) << " n " << ntops << " x " << xin << " y " << yin << " z radiator " << zRadiatorCentre;
275+
ins->AddNode(cat, ntops, new TGeoTranslation(xin, yin, zCathodeCentre));
276+
LOG(debug) << " n " << ntops << " x " << xin << " y " << yin << " z cathod " << zCathodeCentre;
255277
}
256278
}
257279
// MCP
258280
TVirtualMC::GetMC()->Gsvolu("0MTO", "BOX", getMediumID(kOpGlass), pmcptopglass, 3); // Op Glass
259281
TGeoVolume* mcptop = gGeoManager->GetVolume("0MTO");
260-
z = -mInStart[2] + 2 * ptopref[2] + pmcptopglass[2];
261-
ins->AddNode(mcptop, 1, new TGeoTranslation(0, 0, z));
282+
ins->AddNode(mcptop, 1, new TGeoTranslation(0, 0, zTopGlassCentre));
262283

263284
TVirtualMC::GetMC()->Gsvolu("0MCP", "BOX", getMediumID(kAir), pmcp, 3); // glass
264285
TGeoVolume* mcp = gGeoManager->GetVolume("0MCP");
265-
z = -mInStart[2] + 2 * ptopref[2] + 2 * pmcptopglass[2] + 2 * preg[2] + pmcp[2];
266-
ins->AddNode(mcp, 1, new TGeoTranslation(0, 0, z));
286+
ins->AddNode(mcp, 1, new TGeoTranslation(0, 0, zCathodeBack + double(pmcp[2])));
267287

268288
TVirtualMC::GetMC()->Gsvolu("0MSI", "BOX", getMediumID(kMCPwalls), pmcpside, 3); // glass
269289
TGeoVolume* mcpside = gGeoManager->GetVolume("0MSI");

0 commit comments

Comments
 (0)