void AliITSMaterialsTGeo(TString gfile="geometry.root"){ // Macro to print out the ITS material definitions as found // in the TGeo geometry file. // retrives geometry if(!gGeoManager) gGeoManager = new TGeoManager(); TGeoManager::Import(gfile.Data()); if (!gGeoManager) { cout<<"geometry not found\n"; return; } // end if TList *medlist=gGeoManager->GetListOfMedia(); TGeoMedium *med; TGeoMaterial *mat; Int_t imed,nmed,i; printf("imed Id Med_Name Mat_Name "); for(i=0;i<20;i++) printf(" par[%2d] ",i); printf("\n"); imed=0; do{ med = (TGeoMedium*)(medlist->At(imed)); if(!med) continue; /*if((((med->GetName())[0]=='I')&& // Only ITS. ((med->GetName())[1]=='T')&& ((med->GetName())[2]=='S')&& ((med->GetName())[3]=='_')))*/{ mat = med->GetMaterial(); if(mat) printf("%4d %4d %30s %30s",imed,med->GetId(),med->GetName(),mat->GetName()); else printf("%4d %4d %30s %30s",imed,med->GetId(),med->GetName(),"No Material"); for(i=0;i<20;i++) printf(" %12g",med->GetParam(i)); printf("\n"); imed++; } }while(med!=medlist->Last()); }
/** * Calculate effective radiation length traversed by particle traveling between two points * along straight line. * * Calculation is done according to the eq. (27.23) * @see http://pdg.lbl.gov/2006/reviews/passagerpp.pdf * * @param globalPosStart starting point in the global coordinate system * @param globalPosFinish ending point in the global coordinate system * @param skipBoundaryVolumes if true subtract rad length of the volumes containing start and finish points * * @return radiation length in units of X0 */ float EUTelGeometryTelescopeGeoDescription::findRadLengthIntegral( const double globalPosStart[], const double globalPosFinish[], bool skipBoundaryPonitsVolumes ) { streamlog_out(DEBUG1) << "EUTelGeometryTelescopeGeoDescription::findRadLengthIntegral()" << std::endl; float rad = 0.; // integral of radiation length in units of X0 const double mm2cm = 0.1; /* TGeo uses cm and grams as internal units e.g. in radiation length and density. Telescope/LCIO uses mm. Therefore this routine is full of annoying conversion factors */ const double stepLenght2 = ( globalPosFinish[0] - globalPosStart[0] )*( globalPosFinish[0] - globalPosStart[0] ) + ( globalPosFinish[1] - globalPosStart[1] )*( globalPosFinish[1] - globalPosStart[1] ) + ( globalPosFinish[2] - globalPosStart[2] )*( globalPosFinish[2] - globalPosStart[2] ); const double stepLenght = TMath::Sqrt( stepLenght2 ); // don't need conversion factor to for calculation of directions const double xp = ( globalPosFinish[0] - globalPosStart[0] )/stepLenght; const double yp = ( globalPosFinish[1] - globalPosStart[1] )/stepLenght; const double zp = ( globalPosFinish[2] - globalPosStart[2] )/stepLenght; streamlog_out(DEBUG0) << "Start point (x,y,z):" << globalPosStart[0] << "," << globalPosStart[1] << "," << globalPosStart[2] << std::endl; streamlog_out(DEBUG0) << "Finish point (x,y,z):" << globalPosFinish[0] << "," << globalPosFinish[1] << "," << globalPosFinish[2] << std::endl; streamlog_out(DEBUG0) << "Direction (nx,ny,nz):" << xp << "," << yp << "," << zp << std::endl; double snext; double pt[3], loc[3]; double epsil = 1.E-7; double lastrad = 0.; int ismall = 0; int nbound = 0; float length = 0.; TGeoMedium *med; TGeoShape *shape; // Get starting node gGeoManager->InitTrack( globalPosStart[0]/*mm*/, globalPosStart[1]/*mm*/, globalPosStart[2]/*mm*/, xp, yp, zp ); TGeoNode *nextnode = gGeoManager->GetCurrentNode( ); double currentStep = stepLenght /*mm*/; // Loop over all, encountered during the propagation, volumes while ( nextnode ) { med = NULL; // Check if current point is inside silicon sensor. Radiation length of silicon sensors is accounted in thin scatterers of GBL. bool isBoundaryVolume = false; if ( gGeoManager->IsSameLocation( globalPosStart[0], globalPosStart[1], globalPosStart[2] ) || gGeoManager->IsSameLocation( globalPosFinish[0], globalPosFinish[1], globalPosFinish[2] ) ) isBoundaryVolume = true; if ( nextnode ) med = nextnode->GetVolume()->GetMedium(); else return 0.; shape = nextnode->GetVolume()->GetShape(); // make a step to the next intersection point if ( currentStep > 1.e-9 /*mm*/ ) nextnode = gGeoManager->FindNextBoundaryAndStep( currentStep /*mm*/ ); else return rad; snext = gGeoManager->GetStep() /*mm*/; // Small steps treatment if ( snext < 1.e-8 /*mm*/ ) { ismall++; // Terminate calculation if too many small steps done if ( ismall > 3 ) { streamlog_out( WARNING1 ) << "ERROR: Small steps in: " << gGeoManager->GetPath() << " shape=" << shape->ClassName() << endl; return rad; } // increase step size (epsilon) and advance along the particle direction memcpy( pt, gGeoManager->GetCurrentPoint(), 3 * sizeof (double) ); const double *dir = gGeoManager->GetCurrentDirection(); for ( Int_t i = 0; i < 3; i++ ) pt[i] += epsil * dir[i]; snext = epsil; length += snext; // Ignore start and finish volumes if required if ( skipBoundaryPonitsVolumes && isBoundaryVolume ) { rad += 0.; } else { rad += lastrad*snext; } gGeoManager->CdTop( ); nextnode = gGeoManager->FindNode( pt[0], pt[1], pt[2] ); // Check if particle is crossed the boundary if ( gGeoManager->IsOutside() ) return rad; // leave if not TGeoMatrix *mat = gGeoManager->GetCurrentMatrix(); mat->MasterToLocal( pt, loc ); if ( !gGeoManager->GetCurrentVolume()->Contains( loc ) ) { gGeoManager->CdUp(); nextnode = gGeoManager->GetCurrentNode(); // move to new volume } continue; } else { ismall = 0; } // Normal steps case nbound++; length += snext; currentStep -= snext; if ( med ) { double radlen = med->GetMaterial()->GetRadLen() /*cm*/; if ( radlen > 1.e-9 && radlen < 1.e10 ) { lastrad = 1. / radlen * mm2cm; // Ignore start and finish volumes if required if ( skipBoundaryPonitsVolumes && isBoundaryVolume ) { rad += 0.; } else { rad += lastrad*snext; } } else { lastrad = 0.; } streamlog_out( DEBUG0 ) << "STEP #" << nbound << std::endl; streamlog_out( DEBUG0 ) << " step[mm]=" << snext << " length[mm]=" << length << " rad[X0]=" << snext * mm2cm / radlen << " " << med->GetName( ) << " rho[g/cm^3]=" << med->GetMaterial()->GetDensity() <<" radlen[cm]=" << radlen << " Boundary:" << (isBoundaryVolume?"yes":"no") << std::endl; } } streamlog_out(DEBUG1) << "--------EUTelGeometryTelescopeGeoDescription::findRadLengthIntegral()--------" << std::endl; return rad; }