#include "AliRICHParam.h"
-#include "AliRICHConst.h" //for units ????
+#include "AliRICHConst.h"
+#include <TMath.h>
+#include <TRandom.h>
ClassImp(AliRICHParam)
-//______________________________________________________________________________
// RICH main parameters manipulator
+//__________________________________________________________________________________________________
AliRICHParam::AliRICHParam()
{//defines the default parameters
- Segmentation (144,160); //nx,ny
+ Segmentation (144,160); //nx,ny for the whole chamber
DeadZone (3*cm); //spacer between PC planes
PadSize (8.4*mm,8.0*mm);
+ fWirePitch=PadSizeX()/2;
- Size (80*cm,7*cm,60*cm); //full length, not GEANT half notation
- AngleRot (60); //rotation of the whole RICH around Z, deg
- Angles (20,19.5); //XY angle, YZ angle deg
- Offset (490*cm+1.267*cm); //1.267???????cm distance from IP to the center of module
+ Size (132.6*cm,26*cm,136.7*cm); //full length, not GEANT half notation
+ AngleRot (60); //rotation of the whole RICH around Z, deg
+ Angles (20,19.5); //XY angle, YZ angle deg
+ Offset (490*cm+1.267*cm); //1.267???????cm distance from IP to the center of module
GapThickness (8*cm);
ProximityGapThickness(0.4*cm);
QuartzLength (133*cm);
InnerFreonLength (133*cm);
InnerFreonWidth (41.3*cm);
FreonThickness (1.5*cm);
- RadiatorToPads (0);
+ RadiatorToPads (80*mm);
ChargeSlope(27.);
ChargeSpreadX(0.18);ChargeSpreadY(0.18);
Recalc();
}//AliRICHParam::named ctor
-//______________________________________________________________________________
+//__________________________________________________________________________________________________
void AliRICHParam::Recalc()
{//recalculate
- Float_t csi_length=fNy*fPadY+fDeadZone;
- Float_t csi_width =fNx*fPadX+2*fDeadZone;
- fPadPlaneWidth = (csi_width - 2*fDeadZone)/3;
- fPadPlaneLength = (csi_length - fDeadZone)/2;
+ fPcSizeX=Nx()*fPadSizeX+2*fDeadZone;
+ fPcSizeY=Ny()*fPadSizeY+fDeadZone;
+ fSectorSizeX=(fPcSizeX-2*fDeadZone)/3;
+ fSectorSizeY=(fPcSizeY-fDeadZone)/2;
}//void AliRICHParam::Recalc()
-//______________________________________________________________________________
+//__________________________________________________________________________________________________
+Int_t AliRICHParam::Sector(Float_t x, Float_t y)const
+{//Calculate in which sector is the hit
+ if(TMath::Abs(x)>fPcSizeX/2 || TMath::Abs(y)>fPcSizeY/2){
+ Error("Sector","given position is out of active PC area");
+ return kBad;
+ }
+ Int_t sector=kBad;
+ if(x<=-fSectorSizeX/2-fDeadZone) sector=1;
+ if(x>=-fSectorSizeX/2 && x<=fSectorSizeX/2) sector=2;
+ if(x>= fSectorSizeX/2+fDeadZone) sector=3;
+ if(y>= fDeadZone/2)
+ return sector;
+ else if(y<=-fDeadZone/2)
+ return -sector;
+ else
+ return kBad;
+}//Int_t AliRICHParam::Sector(Float_t x, Float_t y)
+//__________________________________________________________________________________________________
+Int_t AliRICHParam::L2P(Float_t x, Float_t y, Int_t &iPadX, Int_t &iPadY)const
+{//returns pad numbers (iPadX,iPadY) for given point in local coordinates (x,y)
+//
+// Please check origin of pad numbering !!!
+ iPadX=kBad;
+ iPadY=kBad;
+ Int_t sector=Sector(x,y);
+ switch(sector){
+ case -3:
+ iPadX = Int_t ((x-fDeadZone)/fPadSizeX);
+ iPadY = Int_t ((y+fDeadZone/2)/fPadSizeY)-1;
+ break;
+ case 3:
+ iPadX = Int_t ((x-fDeadZone)/fPadSizeX);
+ iPadY = Int_t ((y-fDeadZone/2)/fPadSizeY);
+ break;
+ case -2:
+ iPadX = (x>=0)? iPadX = Int_t (x/fPadSizeX) : iPadX = Int_t (x/fPadSizeX)-1;
+ iPadY = Int_t ((y+fDeadZone/2)/fPadSizeY)-1;
+ break;
+ case 2:
+ iPadX = (x>=0)? iPadX = Int_t (x/fPadSizeX) : iPadX = Int_t (x/fPadSizeX)-1;
+ iPadY = Int_t ((y-fDeadZone/2)/fPadSizeY);
+ break;
+ case -1:
+ iPadX = Int_t ((x+fDeadZone)/fPadSizeX)-1;
+ iPadY = Int_t ((y+fDeadZone/2)/fPadSizeY)-1;
+ break;
+ case 1:
+ iPadX = Int_t ((x+fDeadZone)/fPadSizeX)-1;
+ iPadY = Int_t ((y-fDeadZone/2)/fPadSizeY);
+ break;
+ }//switch
+
+ if(iPadY> Ny()) iPadY= Ny();
+ if(iPadY<-Ny()) iPadY=-Ny();
+ if(iPadX> Nx()) iPadX= Nx();
+ if(iPadX<-Nx()) iPadX=-Nx();
+ return sector;
+}//void AliRICHParam::L2P(Float_t x, Float_t y, Int_t &iPadX, Int_t &iPadY)
+//__________________________________________________________________________________________________
+Float_t AliRICHParam::Gain(Float_t y)
+{//Calculates the gain
+ if(fWireSag){
+ Float_t gainK=9e-6*TMath::Power(y,4)+2e-7*TMath::Power(y,3)-0.0316*TMath::Power(y,2)-3e-4*y+25.367;
+ Float_t gain = (ChargeSlope()+ChargeSlope()*gainK/100)*0.9;
+ return -gain*TMath::Log(gRandom->Rndm());
+ }else
+ return -ChargeSlope()*TMath::Log(gRandom->Rndm());
+}//Float_t AliRICHParam::IntPH(Float_t yhit)
+//__________________________________________________________________________________________________
+Float_t AliRICHParam::TotalCharge(Int_t iPID,Float_t eloss,Float_t y)
+{//Get number of electrons and return charge
+
+ if(iPID==kCerenkov||iPID==kFeedback)
+ return Gain(y);
+ else{
+ Int_t iNelectrons=Int_t(eloss/fEIonisation);if(iNelectrons==0) iNelectrons=1;
+ Float_t charge=0;
+ for(Int_t i=1;i<=iNelectrons;i++)
+ charge-=Gain(y);
+ return charge;
+ }
+}//Float_t AliRICHParam::TotalCharge(Int_t iPID,Float_t eloss, Float_t y)
+//__________________________________________________________________________________________________
AliRICHParam();
virtual ~AliRICHParam() {;}
- void Recalc();//Recalculate dependent parameters after changes applied
- void Segmentation(Int_t Nx, Int_t Ny) {fNx=Nx;fNy=Ny;Recalc();}
- Int_t Nx() const{return fNx;}
- Int_t Ny() const{return fNy;}
+ void Recalc(); //Recalculates dependent parameters after changes applied
+ Int_t Sector(Float_t x,Float_t y)const; //Returns sector number for given point (x,y)
+ Int_t L2P(Float_t x,Float_t y,Int_t &iPadX,Int_t &iPadY)const;//Which pad contains point (x,y), returns sector code
+ inline Int_t Wire(Float_t x)const; //Returns wire number for local point (x,y)
+ inline void SigGenInit(Float_t x,Float_t y);
+ inline Bool_t SigGenCond(Float_t x,Float_t y);
+ Float_t Gain(Float_t y); //Returns total charge induced by single photon
+ Float_t TotalCharge(Int_t iPID,Float_t eloss,Float_t y); //Returns total charge induced by particle lost eloss GeV
+ Float_t PadCharge(Int_t iPadX,Int_t iPadY); //Returns charge for a given pad
+
+ void Segmentation(Int_t Nx,Int_t Ny) {fNpadX=Nx;fNpadY=Ny;Recalc();}
+ Int_t Nx() const{return fNpadX;}
+ Int_t Ny() const{return fNpadY;}
void DeadZone(Float_t a) { fDeadZone=a;Recalc();}
Float_t DeadZone() const{return fDeadZone;}
- void PadSize(Float_t x,Float_t y) { fPadX=x;fPadY=y;Recalc();}
- Float_t PadX() const{return fPadX;}
- Float_t PadY() const{return fPadY;}
- Float_t PadPlaneWidth() const{return fPadPlaneWidth;}
- Float_t PadPlaneLength() const{return fPadPlaneLength;}
-
+ void PadSize(Float_t x,Float_t y) { fPadSizeX=x;fPadSizeY=y;Recalc();}
+ Float_t PadSizeX() const{return fPadSizeX;}
+ Float_t PadSizeY() const{return fPadSizeY;}
+ Float_t SectorSizeX() const{return fSectorSizeX;}
+ Float_t SectorSizeY() const{return fSectorSizeY;}
+ Float_t PcSizeX() const{return fPcSizeX;}
+ Float_t PcSizeY() const{return fPcSizeY;}
+
void Size(Float_t x,Float_t y,Float_t z){fSizeX=x;fSizeY=y;fSizeZ=z;}
void GeantSize(Float_t *pArr) const{pArr[0]=fSizeX/2;pArr[1]=fSizeY/2;pArr[2]=fSizeZ/2;}
Float_t SizeX() const{return fSizeX;}
Float_t ChargeSlope() {return fChargeSlope;}
void MaxAdc(Float_t a) { fMaxAdc=a;}
Float_t MaxAdc() const{return fMaxAdc;}
- void Pitch(Float_t a) { fPitch=a;};
+ void Pitch(Float_t a) { fPitch=a;}
Float_t Pitch() const{return fPitch;}
void AlphaFeedback(Float_t a) { fAlphaFeedback=a;}
Float_t AlphaFeedback() const{return fAlphaFeedback;}
void EIonisation(Float_t a) { fEIonisation=a;}
Float_t EIonisation() const{return fEIonisation;}
void SqrtKx3(Float_t a) { fSqrtKx3=a;};
- void Kx2(Float_t a) { fKx2=a;};
- void Kx4(Float_t a) { fKx4=a;};
- void SqrtKy3(Float_t a) { fSqrtKy3=a;};
- void Ky2(Float_t a) { fKy2=a;};
- void Ky4(Float_t a) { fKy4=a;};
- void WireSag(Int_t a) { fWireSag=a;};
- void Voltage(Int_t a) { fVoltage=a;};
+ void Kx2(Float_t a) { fKx2=a;}
+ void Kx4(Float_t a) { fKx4=a;}
+ void SqrtKy3(Float_t a) { fSqrtKy3=a;}
+ void Ky2(Float_t a) { fKy2=a;}
+ void Ky4(Float_t a) { fKy4=a;}
+ void WireSag(Int_t a) { fWireSag=a;}
+ void Voltage(Int_t a) { fVoltage=a;}
+ Float_t Voltage() const{return fVoltage;}
protected:
- Int_t fNx; //number of pads along X
- Int_t fNy; //number of pads along Y
- Float_t fDeadZone; //spacer between PC planes, cm
- Float_t fPadX; //pad width, cm
- Float_t fPadY; //pad lenght, cm
- Float_t fPadPlaneWidth; //pad plane width, cm
- Float_t fPadPlaneLength; //pad plane length, cm
+ Int_t fNpadX; Int_t fNpadY; //number of pads along X-Y in whole chamber (6 sectors)
+ Float_t fDeadZone; //space between PC sectors, cm
+ Float_t fPadSizeX,fPadSizeY; //pad size, cm
+ Float_t fSectorSizeX,fSectorSizeY; //photocathod sector size, cm
+ Float_t fWirePitch; //not yet known parameter ???
+
+ Int_t fCurrentPadX,fCurrentPadY; //???
+ Int_t fCurrentWire; //???
+
+ Float_t fSizeX; Float_t fSizeY; Float_t fSizeZ; //chamber outer size, cm
+ Float_t fAngleRot; //azimuthal rotation XY plane, deg
+ Float_t fAngleYZ; //angle between chambers YZ plane, deg
+ Float_t fAngleXY; //angle between chambers XY plane, deg
+ Float_t fOffset; //chambers offset from IP, cm
+ Float_t fGapThickness; //gap thickness, cm
+ Float_t fProximityGapThickness; //proximity gap thickness, cm
+ Float_t fQuartzLength; Float_t fQuartzWidth; Float_t fQuartzThickness; //quartz window size, cm
+ Float_t fOuterFreonLength; Float_t fOuterFreonWidth; //freon box outer size, cm
+ Float_t fInnerFreonLength; Float_t fInnerFreonWidth; //freon box inner size, cm
+ Float_t fFreonThickness; //freon thickness
+ Float_t fRadiatorToPads; //distance from radiator to pads, cm
+ Float_t fPcSizeX,fPcSizeY; //photocathod active area size,cm
- Float_t fSizeX; //chamber length, cm
- Float_t fSizeY; //chamber thickness, cm
- Float_t fSizeZ; //chamber width, cm
- Float_t fAngleRot; //azimuthal rotation angle in X-Y plane, deg
- Float_t fAngleYZ; //angle between RICH chambers in YZ plane, deg
- Float_t fAngleXY; //angle between RICH chambers in XY plane, deg
- Float_t fOffset; //chambers offset from IP, cm
- Float_t fGapThickness; //gap thickness, cm
- Float_t fProximityGapThickness; //proximity gap thickness, cm
- Float_t fQuartzLength; //quartz length, cm
- Float_t fQuartzWidth; //quartz width, cm
- Float_t fQuartzThickness; //quartz thickness, cm
- Float_t fOuterFreonLength; //outer freon length, cm
- Float_t fOuterFreonWidth; //outer freon width, cm
- Float_t fInnerFreonLength; //inner freon length, cm
- Float_t fInnerFreonWidth; //inner freon width, cm
- Float_t fFreonThickness; //freon thickness
- Float_t fRadiatorToPads; //distance from radiator to pads, cm
-
Float_t fChargeSlope; //Slope of the charge distribution
Float_t fChargeSpreadX; //Width of the charge distribution in x
Float_t fChargeSpreadY; //Width of the charge distribution in y
ClassDef(AliRICHParam,1) //RICH main parameters
};
-
+//__________________________________________________________________________________________________
+Int_t AliRICHParam::Wire(Float_t x)const
+{
+ Int_t iWire=(x>0)?Int_t(x/fWirePitch)+1:Int_t(x/fWirePitch)-1;
+ return iWire;
+}//Int_t AliRICHParam::Wire(Float_t x, Float_t y)
+//__________________________________________________________________________________________________
+void AliRICHParam::SigGenInit(Float_t x,Float_t y)
+{//Initialises pad and wire position during stepping
+ L2P(x,y,fCurrentPadX,fCurrentPadY);
+ fCurrentWire= (x>0) ? Int_t(x/fWirePitch)+1 : Int_t(x/fWirePitch)-1 ;
+}
+//__________________________________________________________________________________________________
+Bool_t AliRICHParam::SigGenCond(Float_t x,Float_t y)
+{//Signal will be generated if particle crosses pad boundary or boundary between two wires.
+ Int_t curPadX,curPadY;
+ L2P(x,y,curPadX,curPadY);
+ Int_t currentWire=(x>0) ? Int_t(x/fWirePitch)+1 : Int_t(x/fWirePitch)-1;
+ if((curPadX != fCurrentPadX) || (curPadY != fCurrentPadY) || (currentWire!=fCurrentWire))
+ return kTRUE;
+ else
+ return kFALSE;
+}
+//__________________________________________________________________________________________________
#endif //AliRICHParam_h