10 #include <ecl/modules/eclee5x5Collector/eclee5x5CollectorModule.h>
13 #include <ecl/dataobjects/ECLCalDigit.h>
14 #include <ecl/dataobjects/ECLDigit.h>
15 #include <ecl/dataobjects/ECLElementNumbers.h>
16 #include <ecl/dbobjects/ECLCrystalCalib.h>
19 #include <analysis/ClusterUtility/ClusterUtils.h>
20 #include <framework/dataobjects/EventMetaData.h>
21 #include <framework/datastore/RelationVector.h>
22 #include <framework/geometry/VectorUtil.h>
23 #include <mdst/dataobjects/ECLCluster.h>
24 #include <mdst/dataobjects/TRGSummary.h>
27 #include <Math/Vector3D.h>
28 #include <Math/Vector4D.h>
47 m_ECLExpee5x5E(
"ECLExpee5x5E"), m_ElectronicsCalib(
"ECLCrystalElectronics"), m_ee5x5Calib(
"ECLCrystalEnergyee5x5"),
48 m_selectdPhiData(
"ECLeedPhiData"), m_selectdPhiMC(
"ECLeedPhiMC")
51 setDescription(
"Calibration Collector Module for ECL single crystal energy calibration using Bhabha events");
55 addParam(
"minE0",
m_minE0,
"minimum energy of cluster 0: E*0/sqrts", 0.45);
56 addParam(
"minE1",
m_minE1,
"minimum energy of cluster 1: E*1/sqrts", 0.40);
57 addParam(
"maxdThetaSum",
m_maxdThetaSum,
"maximum diff between 180 deg and sum of cluster theta* (deg)", 2.);
73 B2INFO(
"eclee5x5Collector: Experiment = " <<
m_evtMetaData->getExperiment() <<
" run = " <<
m_evtMetaData->getRun() <<
" sqrts = "
79 auto EnVsCrysID =
new TH2F(
"EnVsCrysID",
"Normalized 5x5 energy for each crystal;crystal ID;E25/Expected",
82 registerObject<TH2F>(
"EnVsCrysID", EnVsCrysID);
84 auto RvsCrysID =
new TH1F(
"RvsCrysID",
"E_exp x E_crysID / sigma^2;crysID;sum of E_exp x E_crysID/sigma^2",
88 auto NRvsCrysID =
new TH1F(
"NRvsCrysID",
"Entries in RvsCrysID vs crysID;crysID;Entries in RvsCrysID",
97 auto ElecCalibvsCrys =
new TH1F(
"ElecCalibvsCrys",
"Sum electronics calib const vs crystal ID;crystal ID;calibration constant",
99 registerObject<TH1F>(
"ElecCalibvsCrys", ElecCalibvsCrys);
100 auto ExpEvsCrys =
new TH1F(
"ExpEvsCrys",
"Sum expected energy calib const vs crystalID;crystal ID;calibration constant",
103 registerObject<TH1F>(
"ExpEvsCrys", ExpEvsCrys);
104 auto InitialCalibvsCrys =
new TH1F(
"InitialCalibvsCrys",
"Sum initial calib const vs crystal ID;crystal ID;calibration constant",
106 registerObject<TH1F>(
"InitialCalibvsCrys", InitialCalibvsCrys);
108 auto CalibEntriesvsCrys =
new TH1F(
"CalibEntriesvsCrys",
"Entries in calib vs crys histograms;crystal ID;Entries per crystal",
111 registerObject<TH1F>(
"CalibEntriesvsCrys", CalibEntriesvsCrys);
113 auto EntriesvsCrys =
new TH1F(
"EntriesvsCrys",
"Selected Bhabha clusters vs crystal ID;crystal ID;Entries",
115 registerObject<TH1F>(
"EntriesvsCrys", EntriesvsCrys);
117 auto dPhivsThetaID =
new TH2F(
"dPhivsThetaID",
118 "Phi* vs thetaID forward, pass thetaSum,E0,E1;thetaID of forward cluster;dPhi COM (deg)", 69, 0, 69, 150, 165, 180);
119 registerObject<TH2F>(
"dPhivsThetaID", dPhivsThetaID);
123 B2INFO(
"Input parameters to eclee5x5Collector:");
160 for (
int ic = 1; ic < 9000; ic += 1000) {
161 B2INFO(
"DB constants for cellID=" << ic <<
": ee5x5Calib = " <<
ee5x5Calib[ic - 1] <<
" Expee5x5E = " <<
Expee5x5E[ic - 1] <<
162 " ElectronicsCalib = " <<
169 if (
Expee5x5E[crysID] == 0) {B2FATAL(
"eclee5x5Collector: Expee5x5E = 0 for crysID = " << crysID);}
170 if (
ee5x5Calib[crysID] == 0) {B2FATAL(
"eclee5x5Collector: ee5x5Calib = 0 for crysID = " << crysID);}
183 for (
int it = 0; it < 69; it++) {
205 getObjectPtr<TH1F>(
"ExpEvsCrys")->Fill(crysID + 0.001,
Expee5x5E[crysID]);
206 getObjectPtr<TH1F>(
"ElecCalibvsCrys")->Fill(crysID + 0.001,
ElectronicsCalib[crysID]);
207 getObjectPtr<TH1F>(
"InitialCalibvsCrys")->Fill(crysID + 0.001,
ee5x5Calib[crysID]);
208 getObjectPtr<TH1F>(
"CalibEntriesvsCrys")->Fill(crysID + 0.001);
215 bool newConst =
false;
224 B2INFO(
"ECLCrystalElectronics has changed, exp = " <<
m_evtMetaData->getExperiment() <<
" run = " <<
m_evtMetaData->getRun());
229 B2INFO(
"ECLCrystalEnergyee5x5 has changed, exp = " <<
m_evtMetaData->getExperiment() <<
" run = " <<
m_evtMetaData->getRun());
234 for (
int ic = 1; ic < 9000; ic += 1000) {
235 B2INFO(
"DB constants for cellID=" << ic <<
": ee5x5Calib = " <<
ee5x5Calib[ic - 1] <<
" Expee5x5E = " <<
Expee5x5E[ic - 1] <<
236 " ElectronicsCalib = " <<
243 if (
Expee5x5E[crysID] == 0) {B2FATAL(
"eclee5x5Collector: Expee5x5E = 0 for crysID = " << crysID);}
244 if (
ee5x5Calib[crysID] == 0) {B2FATAL(
"eclee5x5Collector: ee5x5Calib = 0 for crysID = " << crysID);}
251 unsigned int L1TriggerResults =
m_TRGResults->getTRGSummary(0);
252 if (L1TriggerResults == 0) {
return;}
257 int icMax[2] = { -1, -1};
258 double maxClustE[2] = { -1., -1.};
260 for (
int ic = 0; ic < nclust; ic++) {
263 if (eClust > maxClustE[0]) {
264 maxClustE[1] = maxClustE[0];
266 maxClustE[0] = eClust;
268 }
else if (eClust > maxClustE[1]) {
269 maxClustE[1] = eClust;
278 if (icMax[1] == -1) {
return;}
288 double dt99min = dt990;
289 if (dt991 < dt990) {dt99min = dt991;}
290 if (dt99min <= 0) {dt99min = 0.0001;}
291 if (abs(t1 - t0) > dt99min *
m_maxTime) {
return;}
296 const ROOT::Math::XYZVector clustervertex = cUtil.
GetIPPosition();
299 ROOT::Math::XYZVector p30;
300 VectorUtil::setMagThetaPhi(p30, maxClustE[0], theta0, phi0);
305 ROOT::Math::XYZVector p31;
306 VectorUtil::setMagThetaPhi(p31, maxClustE[1], theta1, phi1);
313 double theta01COM = (p41COM.Theta() + p40COM.Theta()) * TMath::RadToDeg();
323 int crysIDMax[2] = { -1, -1};
324 double crysEMax[2] = { -1., -1.};
325 for (
int imax = 0; imax < 2; imax++) {
327 for (
unsigned int ir = 0; ir < eclClusterRelations.size(); ir++) {
328 const auto calDigit = eclClusterRelations.object(ir);
329 int tempCrysID = calDigit->
getCellId() - 1;
330 float tempE = calDigit->getEnergy();
331 if (tempE > crysEMax[imax]) {
332 crysEMax[imax] = tempE;
333 crysIDMax[imax] = tempCrysID;
339 double dphiCOM = abs(p41COM.Phi() - p40COM.Phi()) * TMath::RadToDeg();
340 if (dphiCOM > 180.) {dphiCOM = 360. - dphiCOM;}
342 int thetaIDmin =
m_thetaID[crysIDMax[0]];
344 getObjectPtr<TH2F>(
"dPhivsThetaID")->Fill(thetaIDmin + 0.001, dphiCOM);
354 int tempCrysID = eclCalDigit.getCellId() - 1;
355 EperCrys[tempCrysID] = eclCalDigit.getEnergy();
359 int tempCrysID = eclDigit.getCellId() - 1;
367 for (
int ic = 0; ic < 2; ic++) {
368 int crysMax = crysIDMax[ic];
374 double reducedExpE = expE;
376 for (
auto& cellID : neighbours) {
379 reducedExpE -=
EperCrys[cellID - 1];
384 double rexpE = reducedExpE / sigmaExp;
385 for (
auto& celli : neighbours) {
387 float rEi =
EperCrys[celli - 1] / sigmaExp;
388 getObjectPtr<TH1F>(
"RvsCrysID")->Fill(celli - 0.999, rexpE * rEi);
389 getObjectPtr<TH1F>(
"NRvsCrysID")->Fill(celli - 0.999);
390 for (
auto& cellj : neighbours) {
392 float rEj =
EperCrys[cellj - 1] / sigmaExp;
393 getObjectPtr<TH2F>(
"Qmatrix")->Fill(celli - 0.999, cellj - 0.999, rEi * rEj);
400 getObjectPtr<TH2F>(
"EnVsCrysID")->Fill(crysMax + 0.001, E25 / expE);
401 getObjectPtr<TH1F>(
"EntriesvsCrys")->Fill(crysMax + 0.001);
402 getObjectPtr<TH1F>(
"ExpEvsCrys")->Fill(crysMax + 0.001,
Expee5x5E[crysMax]);
403 getObjectPtr<TH1F>(
"ElecCalibvsCrys")->Fill(crysMax + 0.001,
ElectronicsCalib[crysMax]);
404 getObjectPtr<TH1F>(
"InitialCalibvsCrys")->Fill(crysMax + 0.001,
ee5x5Calib[crysMax]);
405 getObjectPtr<TH1F>(
"CalibEntriesvsCrys")->Fill(crysMax + 0.001);
Calibration collector module base class.
void registerObject(std::string name, T *obj)
Register object with a name, takes ownership, do not access the pointer beyond prepare()
Class to provide momentum-related information from ECLClusters.
const ROOT::Math::PxPyPzEVector Get4MomentumFromCluster(const ECLCluster *cluster, ECLCluster::EHypothesisBit hypo)
Returns four momentum vector.
const ROOT::Math::XYZVector GetIPPosition()
Returns default IP position from beam parameters.
Class to store calibrated ECLDigits: ECLCalDigits.
int getCellId() const
Get Cell ID.
@ c_nPhotons
CR is split into n photons (N1)
Class to get the neighbours for a given cell id.
const std::vector< short int > & getNeighbours(short int cid) const
Return the neighbours for a given cell ID.
short int getCrystalsPerRing(const short int thetaid) const
return number of crystals in a given theta ring
void setDescription(const std::string &description)
Sets the description of the module.
void setPropertyFlags(unsigned int propertyFlags)
Sets the flags for the module properties.
@ c_ParallelProcessingCertified
This module can be run in parallel processing mode safely (All I/O must be done through the data stor...
DBObjPtr< ECLCrystalCalib > m_selectdPhiData
dPhi cut
StoreArray< ECLDigit > m_eclDigitArray
Required input array of ECLDigits.
std::vector< float > widthdPhi
width of requirement on dPhi from DB object
std::vector< float > Expee5x5E
vector of energies obtained from DB object
bool m_requireL1
require events to satisfy a level 1 trigger (false)
DBObjPtr< ECLCrystalCalib > m_ECLExpee5x5E
Expected energies from database.
double m_maxTime
maximum cluster time diff abs(t1-t0)/dt99 (10)
double m_maxdThetaSum
abs(theta0* + theta1* - 180 deg) must be less than less (2 deg)
StoreArray< ECLCluster > m_eclClusterArray
Required arrays.
StoreObjPtr< TRGSummary > m_TRGResults
dataStore TRGSummary
bool storeCalib
force the input calibration constants to be saved first event
double m_minE0
minimum energy of cluster 0: E*0/sqrts (0.45)
std::vector< float > EperCrys
Energy for each crystal from ECLDigit or ECLCalDigit (GeV)
std::vector< int > m_thetaID
thetaID of each crystal
ECL::ECLNeighbours * m_eclNeighbours5x5
Neighbour map of 25 crystals.
bool m_useCalDigits
use eclCalDigit to determine MC deposited energy (false)
std::vector< float > Expee5x5Sigma
vector of sigmaE obtained from DB object
std::vector< float > m_dPhiMin
minimum dPhi* as a function of thetaID
std::vector< float > m_dPhiMax
maximum dPhi* as a function of thetaID
void collect() override
Select events and crystals and accumulate histograms.
StoreObjPtr< EventMetaData > m_evtMetaData
dataStore EventMetaData
std::vector< float > ElectronicsCalib
vector obtained from DB object
StoreArray< ECLCalDigit > m_eclCalDigitArray
Required input array of ECLCalDigits.
double m_thetaLabMax
m_thetaLabMaxDeg converted to radians
std::vector< float > meandPhi
mean requirement on dPhi from DB object
double m_sqrts
sqrt s from m_boostrotate
void prepare() override
Define histograms and read payloads from DB.
std::vector< float > ee5x5Calib
vector obtained from DB object
double m_thetaLabMin
Some other useful quantities.
DBObjPtr< ECLCrystalCalib > m_selectdPhiMC
DB object for MC.
double m_thetaLabMaxDeg
maximum ecl cluster theta in lab (150 degrees)
DBObjPtr< ECLCrystalCalib > m_ee5x5Calib
Existing single crystal calibration from DB; will be updated by CAF.
double m_thetaLabMinDeg
Parameters to control the job.
PCmsLabTransform m_boostrotate
boost from COM to lab and visa versa
double m_dPhiScale
scale dPhi* cut by this factor (1)
double m_minE1
minimum energy of cluster 1: E*1/sqrts (0.40)
DBObjPtr< ECLCrystalCalib > m_ElectronicsCalib
Electronics calibration from database.
void addParam(const std::string &name, T ¶mVariable, const std::string &description, const T &defaultValue)
Adds a new parameter to the module.
#define REG_MODULE(moduleName)
Register the given module (without 'Module' suffix) with the framework.
const int c_NCrystals
Number of crystals.
Abstract base class for different kinds of events.