00001
00002
00003
00004
00005
00007 #include "SimRomanPot/SimFP420/interface/HitDigitizerFP420.h"
00008
00009
00010
00011 #include "SimDataFormats/TrackingHit/interface/PSimHit.h"
00012 #include "SimDataFormats/TrackingHit/interface/PSimHitContainer.h"
00013 #include "DataFormats/GeometryVector/interface/LocalPoint.h"
00014 #include "DataFormats/GeometryVector/interface/LocalVector.h"
00015
00016 #include "SimRomanPot/SimFP420/interface/ChargeDrifterFP420.h"
00017 #include "SimRomanPot/SimFP420/interface/ChargeDividerFP420.h"
00018 #include "SimRomanPot/SimFP420/interface/InduceChargeFP420.h"
00019
00020 using namespace std;
00021 #include<vector>
00022
00023 #define CBOLTZ (1.38E-23)
00024 #define e_SI (1.6E-19)
00025
00026
00027
00028 HitDigitizerFP420::HitDigitizerFP420(float in,float ild,float ildx,float ildy,float in0,float in2,float in3,int verbosity){
00029 moduleThickness =in;
00030 double bz420 = in0;
00031 double bzD2 = in2;
00032 double bzD3 = in3;
00033
00034
00035
00036 double ldrift =ild;
00037 double ldriftX =ildx;
00038 double ldriftY =ildy;
00039
00040
00041
00042
00043
00044 theCDividerFP420 = new ChargeDividerFP420(moduleThickness, bz420, bzD2, bzD3, verbosity);
00045
00046 depletionVoltage=20.0;
00047 appliedVoltage=25.0;
00048
00049
00050 chargeMobility=1350.0;
00051
00052
00053 temperature=263.;
00054 double diffusionConstant = CBOLTZ/e_SI * chargeMobility * temperature;
00055
00056 noDiffusion=false;
00057 if (noDiffusion) diffusionConstant *= 1.0e-3;
00058
00059 chargeDistributionRMS=6.5e-10;
00060
00061
00062 tanLorentzAnglePerTesla = 0. ;
00063
00064
00065
00066
00067 double timeNormalisation = pow(ldrift,2)/(2.*depletionVoltage*chargeMobility);
00068
00069 timeNormalisation = timeNormalisation*0.01;
00070
00071
00072
00073
00074 double clusterWidth=5.;
00075 gevperelectron= 3.61e-09;
00076
00077
00078 if(verbosity>0) {
00079 std::cout << "HitDigitizerFP420: constructor ldrift= " << ldrift << std::endl;
00080 std::cout << "ldriftY= " <<ldriftY << "ldriftX= " <<ldriftX << std::endl;
00081 std::cout << "depletionVoltage" << depletionVoltage << "appliedVoltage" << appliedVoltage << "chargeMobility" << chargeMobility << "temperature" << temperature << "diffusionConstant" << diffusionConstant << "chargeDistributionRMS" << chargeDistributionRMS << "moduleThickness" << moduleThickness << "timeNormalisation" << timeNormalisation << "gevperelectron" << gevperelectron << std::endl;
00082 }
00083
00084
00085 theCDrifterFP420 =
00086 new ChargeDrifterFP420(moduleThickness,
00087 timeNormalisation,
00088 diffusionConstant,
00089 temperature,
00090 chargeDistributionRMS,
00091 depletionVoltage,
00092 appliedVoltage,
00093 ldriftX,
00094 ldriftY, verbosity);
00095
00096
00097
00098 theIChargeFP420 = new InduceChargeFP420(clusterWidth,gevperelectron);
00099 }
00100
00101
00102 HitDigitizerFP420::~HitDigitizerFP420(){
00103 delete theCDividerFP420;
00104 delete theCDrifterFP420;
00105 delete theIChargeFP420;
00106 }
00107
00108
00109
00110 HitDigitizerFP420::hit_map_type HitDigitizerFP420::processHit(const PSimHit& hit, G4ThreeVector bfield, int xytype,int numStrips, double pitch, int numStripsW, double pitchW, double moduleThickness, int verbosity){
00111
00112
00113
00114
00115 float middlex = (hit.exitPoint().x() + hit.entryPoint().x() )/2.;
00116 float middley = (hit.exitPoint().y() + hit.entryPoint().y() )/2.;
00117
00118
00119 float chargePosition= -100.;
00120
00121 if(xytype == 1) {
00122
00123
00124
00125
00126
00127 chargePosition = 0.5*(numStrips) + middlex/pitch ;
00128
00129
00130 }
00131
00132 else if(xytype == 2) {
00133
00134
00135
00136
00137
00138 chargePosition = 0.5*(numStrips) + middley/pitch ;
00139
00140
00141 }
00142 else {
00143 std::cout <<"================================================================"<<std::endl;
00144 std::cout << "**** HitDigitizerFP420: !!! ERROR: you have not to be here !!! xytype=" << xytype << std::endl;
00145
00146
00147
00148
00149 }
00150
00151 if(chargePosition > numStrips || chargePosition < 0) {
00152 std::cout << "**** HitDigitizerFP420: !!! ERROR: check correspondence of XY detector dimensions in XML and here !!! chargePosition = " << chargePosition << std::endl;
00153
00154 }
00155
00156 if(verbosity>0) {
00157 std::cout << " ====== **** HitDigitizerFP420: !!! processHit !!! : input: xytype=" << xytype << " numStrips= " << numStrips << " pitch= " << pitch << " Calculated chargePosition= " << chargePosition << std::endl;
00158 std::cout << "The middle of hit point on input was: middlex = " << middlex << std::endl;
00159 std::cout << "The middle of hit point on input was: middley = " << middley << std::endl;
00160
00161 std::cout << " ====== **** HitDigitizerFP420:processHit: start CDrifterFP420 divide" << std::endl;
00162 }
00163
00164
00165
00166
00167
00168 CDrifterFP420::ionization_type ion = theCDividerFP420->divide(hit,moduleThickness);
00169
00170
00171
00172
00173
00174 G4ThreeVector driftDir = DriftDirection(bfield,xytype,verbosity);
00175 if(verbosity>0) {
00176 std::cout << " ====== **** HitDigitizerFP420:processHit: driftDir= " << driftDir << std::endl;
00177 std::cout << " ====== **** HitDigitizerFP420:processHit: start induce , CDrifterFP420 drift " << std::endl;
00178 }
00179
00180
00181
00182
00183
00184
00185 return theIChargeFP420->induce(theCDrifterFP420->drift(ion,driftDir,xytype), numStrips, pitch, numStripsW, pitchW, xytype, verbosity);
00186
00187
00188 }
00189
00190
00191
00192 G4ThreeVector HitDigitizerFP420::DriftDirection(G4ThreeVector _bfield, int xytype, int verbosity){
00193
00194
00195
00196
00197
00198 G4ThreeVector Bfield=_bfield;
00199 float dir_x, dir_y, dir_z;
00200
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211 if(xytype == 2) {
00212 dir_x = 1.;
00213 dir_y = +tanLorentzAnglePerTesla * Bfield.z();
00214 dir_z = -tanLorentzAnglePerTesla * Bfield.y();
00215 }
00216
00217
00218 else if(xytype == 1) {
00219 dir_x = +tanLorentzAnglePerTesla * Bfield.z();
00220 dir_y = 1.;
00221 dir_z = -tanLorentzAnglePerTesla * Bfield.x();
00222 }
00223 else{
00224 dir_x = 0.;
00225 dir_y = 0.;
00226 dir_z = 0.;
00227 std::cout << "HitDigitizerFP420: ERROR - wrong xytype=" << xytype << std::endl;
00228 }
00229
00230
00231
00232 G4ThreeVector theDriftDirection(dir_x,dir_y,dir_z);
00233
00234 if(verbosity>0) {
00235 std::cout << "HitDigitizerFP420:DriftDirection tanLorentzAnglePerTesla= " << tanLorentzAnglePerTesla << std::endl;
00236 std::cout << "HitDigitizerFP420:DriftDirection The drift direction in local coordinate is " << theDriftDirection << std::endl;
00237 }
00238
00239 return theDriftDirection;
00240
00241 }