Loading [MathJax]/extensions/tex2jax.js
ATLAS Offline Software
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Modules Pages
NSWCalibTool.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2024 CERN for the benefit of the ATLAS collaboration
3 */
4 
5 #include "NSWCalibTool.h"
6 #include "GaudiKernel/SystemOfUnits.h"
7 #include "GaudiKernel/PhysicalConstants.h"
10 
11 namespace {
12  constexpr double toRad = M_PI/180;
13  constexpr double pitchErr = 0.425 * 0.425 / 12;
14  constexpr double reciprocalSpeedOfLight = 1. / Gaudi::Units::c_light; // mm/ns
15 
16  // since the final operation gas is not yet fixed different, different mixtures are added for studies
17  static const std::map<std::string, float> map_transDiff {{"ArCo2_937", 0.036},
18  {"ArCo2_8020", 0.019}, {"ArCo2iC4H10_9352", 0.035}};
19  static const std::map<std::string, float> map_longDiff {{"ArCo2_937", 0.019},
20  {"ArCo2_8020", 0.022 }, {"ArCo2iC4H10_9352", 0.0195}};
21  static const std::map<std::string, float> map_vDrift {{"ArCo2_937", 0.047},
22  {"ArCo2_8020", 0.040}, {"ArCo2iC4H10_9352", 0.045}};
23 
24 
25  // unit correction factors
26  constexpr double const MM_electronsPerfC = 6241.;
27  constexpr double const sTGC_pCPerfC = 1000.;
28 
29 
30  //Functional form fit to agree with Garfield simulations. Fit and parameters from G. Iakovidis
31  // For now only the parametrisation for 93:7 is available
32  using angleFunction = NSWCalib::MicroMegaGas::angleFunction;
33  static const std::map<std::string, angleFunction> map_lorentzAngleFunctionPars {
34  {"ArCo2_937", [](double x) {return 0.f + 58.87f*x -2.983f*x*x -10.62f*x*x*x + 2.818f*x*x*x*x;}},
35  {"ArCo2_8020", [](double x) {return 0.f + 58.87f*x -2.983f*x*x -10.62f*x*x*x + 2.818f*x*x*x*x;}},
36  {"ArCo2iC4H10_9352", [](double x) {return 0.f + 58.87f*x -2.983f*x*x -10.62f*x*x*x + 2.818f*x*x*x*x;}}};
37 
38  // For now only the parametrisation for 93:7 is available
39  static const std::map<std::string, float> map_interactionDensitySigma {{"ArCo2_937", 4.04 / 5.},
40  {"ArCo2_8020", 4.04 / 5.}, {"ArCo2iC4H10_9352", 4.04 / 5.}};
41  static const std::map<std::string, float> map_interactionDensityMean {{"ArCo2_937", 16.15 / 5.},
42  {"ArCo2_8020", 16.15 / 5.}, {"ArCo2iC4H10_9352", 16.15 / 5.}};
43 
44 }
45 
46 Muon::NSWCalibTool::NSWCalibTool(const std::string& t, const std::string& n, const IInterface* p) :
47  AthAlgTool(t,n,p) {
48  declareInterface<INSWCalibTool>(this);
49 }
50 
51 
53 {
54  ATH_MSG_DEBUG("In initialize()");
55  ATH_CHECK(m_idHelperSvc.retrieve());
56  ATH_CHECK(m_condTdoPdoKey.initialize());
57  ATH_CHECK(m_condT0Key.initialize(m_applyMmT0Calib || m_applysTgcT0Calib));
58  ATH_CHECK(m_fieldCondObjInputKey.initialize());
59  ATH_CHECK(m_muDetMgrKey.initialize());
60  ATH_CHECK(initializeGasProperties());
61  ATH_CHECK(m_ctpClusterCalibKey.initialize(m_CalibDriftVelocityFromData));
62  ATH_CHECK(initializeGasProperties());
63  return StatusCode::SUCCESS;
64 }
65 
67  if (!map_vDrift.count(m_gasMixture)) {
68  ATH_MSG_FATAL("Configured Micromegas with unkown gas mixture: " << m_gasMixture);
69  return StatusCode::FAILURE;
70  }
71 
72  m_vDrift = map_vDrift.find(m_gasMixture)->second;
73  m_transDiff = map_transDiff.find(m_gasMixture)->second;
74  m_longDiff = map_longDiff.find(m_gasMixture)->second;
75  m_interactionDensitySigma = map_interactionDensitySigma.find(m_gasMixture)->second;
76  m_interactionDensityMean = map_interactionDensityMean.find(m_gasMixture)->second;
77  m_lorentzAngleFunction = map_lorentzAngleFunctionPars.find(m_gasMixture)->second;
78  return StatusCode::SUCCESS;
79 }
80 
81 const NswCalibDbTimeChargeData* Muon::NSWCalibTool::getCalibData(const EventContext& ctx) const {
82  // set up pointer to conditions object
83  SG::ReadCondHandle<NswCalibDbTimeChargeData> readTdoPdo{m_condTdoPdoKey, ctx};
84  if(!readTdoPdo.isValid()){
85  ATH_MSG_ERROR("Cannot find conditions data container for TDOs and PDOs!");
86  return nullptr;
87  }
88  return readTdoPdo.cptr();
89 }
90 
92  //Can we not get this somewhere above? Can this not be read just once? per run?
93  SG::ReadCondHandle<Muon::mmCTPClusterCalibData> ctpClusterCalibDB{m_ctpClusterCalibKey, ctx};
94  if (!ctpClusterCalibDB.isValid()) {
95  ATH_MSG_FATAL("Failed to retrieve the parameterized errors "<<ctpClusterCalibDB.fullKey());
96  return nullptr;
97  }
98  return ctpClusterCalibDB.cptr();
99 }
100 
101 
102 StatusCode Muon::NSWCalibTool::calibrateClus(const EventContext& ctx, const Muon::MMPrepData* prepData, const Amg::Vector3D& globalPos, std::vector<NSWCalib::CalibratedStrip>& calibClus) const {
103 
104  double lorentzAngle {0.};
105  if(m_applyMmBFieldCalib){
107  MagField::AtlasFieldCache fieldCache;
108  if (!loadMagneticField(ctx, fieldCache)) return StatusCode::FAILURE;
109  Amg::Vector3D magneticField{Amg::Vector3D::Zero()};
110  fieldCache.getField(globalPos.data(), magneticField.data());
111 
113  double phi = globalPos.phi();
114  double bfield = (magneticField.x()*std::sin(phi)-magneticField.y()*std::cos(phi))*1000.;
115 
117  int gasGap = m_idHelperSvc->mmIdHelper().gasGap(prepData->identify());
118  bool changeSign = ( globalPos.z() < 0. ? (gasGap==1 || gasGap==3) : (gasGap==2 || gasGap==4) );
119  if (changeSign) bfield = -bfield;
120 
122  lorentzAngle = (bfield>0. ? 1. : -1.)*m_lorentzAngleFunction(std::abs(bfield)) * toRad;
123  }
124 
126  for (unsigned int i = 0; i < prepData->stripNumbers().size(); ++i){
127  Identifier id = prepData->rdoList().at(i);
128  double time = prepData->stripTimes().at(i);
129  double charge = prepData->stripCharges().at(i);
130  //Retrieve pointing constraint
131  const Amg::Vector3D& globPos{prepData->globalPosition()};
132  NSWCalib::CalibratedStrip calibStrip;
133  ATH_CHECK(calibrateStrip(ctx, id, time, charge, (globPos.theta() / toRad) , lorentzAngle, calibStrip));
134 
135  calibClus.push_back(std::move(calibStrip));
136  }
137  return StatusCode::SUCCESS;
138 }
139 
140 StatusCode Muon::NSWCalibTool::calibrateStrip(const EventContext& ctx, const Identifier& id, const double time, const double charge, const double theta, const double lorentzAngle, NSWCalib::CalibratedStrip& calibStrip) const {
141 
142 
143  //get local positon
145  if(!localStripPosition(id,locPos)) {
146  ATH_MSG_WARNING(__FILE__<<":"<<__LINE__<<" Failed to retrieve local strip position "<<m_idHelperSvc->toString(id));
147  return StatusCode::FAILURE;
148  }
149 
150  calibStrip.identifier = id;
151  calibStrip.charge = charge;
152  calibStrip.time = time;
153 
154  //retrieve identifier for the gas gap, not necessarily for the channel
155  //There is no pcb segmentation for these corrections, stored with pcb = 1 as default
156  Identifier gasGapId = m_idHelperSvc->mmIdHelper().channelID(id, m_idHelperSvc->mmIdHelper().multilayer(id),
157 m_idHelperSvc->mmIdHelper().gasGap(id), 1);
158 
159  double vDrift = m_vDrift; //nominal value from Garfield simulation
160 
161  if(m_CalibDriftVelocityFromData){
162  vDrift = getCTPClusterCalibData(ctx)->getCTPCorrectedDriftVelocity(gasGapId, theta);
163 
164  //Calculate the new half max possible time based on the new drift velocity
165  float max_half_drifttime = (vDrift != 0 ) ? 2.5/vDrift : 50.;
166 
167  //Shift the mean of the time to account for different values of drift velocities
168  calibStrip.time = time + (max_half_drifttime - m_mmT0TargetValue);
169  ATH_MSG_VERBOSE( "Original drift time: " << time << " new max half drift time: " << max_half_drifttime << " new time: " << calibStrip.time << " targett0 " << m_mmT0TargetValue );
170  }
171 
172 
173  double vDriftCorrected = vDrift * std::cos(lorentzAngle);
174 
175  calibStrip.distDrift = vDriftCorrected * calibStrip.time;
176 
178  calibStrip.resTransDistDrift = pitchErr + std::pow(m_transDiff * calibStrip.distDrift, 2);
179  calibStrip.resLongDistDrift = std::pow(m_ionUncertainty * vDriftCorrected, 2)
180  + std::pow(m_longDiff * calibStrip.distDrift, 2);
181  calibStrip.dx = std::sin(lorentzAngle) * calibStrip.time * vDrift;
182  calibStrip.locPos = Amg::Vector2D(locPos.x() + calibStrip.dx, locPos.y());
183  return StatusCode::SUCCESS;
184 }
185 
186 
187 StatusCode Muon::NSWCalibTool::calibrateStrip(const EventContext& ctx, const Muon::MM_RawData* mmRawData, NSWCalib::CalibratedStrip& calibStrip) const {
188 
189  const Identifier rdoId = mmRawData->identify();
190  //get local postion
191  Amg::Vector2D locPos{0,0};
192  if(!localStripPosition(rdoId,locPos)) {
193  ATH_MSG_WARNING(__FILE__<<":"<<__LINE__<<" Failed to retrieve local strip position "<<m_idHelperSvc->toString(rdoId));
194  return StatusCode::FAILURE;
195  }
196 
197  // MuonDetectorManager from the conditions store
198  SG::ReadCondHandle<MuonGM::MuonDetectorManager> muDetMgrHandle{m_muDetMgrKey, ctx};
199  const MuonGM::MuonDetectorManager* muDetMgr = muDetMgrHandle.cptr();
200 
201  //get globalPos
202  Amg::Vector3D globalPos{Amg::Vector3D::Zero()};
203  const MuonGM::MMReadoutElement* detEl = muDetMgr->getMMReadoutElement(rdoId);
204  detEl->stripGlobalPosition(rdoId,globalPos);
205 
206  // RDO has values in counts for both simulation and data
207  float time{-FLT_MAX}, charge{-FLT_MAX};
208  tdoToTime (ctx, mmRawData->timeAndChargeInCounts(), mmRawData->time (), rdoId, time , mmRawData->relBcid());
209  pdoToCharge(ctx, mmRawData->timeAndChargeInCounts(), mmRawData->charge(), rdoId, charge );
210 
211  calibStrip.charge = charge;
212  // historically the peak time is included in the time determined by the MM digitization and therefore added back in the tdoToTime function
213  // in order to not break the RDO to digit conversion needed for the trigger and the overlay
214  calibStrip.time = time - globalPos.norm() * reciprocalSpeedOfLight - mmPeakTime();
215  // applying T0 calibration, cannot be done inside the the tdo to time function since the tof correction was included when deriving the calibration constants
216  if(m_applyMmT0Calib){
217  calibStrip.time = applyT0Calibration(ctx, rdoId, calibStrip.time);
218  }
219 
220  calibStrip.identifier = rdoId;
221 
222  ATH_MSG_DEBUG("Calibrating RDO " << m_idHelperSvc->toString(rdoId) << "with pdo: " << mmRawData->charge() << " tdo: "<< mmRawData->time() << " relBCID "<< mmRawData->relBcid() << " charge and time in counts " <<
223  mmRawData->timeAndChargeInCounts() << " isData "<< m_isData << " to charge: " << calibStrip.charge << " electrons time after corrections " << calibStrip.time << " ns time before corrections "<< time << "ns");
224 
225 
226  //get stripWidth
227  detEl->getDesign(rdoId)->channelWidth(); // positon is not used for strip width
228 
229  calibStrip.distDrift = m_vDrift * calibStrip.time;
230  calibStrip.resTransDistDrift = pitchErr + std::pow(m_transDiff * calibStrip.distDrift, 2);
231  calibStrip.resLongDistDrift = std::pow(m_ionUncertainty * m_vDrift, 2)
232  + std::pow(m_longDiff * calibStrip.distDrift, 2);
233 
234  calibStrip.locPos = locPos;
235 
236  return StatusCode::SUCCESS;
237 }
238 
239 StatusCode Muon::NSWCalibTool::calibrateStrip(const EventContext& ctx, const Muon::STGC_RawData* sTGCRawData, NSWCalib::CalibratedStrip& calibStrip) const {
240 
241  Identifier rdoId = sTGCRawData->identify();
242  SG::ReadCondHandle<MuonGM::MuonDetectorManager> muDetMgrHandle{m_muDetMgrKey, ctx};
243  const MuonGM::MuonDetectorManager* muDetMgr = muDetMgrHandle.cptr();
244 
245  //get globalPos
246  Amg::Vector3D globalPos{Amg::Vector3D::Zero()};
247  const MuonGM::sTgcReadoutElement* detEl = muDetMgr->getsTgcReadoutElement(rdoId);
248  detEl->stripGlobalPosition(rdoId,globalPos);
249 
250  //get local postion
252  if(!localStripPosition(rdoId,locPos)) {
253  ATH_MSG_WARNING(__FILE__<<":"<<__LINE__<<" Failed to retrieve local strip position "<<m_idHelperSvc->toString(rdoId));
254  return StatusCode::FAILURE;
255  }
256 
257  // RDO has values in counts for both simulation and data
258  float time{-FLT_MAX}, charge{-FLT_MAX};
259  tdoToTime (ctx, sTGCRawData->timeAndChargeInCounts(), sTGCRawData->time (), rdoId, time , sTGCRawData->bcTag());
260  pdoToCharge(ctx, sTGCRawData->timeAndChargeInCounts(), sTGCRawData->charge(), rdoId, charge );
261  if(sTGCRawData->timeAndChargeInCounts()){
262  calibStrip.charge = charge * sTGC_pCPerfC;
263  } else {
264  calibStrip.charge = charge;
265  }
266  calibStrip.time = time - stgcPeakTime();
267 
268  if(m_applysTgcT0Calib){
269  calibStrip.time = applyT0Calibration(ctx, rdoId, calibStrip.time);
270  }
271 
272  calibStrip.identifier = rdoId;
273  calibStrip.locPos = locPos;
274  return StatusCode::SUCCESS;
275 
276 }
277 bool Muon::NSWCalibTool::loadMagneticField(const EventContext& ctx, MagField::AtlasFieldCache& fieldCache) const {
278  SG::ReadCondHandle<AtlasFieldCacheCondObj> readHandle{m_fieldCondObjInputKey, ctx};
279  if (!readHandle.isValid()) {
280  ATH_MSG_ERROR("doDigitization: Failed to retrieve AtlasFieldCacheCondObj with key " << m_fieldCondObjInputKey.key());
281  return false;
282  }
283  readHandle.cptr()->getInitializedCache(fieldCache);
284  return true;
285 }
286 StatusCode Muon::NSWCalibTool::distToTime(const EventContext& ctx, const Muon::MMPrepData* prepData, const Amg::Vector3D& globalPos, const std::vector<double>& driftDistances, std::vector<double>& driftTimes) const {
288  MagField::AtlasFieldCache fieldCache;
289  if (!loadMagneticField(ctx, fieldCache)) return StatusCode::FAILURE;
290  Amg::Vector3D magneticField{Amg::Vector3D::Zero()};
291  fieldCache.getField(globalPos.data(), magneticField.data());
292 
294  const double phi = globalPos.phi();
295  double bfield = (magneticField.x()*std::sin(phi)-magneticField.y()*std::cos(phi))*1000.;
296 
298  int gasGap = m_idHelperSvc->mmIdHelper().gasGap(prepData->identify());
299  bool changeSign = ( globalPos.z() < 0. ? (gasGap==1 || gasGap==3) : (gasGap==2 || gasGap==4) );
300  if (changeSign) bfield = -bfield;
301  double cos2_lorentzAngle = std::pow(std::cos ( (bfield>0. ? 1. : -1.)*m_lorentzAngleFunction(std::abs(bfield)) * toRad), 2);
303  for (const double dist : driftDistances){
304  double time = dist / (m_vDrift*cos2_lorentzAngle);
305  driftTimes.push_back(time);
306  }
307  return StatusCode::SUCCESS;
308 
309 }
310 
311 bool
312 Muon::NSWCalibTool::chargeToPdo(const EventContext& ctx, const float charge, const Identifier& chnlId, int& pdo) const {
313  const NswCalibDbTimeChargeData* tdoPdoData = getCalibData(ctx);
314  if (!tdoPdoData) {
315  pdo = 0;
316  return false;
317  }
318  const TimeCalibConst* calib_ptr = tdoPdoData->getCalibForChannel(TimeCalibType::PDO, chnlId);
319  if (!calib_ptr) {
320  pdo = 0;
321  return false;
322  }
323  const TimeCalibConst& calib{*calib_ptr};
324  float c = charge;
325  if (m_idHelperSvc->isMM (chnlId)) c /= MM_electronsPerfC;
326  else if(m_idHelperSvc->issTgc(chnlId)) c *= sTGC_pCPerfC;
327  else {
328  pdo = 0;
329  return false;
330  }
331  pdo = c * calib.slope + calib.intercept;
332  return true;
333 }
334 
335 bool
336 Muon::NSWCalibTool::pdoToCharge(const EventContext& ctx, const bool inCounts, const int pdo, const Identifier& chnlId, float& charge) const {
337  if(!inCounts){
338  charge = pdo;
339  return true;
340  }
341  const NswCalibDbTimeChargeData* tdoPdoData = getCalibData(ctx);
342  if (!tdoPdoData) {
343  charge =0.;
344  return false;
345  }
346  const TimeCalibConst* calib_ptr = tdoPdoData->getCalibForChannel(TimeCalibType::PDO, chnlId);
347  if (!calib_ptr) {
348  charge = 0.;
349  return false;
350  }
351  const TimeCalibConst& calib{*calib_ptr};
352  charge = (pdo-calib.intercept)/calib.slope;
353  if (m_idHelperSvc->isMM (chnlId)) charge *= MM_electronsPerfC;
354  else if(m_idHelperSvc->issTgc(chnlId)) charge /= sTGC_pCPerfC;
355  else return false;
356  return true;
357 }
358 
359 bool
360 Muon::NSWCalibTool::timeToTdo(const EventContext& ctx, const float time, const Identifier& chnlId, int& tdo, int& relBCID) const {
361  const NswCalibDbTimeChargeData* tdoPdoData = getCalibData(ctx);
362  if (!tdoPdoData) return false;
363  if (m_idHelperSvc->isMM (chnlId)) return timeToTdoMM (tdoPdoData, time, chnlId, tdo, relBCID);
364  else if(m_idHelperSvc->issTgc(chnlId)) return timeToTdoSTGC(tdoPdoData, time, chnlId, tdo, relBCID);
365  return false;
366 }
367 
368 bool
369 Muon::NSWCalibTool::timeToTdoMM(const NswCalibDbTimeChargeData* tdoPdoData, const float time, const Identifier& chnlId, int& tdo, int& relBCID) const {
370  const float t = time - m_mmPeakTime - m_mmLatencyMC; // subtract peaking time first! This is not supossed to run on data ever only needed for the RDO->Digit step
371  const TimeCalibConst* calib_ptr = tdoPdoData->getCalibForChannel(TimeCalibType::TDO, chnlId);
372  if (!calib_ptr) {
373  tdo = relBCID = 0;
374  return false;
375  }
376  const TimeCalibConst& calib{*calib_ptr};
377  float tdoTime = -999.9;
378  constexpr float lowerBound = Muon::MM_RawData::s_lowerTimeBound;
379  for(int i_relBCID=0; i_relBCID<Muon::MM_RawData::s_BCWindow; i_relBCID++){
380  if(t >= lowerBound+i_relBCID*25 && t < (lowerBound+25)+i_relBCID*25){
381  tdoTime = i_relBCID*25 - t;
382  relBCID = i_relBCID;
383  break;
384  }
385  }
386  if(tdoTime < lowerBound) {
387  tdo = relBCID = 0;
388  return false;
389  }
390  tdo = tdoTime*calib.slope + calib.intercept;
391  return true;
392 }
393 
394 bool
395 Muon::NSWCalibTool::timeToTdoSTGC(const NswCalibDbTimeChargeData* tdoPdoData, const float time, const Identifier& chnlId, int& tdo, int& relBCID) const {
396  const float t = time - m_stgcPeakTime - m_stgcLatencyMC; // subtract peaking time and latency first! This is not supossed to run on data ever only needed for the RDO->Digit step
397  const TimeCalibConst* calib_ptr = tdoPdoData->getCalibForChannel(TimeCalibType::TDO, chnlId);
398  if (!calib_ptr){
399  tdo = relBCID = 0;
400  return false;
401  }
402  const TimeCalibConst& calib = {*calib_ptr};
403  float tdoTime = -999.9;
404  const float lowerBound = Muon::STGC_RawData::s_lowerTimeBound - m_stgcLatencyMC; // this is not supossed to run on data ever, only needed for the RDO->Digit step
405  for(int i_relBCID=0; i_relBCID<Muon::STGC_RawData::s_BCWindow; ++i_relBCID){
406  if(t >= lowerBound+i_relBCID*25 && t < (lowerBound+25)+i_relBCID*25){
407  tdoTime = i_relBCID*25 - t;
408  relBCID = i_relBCID;
409  break;
410  }
411  }
412  if(tdoTime < lowerBound) {
413  tdo = relBCID = 0;
414  return false;
415  }
416  tdo = tdoTime*calib.slope + calib.intercept;
417  return true;
418 }
419 
420 float Muon::NSWCalibTool::applyT0Calibration(const EventContext& ctx, const Identifier& id, float time) const {
421  SG::ReadCondHandle<NswT0Data> readT0{m_condT0Key, ctx};
422  if(!readT0.isValid()){
423  ATH_MSG_ERROR("Cannot find conditions data container for T0s!");
424  }
425  float t0 {0};
426  bool isGood = readT0->getT0(id, t0);
427  if(!isGood || t0==0){
428  ATH_MSG_DEBUG("failed to retrieve good t0 from database, skipping t0 calibration");
429  return time;
430  } else {
431  float targetT0 = (m_idHelperSvc->isMM(id) ? m_mmT0TargetValue : m_stgcT0TargetValue);
432  float newTime = time + (targetT0 - t0);
433  ATH_MSG_DEBUG("doing T0 calibration for RDO " << m_idHelperSvc->toString(id) << " time " << time <<" t0 from database " << t0 << " t0 target " << targetT0 << " new time " << newTime);
434  return newTime;
435  }
436 }
437 
438 
439 bool
440 Muon::NSWCalibTool::tdoToTime(const EventContext& ctx, const bool inCounts, const int tdo, const Identifier& chnlId, float& time, const int relBCID) const {
441  if(!inCounts){
442  time = tdo;
443  return true;
444  }
445  const NswCalibDbTimeChargeData* tdoPdoData = getCalibData(ctx);
446  if (!tdoPdoData) {
447  time = 0.;
448  return false;
449  }
450  const TimeCalibConst* calib_ptr = tdoPdoData->getCalibForChannel(TimeCalibType::TDO, chnlId);
451  if (!calib_ptr){
452  time = 0.;
453  return false;
454  }
455  const TimeCalibConst& calib {*calib_ptr};
456  //this shift of 25ns is necessary to align the time of the signal with the way the VMM determines the time
457  //(relBCID 0 corresponds to -37.5 ns to - 12.5 ns)
458  //Eventually it should go into the conditions db since it is probably not the same for MC and Data
459  //but for now it is kept like it is. pscholer 8th of June 2022
460  float mmLatency = (m_isData? m_mmLatencyData : m_mmLatencyMC );
461  float stgcLatency = (m_isData? m_stgcLatencyData : m_stgcLatencyMC);
462 
463  const float peakTime = m_idHelperSvc->isMM(chnlId) ? mmPeakTime() + mmLatency : stgcPeakTime() + stgcLatency;
464  time = relBCID*25. - (tdo-calib.intercept)/calib.slope + peakTime;
465  return true;
466 }
467 
470  properties.driftVelocity = m_vDrift;
471  properties.longitudinalDiffusionSigma = m_longDiff;
472  properties.transverseDiffusionSigma = m_transDiff;
473  properties.interactionDensityMean = m_interactionDensityMean;
474  properties.interactionDensitySigma = m_interactionDensitySigma;
475  properties.lorentzAngleFunction = m_lorentzAngleFunction;
476  return properties;
477 }
478 
479 
481  // MuonDetectorManager from the conditions store
482  SG::ReadCondHandle<MuonGM::MuonDetectorManager> muDetMgrHandle{m_muDetMgrKey};
483  const MuonGM::MuonDetectorManager* muDetMgr = muDetMgrHandle.cptr();
484  if(m_idHelperSvc->isMM(id)){
485  const MuonGM::MMReadoutElement* detEl = muDetMgr->getMMReadoutElement(id);
486  return detEl->stripPosition(id,locPos);
487 
488  } else if(m_idHelperSvc->issTgc(id)){
489  const MuonGM::sTgcReadoutElement* detEl = muDetMgr->getsTgcReadoutElement(id);
490  return detEl->stripPosition(id,locPos);
491 
492  } else {
493  return false;
494  }
495 }
MuonGM::MMReadoutElement::stripPosition
virtual bool stripPosition(const Identifier &id, Amg::Vector2D &pos) const override final
strip position – local or global If the strip number is outside the range of valid strips,...
Definition: MMReadoutElement.h:207
Muon::STGC_RawData::identify
const Identifier identify() const
Definition: STGC_RawData.h:52
dumpTgcDigiDeadChambers.gasGap
list gasGap
Definition: dumpTgcDigiDeadChambers.py:33
NSWCalib::CalibratedStrip::time
double time
Definition: INSWCalibTool.h:22
ATH_MSG_FATAL
#define ATH_MSG_FATAL(x)
Definition: AthMsgStreamMacros.h:34
Muon::MMPrepData
Class to represent MM measurements.
Definition: MMPrepData.h:22
Muon::MM_RawData::relBcid
uint16_t relBcid() const
Definition: MM_RawData.h:63
Muon::MM_RawData::s_lowerTimeBound
static constexpr double s_lowerTimeBound
Definition: MM_RawData.h:72
NswCalibDbTimeChargeData::CalibConstants
Helper struct to cache all calibration constants in a common place of the memory.
Definition: NswCalibDbTimeChargeData.h:28
Muon::MMPrepData::globalPosition
virtual const Amg::Vector3D & globalPosition() const override final
Returns the global position.
Definition: MMPrepData.h:211
NSWCalib::CalibratedStrip::charge
double charge
Definition: INSWCalibTool.h:21
SG::ReadCondHandle
Definition: ReadCondHandle.h:44
Muon::NSWCalibTool::initializeGasProperties
StatusCode initializeGasProperties()
Definition: NSWCalibTool.cxx:66
python.TestDriveDummies.properties
dictionary properties
Definition: TestDriveDummies.py:14
NSWCalib::CalibratedStrip::distDrift
double distDrift
Definition: INSWCalibTool.h:24
Muon::NSWCalibTool::pdoToCharge
bool pdoToCharge(const EventContext &ctx, const bool inCounts, const int pdo, const Identifier &chnlId, float &charge) const override
Definition: NSWCalibTool.cxx:336
NSWCalib::CalibratedStrip::dx
double dx
Definition: INSWCalibTool.h:27
sTgcReadoutElement.h
Amg::Vector2D
Eigen::Matrix< double, 2, 1 > Vector2D
Definition: GeoPrimitives.h:48
Muon::MM_RawData::timeAndChargeInCounts
bool timeAndChargeInCounts() const
Definition: MM_RawData.h:65
Muon::MM_RawData::identify
const Identifier & identify() const
Definition: MM_RawData.h:58
MuonGM::MMReadoutElement::getDesign
const MuonChannelDesign * getDesign(const Identifier &id) const
returns the MuonChannelDesign class for the given identifier
Definition: MMReadoutElement.h:191
Muon::MM_RawData::time
int time() const
Definition: MM_RawData.h:62
Muon::NSWCalibTool::timeToTdo
bool timeToTdo(const EventContext &ctx, const float time, const Identifier &chnlId, int &tdo, int &relBCID) const override
Definition: NSWCalibTool.cxx:360
NSWCalib::CalibratedStrip::resTransDistDrift
double resTransDistDrift
Definition: INSWCalibTool.h:25
M_PI
#define M_PI
Definition: ActiveFraction.h:11
Trk::PrepRawData::rdoList
const std::vector< Identifier > & rdoList() const
return the List of rdo identifiers (pointers)
Muon::NSWCalibTool::tdoToTime
bool tdoToTime(const EventContext &ctx, const bool inCounts, const int tdo, const Identifier &chnlId, float &time, const int relBCID) const override
Definition: NSWCalibTool.cxx:440
read_hist_ntuple.t
t
Definition: read_hist_ntuple.py:5
drawFromPickle.cos
cos
Definition: drawFromPickle.py:36
ATH_MSG_VERBOSE
#define ATH_MSG_VERBOSE(x)
Definition: AthMsgStreamMacros.h:28
Muon::MM_RawData::s_BCWindow
static constexpr int s_BCWindow
Definition: MM_RawData.h:75
NSWCalib::CalibratedStrip::resLongDistDrift
double resLongDistDrift
Definition: INSWCalibTool.h:26
x
#define x
Muon::NSWCalibTool::loadMagneticField
bool loadMagneticField(const EventContext &ctx, MagField::AtlasFieldCache &fieldCache) const
Definition: NSWCalibTool.cxx:277
Muon::STGC_RawData::s_lowerTimeBound
static constexpr double s_lowerTimeBound
Definition: STGC_RawData.h:67
MuonGM::sTgcReadoutElement::stripPosition
virtual bool stripPosition(const Identifier &id, Amg::Vector2D &pos) const override final
strip position - should be renamed to channel position If the strip number is outside the range of va...
Definition: MuonDetDescr/MuonReadoutGeometry/MuonReadoutGeometry/sTgcReadoutElement.h:321
Muon::NSWCalibTool::mmGasProperties
NSWCalib::MicroMegaGas mmGasProperties() const override
Definition: NSWCalibTool.cxx:468
python.setupRTTAlg.size
int size
Definition: setupRTTAlg.py:39
MMReadoutElement.h
python.utils.AtlRunQueryDQUtils.p
p
Definition: AtlRunQueryDQUtils.py:210
Muon::MMPrepData::stripCharges
const std::vector< int > & stripCharges() const
returns the list of charges
Definition: MMPrepData.h:257
ATH_MSG_ERROR
#define ATH_MSG_ERROR(x)
Definition: AthMsgStreamMacros.h:33
NSWCalib::MicroMegaGas::angleFunction
std::function< double(double)> angleFunction
Definition: INSWCalibTool.h:40
Muon::NSWCalibTool::distToTime
StatusCode distToTime(const EventContext &ctx, const Muon::MMPrepData *prepData, const Amg::Vector3D &globalPos, const std::vector< double > &driftDistances, std::vector< double > &driftTimes) const override
Definition: NSWCalibTool.cxx:286
Muon::NSWCalibTool::timeToTdoSTGC
bool timeToTdoSTGC(const NswCalibDbTimeChargeData *tdoPdoData, const float time, const Identifier &chnlId, int &tdo, int &relBCID) const
Definition: NSWCalibTool.cxx:395
Muon::STGC_RawData
Definition: STGC_RawData.h:14
lumiFormat.i
int i
Definition: lumiFormat.py:85
Muon::MM_RawData
Temporary class to hold the MM RDO.
Definition: MM_RawData.h:20
Muon::NSWCalibTool::applyT0Calibration
float applyT0Calibration(const EventContext &ctx, const Identifier &id, float time) const
Definition: NSWCalibTool.cxx:420
beamspotman.n
n
Definition: beamspotman.py:731
EL::StatusCode
::StatusCode StatusCode
StatusCode definition for legacy code.
Definition: PhysicsAnalysis/D3PDTools/EventLoop/EventLoop/StatusCode.h:22
ATH_MSG_DEBUG
#define ATH_MSG_DEBUG(x)
Definition: AthMsgStreamMacros.h:29
MuonGM::MMReadoutElement::stripGlobalPosition
bool stripGlobalPosition(const Identifier &id, Amg::Vector3D &gpos) const
Definition: MMReadoutElement.h:280
NSWCalib::CalibratedStrip::locPos
Amg::Vector2D locPos
Definition: INSWCalibTool.h:28
MuonGM::sTgcReadoutElement
An sTgcReadoutElement corresponds to a single STGC module; therefore typicaly a barrel muon station c...
Definition: MuonDetDescr/MuonReadoutGeometry/MuonReadoutGeometry/sTgcReadoutElement.h:30
ATH_CHECK
#define ATH_CHECK
Definition: AthCheckMacros.h:40
Muon::MMPrepData::stripNumbers
const std::vector< uint16_t > & stripNumbers() const
returns the list of strip numbers
Definition: MMPrepData.h:247
NSWCalib::CalibratedStrip
Definition: INSWCalibTool.h:20
Muon::MMPrepData::stripTimes
const std::vector< short int > & stripTimes() const
returns the list of times
Definition: MMPrepData.h:252
Trk::PrepRawData::identify
Identifier identify() const
return the identifier
Muon::MM_RawData::charge
int charge() const
Definition: MM_RawData.h:64
Muon::NSWCalibTool::getCTPClusterCalibData
const Muon::mmCTPClusterCalibData * getCTPClusterCalibData(const EventContext &ctx) const
Definition: NSWCalibTool.cxx:91
Muon::NSWCalibTool::calibrateStrip
StatusCode calibrateStrip(const EventContext &ctx, const Identifier &id, const double time, const double charge, const double theta, const double lorentzAngle, NSWCalib::CalibratedStrip &calibStrip) const override
Definition: NSWCalibTool.cxx:140
id
SG::auxid_t id
Definition: Control/AthContainers/Root/debug.cxx:239
Muon::NSWCalibTool::getCalibData
const NswCalibDbTimeChargeData * getCalibData(const EventContext &ctx) const
Definition: NSWCalibTool.cxx:81
MuonGM::sTgcReadoutElement::stripGlobalPosition
bool stripGlobalPosition(const Identifier &id, Amg::Vector3D &gpos) const
Definition: MuonDetDescr/MuonReadoutGeometry/MuonReadoutGeometry/sTgcReadoutElement.h:332
Muon::STGC_RawData::time
float time() const
Definition: STGC_RawData.h:55
charge
double charge(const T &p)
Definition: AtlasPID.h:931
Muon::NSWCalibTool::calibrateClus
StatusCode calibrateClus(const EventContext &ctx, const Muon::MMPrepData *prepData, const Amg::Vector3D &globalPos, std::vector< NSWCalib::CalibratedStrip > &calibClus) const override
Definition: NSWCalibTool.cxx:102
python.PhysicalConstants.c_light
float c_light
Definition: PhysicalConstants.py:72
Amg::Vector3D
Eigen::Matrix< double, 3, 1 > Vector3D
Definition: GeoPrimitives.h:47
NSWCalibTool.h
PlotSFuncertainty.calib
calib
Definition: PlotSFuncertainty.py:110
Muon::NSWCalibTool::localStripPosition
bool localStripPosition(const Identifier &id, Amg::Vector2D &locPos) const
Definition: NSWCalibTool.cxx:480
Muon::NSWCalibTool::timeToTdoMM
bool timeToTdoMM(const NswCalibDbTimeChargeData *tdoPdoData, const float time, const Identifier &chnlId, int &tdo, int &relBCID) const
Definition: NSWCalibTool.cxx:369
MuonGM::MuonDetectorManager
The MuonDetectorManager stores the transient representation of the Muon Spectrometer geometry and pro...
Definition: MuonDetDescr/MuonReadoutGeometry/MuonReadoutGeometry/MuonDetectorManager.h:50
ATH_MSG_WARNING
#define ATH_MSG_WARNING(x)
Definition: AthMsgStreamMacros.h:32
MuonGM::MuonDetectorManager::getMMReadoutElement
const MMReadoutElement * getMMReadoutElement(const Identifier &id) const
access via extended identifier (requires unpacking)
Definition: MuonDetDescr/MuonReadoutGeometry/src/MuonDetectorManager.cxx:255
MagField::AtlasFieldCache
Local cache for magnetic field (based on MagFieldServices/AtlasFieldSvcTLS.h)
Definition: AtlasFieldCache.h:43
if
if(febId1==febId2)
Definition: LArRodBlockPhysicsV0.cxx:567
MuonGM::MMReadoutElement
An MMReadoutElement corresponds to a single STGC module; therefore typicaly a barrel muon station con...
Definition: MMReadoutElement.h:25
Muon::NSWCalibTool::NSWCalibTool
NSWCalibTool(const std::string &, const std::string &, const IInterface *)
Definition: NSWCalibTool.cxx:46
MagField::AtlasFieldCache::getField
void getField(const double *ATH_RESTRICT xyz, double *ATH_RESTRICT bxyz, double *ATH_RESTRICT deriv=nullptr)
get B field value at given position xyz[3] is in mm, bxyz[3] is in kT if deriv[9] is given,...
Definition: AtlasFieldCache.cxx:42
Muon::NSWCalibTool::initialize
virtual StatusCode initialize() override
Definition: NSWCalibTool.cxx:52
NswCalibDbTimeChargeData
Definition: NswCalibDbTimeChargeData.h:19
MuonGM::MuonDetectorManager::getsTgcReadoutElement
const sTgcReadoutElement * getsTgcReadoutElement(const Identifier &id) const
access via extended identifier (requires unpacking)
Definition: MuonDetDescr/MuonReadoutGeometry/src/MuonDetectorManager.cxx:259
drawFromPickle.sin
sin
Definition: drawFromPickle.py:36
Muon::STGC_RawData::charge
unsigned int charge() const
Definition: STGC_RawData.h:57
AthAlgTool
Definition: AthAlgTool.h:26
Muon::mmCTPClusterCalibData
Definition: mmCTPClusterCalibData.h:18
Muon::STGC_RawData::bcTag
uint16_t bcTag() const
Definition: STGC_RawData.h:58
pow
constexpr int pow(int base, int exp) noexcept
Definition: ap_fixedTest.cxx:15
MuonGM::MuonChannelDesign::channelWidth
double channelWidth() const
calculate local channel width
Definition: MuonChannelDesign.h:394
Muon::NSWCalibTool::chargeToPdo
bool chargeToPdo(const EventContext &ctx, const float charge, const Identifier &chnlId, int &pdo) const override
Definition: NSWCalibTool.cxx:312
python.compressB64.c
def c
Definition: compressB64.py:93
Muon::STGC_RawData::timeAndChargeInCounts
bool timeAndChargeInCounts() const
Definition: STGC_RawData.h:61
NswCalibDbTimeChargeData::getCalibForChannel
const CalibConstants * getCalibForChannel(const CalibDataType type, const Identifier &channelId) const
Retrieves the calibration constant for a particular readout channel.
Definition: NswCalibDbTimeChargeData.cxx:121
NSWCalib::MicroMegaGas
Definition: INSWCalibTool.h:32
Muon::STGC_RawData::s_BCWindow
static constexpr int s_BCWindow
Definition: STGC_RawData.h:70
generate::Zero
void Zero(TH1D *hin)
Definition: generate.cxx:32
NSWCalib::CalibratedStrip::identifier
Identifier identifier
Definition: INSWCalibTool.h:29
Identifier
Definition: IdentifierFieldParser.cxx:14