ATLAS Offline Software
Loading...
Searching...
No Matches
LayerArrayCreator.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3*/
4
6// LayerArrayCreator.cxx, (c) ATLAS Detector software
8
9// Trk include
14#include "TrkGeometry/Layer.h"
23// Amg
25
26
27// constructor
28Trk::LayerArrayCreator::LayerArrayCreator(const std::string& t, const std::string& n, const IInterface* p)
29: AthAlgTool(t,n,p),
31{
32 declareInterface<ILayerArrayCreator>(this);
33
34 declareProperty("EmptyLayerMode", m_emptyLayerMode);
35}
36
37
38std::unique_ptr<Trk::BinnedArray1D<Trk::Layer>> Trk::LayerArrayCreator::cylinderLayerArray(
39 const std::vector<Trk::CylinderLayer*>& cylLayersInput,
40 double rmin, double rmax, Trk::BinningType btype) const
41{
42 ATH_MSG_VERBOSE( " build LayerArray with " << cylLayersInput.size() << " cylindrical material layers." );
43 ATH_MSG_VERBOSE( " rmin/rmax provided : " << rmin << " / " << rmax );
44
45 //copy so that you can sort
46 std::vector<Trk::CylinderLayer*> cylLayers(cylLayersInput);
47 // sort the vector
49 std::sort(cylLayers.begin(), cylLayers.end(), rSorter);
50
51 // needed for all cases
52 Trk::Layer* cylinderLayer = nullptr;
53 std::unique_ptr<Trk::BinnedArray1D<Trk::Layer>> cylinderLayerArray = nullptr;
54 std::vector< std::pair<std::shared_ptr<Trk::Layer>, Amg::Vector3D> > layerOrderVector;
55
56 switch (btype) {
57
58 // equidistant binning - no navigation layers built
59 case Trk::equidistant :
60 {
61 // count the layers
62 unsigned int layers = cylLayers.size();
63 // loop over layers and put them in
64 for (auto& layIter : cylLayers ) {
65 // get the R
66 const Trk::CylinderSurface& layerSurface = layIter->surfaceRepresentation();
67 double currentR = layerSurface.bounds().r();
68 ATH_MSG_VERBOSE( "equidistant : registering cylindrical MaterialLayer at radius : " << currentR );
69 layerOrderVector.emplace_back(std::shared_ptr<Layer>(layIter),
70 Amg::Vector3D(currentR, 0.,0.));
71 }
72 // create the binUtility
73 auto binUtility = Trk::BinUtility(layers,rmin,rmax,Trk::open, Trk::binR);
74 ATH_MSG_VERBOSE( "equidistant : created a BinUtility as " << binUtility );
75
76 // create the BinnedArray; BinnedArray now owns the binUtility pointer
77 cylinderLayerArray = std::make_unique<Trk::BinnedArray1D<Trk::Layer>>(layerOrderVector, binUtility);
78 } break;
79
80 // bi-equidistant binning - take care the layers have to be binned equidistant + same thickness
82 {
83
84 // count the layers
85 unsigned int layers = cylLayers.size();
86 // take a reference thinkness
87 double layerThickness = cylLayers[0]->thickness();
88 // the radialstep
89 double radialStep = (rmax-rmin)/(layers-1);
90 // the next step
91 double navigationR = 0.;
92 double navLayerHalflengthZ = 0.;
93 const Amg::Transform3D* layerTransform = nullptr;
94
95 // loop over layers
96 for (auto& layIter : cylLayers ) {
97 // get the dimensions
98 const Trk::CylinderSurface& layerSurface = layIter->surfaceRepresentation();
99 layerTransform = layerSurface.transform().isApprox(Amg::Transform3D::Identity()) ? nullptr : &layerSurface.transform();
100
101 double currentR = layerSurface.bounds().r();
102 navigationR = currentR - 0.5*radialStep;
103
104 navLayerHalflengthZ = layerSurface.bounds().halflengthZ();
105 ATH_MSG_VERBOSE( "bi-equidistant : creating cylindrical NavigationLayer at radius : " << navigationR );
106 auto navLayerSurface =
107 layerTransform ? std::make_unique<Trk::CylinderSurface>(
108 Amg::Transform3D(*layerTransform),navigationR, navLayerHalflengthZ)
109 : std::make_unique<Trk::CylinderSurface>(
110 navigationR, navLayerHalflengthZ);
111 // the navigation layer
112 auto navLayer = std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurface));
113 // push the navigation layer in
114 layerOrderVector.emplace_back(std::move(navLayer),
115 Amg::Vector3D(navigationR, 0., 0.));
116 ATH_MSG_VERBOSE( "bi-equidistant : registering cylindrical MaterialLayer at radius : " << currentR );
117 // push the original layer in
118 layerOrderVector.emplace_back(std::shared_ptr<Trk::Layer>(layIter),
119 Amg::Vector3D(currentR, 0., 0.));
120 }
121
122 // special treatment for the last one
123 ATH_MSG_VERBOSE( "bi-equidistant : creating cylindrical NavigationLayer at radius : " << navigationR+radialStep);
124 auto navLayerSurfacFinal = layerTransform ?
125 std::make_unique<Trk::CylinderSurface>(
126 Amg::Transform3D(*layerTransform), navigationR+radialStep, navLayerHalflengthZ) :
127 std::make_unique<Trk::CylinderSurface>(navigationR+radialStep, navLayerHalflengthZ);
128 // the navigation layer
129 auto navLayer = std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurfacFinal));
130 // push the navigation layer in
131 layerOrderVector.emplace_back(std::move(navLayer),
132 Amg::Vector3D(navigationR+radialStep, 0., 0.));
133
134 ATH_MSG_VERBOSE( layerOrderVector.size() << " cylindrical Layers (material + navigation) built. " );
135
136 // create the binUtility
137 double rMinBoundary = rmin-radialStep+0.5*layerThickness;
138 double rMaxBoundary = rmax+radialStep+0.5*layerThickness;
139 auto binUtility = Trk::BinUtility(layers, layerThickness, rMinBoundary, rMaxBoundary, Trk::open, Trk::binR);
140 ATH_MSG_VERBOSE( "bi-equidistant : created a BinUtility as " << binUtility );
141
142 // create the BinnedArray; BinnedArray now owns the binUtility pointer
143 cylinderLayerArray = std::make_unique<Trk::BinnedArray1D<Trk::Layer>>(layerOrderVector, binUtility);
144
145 } break;
146
147 // arbitrary binning
148 case Trk::arbitrary :
149 {
150 std::vector<float> boundaries;
151 // maz z extension
152 double halfLengthZ = 0;
153 const Amg::Transform3D* layerTransform = nullptr;
154
155 // initial step
156 boundaries.push_back(rmin);
157
158 // loop over the provided layers and put Navigation layers in between
159 for (auto& layIter : cylLayers) {
160 // get the cylinder surface
161 const Trk::CylinderSurface& layerSurface = layIter->surfaceRepresentation();
162 layerTransform = layerSurface.transform().isApprox(Amg::Transform3D::Identity()) ? nullptr : &layerSurface.transform();
163 // and get the halflength
164 double currentHalfLengthZ = layerSurface.bounds().halflengthZ();
165 takeBigger(halfLengthZ, currentHalfLengthZ);
166 double layerRadius = layerSurface.bounds().r();
167 double layerThickness = layIter->thickness();
168 // navigation layer : previous bin
169 double navLayerRadius = 0.5*( (layerRadius-0.5*layerThickness) + boundaries[boundaries.size()-1] );
170 auto navLayerSurface = layerTransform ?
171 std::make_unique<Trk::CylinderSurface>(
172 Amg::Transform3D(*layerTransform), navLayerRadius, halfLengthZ) :
173 std::make_unique<Trk::CylinderSurface>(navLayerRadius, halfLengthZ);
174 // material layer : current bin
175 cylinderLayer = checkAndReplaceEmptyLayer(layIter);
176 if (cylinderLayer){
177 ATH_MSG_VERBOSE( "arbitrary : creating cylindrical NavigationLayer at radius : " << navLayerRadius );
178 layerOrderVector.emplace_back(
179 std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurface)),
180 Amg::Vector3D(navLayerRadius, 0., 0.));
181 ATH_MSG_VERBOSE( "arbitrary : registering cylindrical MaterialLayer at radius :" << layerRadius );
182 layerOrderVector.emplace_back(
183 std::shared_ptr<Trk::Layer>(cylinderLayer),
184 Amg::Vector3D(layerRadius, 0.,0.));
185 boundaries.push_back(layerRadius-0.5*layerThickness);
186 boundaries.push_back(layerRadius+0.5*layerThickness);
187 } else {
188 ATH_MSG_VERBOSE( "arbitrary : empty layer configuration cancelled this building of navigation layer.");
189 }
190 }
191 // close up the array with last bin
192 double navLayerRadiusFinal = 0.5*(rmax+boundaries[boundaries.size()-1]);
193 auto navLayerSurfaceFinal = layerTransform ?
194 std::make_unique<Trk::CylinderSurface>(
195 Amg::Transform3D(*layerTransform), navLayerRadiusFinal, halfLengthZ) :
196 std::make_unique<Trk::CylinderSurface>(navLayerRadiusFinal, halfLengthZ);
197 boundaries.push_back(rmax);
198 ATH_MSG_VERBOSE( "arbitrary : creating cylindrical NavigationLayer at radius : " << navLayerRadiusFinal );
199 layerOrderVector.emplace_back(std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurfaceFinal)),
200 Amg::Vector3D(navLayerRadiusFinal, 0., 0.));
201
202 ATH_MSG_VERBOSE( layerOrderVector.size() << " cylindrical Layers (material + navigation) built. " );
203 // create the BinUtility
204 auto binUtility = Trk::BinUtility(boundaries, Trk::open, Trk::binR);
205 ATH_MSG_VERBOSE( "arbitrary : created a BinUtility as " << binUtility );
206
207 // create the BinnedArray; BinnedArray now owns the binUtility pointer
208 cylinderLayerArray = std::make_unique<Trk::BinnedArray1D<Trk::Layer>>(layerOrderVector, binUtility);
209
210 } break;
211
212 // default return 0
213 default : { return nullptr; }
214 }
215
216 return cylinderLayerArray;
217}
218
219
220std::unique_ptr<Trk::BinnedArray1D<Trk::Layer>> Trk::LayerArrayCreator::discLayerArray(
221 const std::vector<Trk::DiscLayer*>& discLayersInput,
222 double zmin,
223 double zmax,
224 Trk::BinningType btype) const
225{
226
227 ATH_MSG_VERBOSE( " build LayerArray with " << discLayersInput.size() << " disc-like material layers." );
228 ATH_MSG_VERBOSE( " zmin/zmax provided : " << zmin << " / " << zmax );
229
230 // needed for all cases
231 std::unique_ptr<Trk::BinnedArray1D<Trk::Layer>> discLayerArray = nullptr;
232 std::vector<std::pair<std::shared_ptr<Trk::Layer>, Amg::Vector3D>> layerOrderVector;
233
234 //copy so that you can sort
235 std::vector<Trk::DiscLayer*> discLayers(discLayersInput);
236 // sort the vector
237 Trk::DiscLayerSorterZ zSorter;
238 std::sort(discLayers.begin(), discLayers.end(), zSorter);
239 // the layer to be pushed back
240 Trk::Layer* discLayer = nullptr;
241
242 switch (btype) {
243
244 // equidistant binning
245 case Trk::equidistant :
246 {
247 // count the layers
248 size_t layers = discLayers.size();
249 // loop over layers and put them in
250 for (Trk::DiscLayer* layIter : discLayers ) {
251 discLayer = checkAndReplaceEmptyLayer(layIter);
252 // get the Z
253 const Trk::Surface& layerSurface = discLayer->surfaceRepresentation();
254 ATH_MSG_VERBOSE( "equidistant : registering disc-like MaterialLayer at z-Position : " << layerSurface.center().z() );
255 layerOrderVector.emplace_back(std::shared_ptr<Layer>(discLayer),
256 layerSurface.center());
257 }
258 // create the binUitlity
259 auto binUtility = Trk::BinUtility(layers,zmin,zmax,Trk::open,Trk::binZ);
260 ATH_MSG_VERBOSE( "equidistant : created a BinUtility as " << binUtility );
261
262 // create the BinnedArray; BinnedArray now owns the binUtility pointer
263 discLayerArray = std::make_unique<Trk::BinnedArray1D<Trk::Layer>>(layerOrderVector, binUtility);
264
265 } break;
266
267 // bi-equidistant binning
268 case Trk::biequidistant :
269 {
270 // count the layers
271 unsigned int layers = discLayers.size();
272 // take a reference layer thickness
273 double layerThickness = discLayers[0]->thickness();
274 ATH_MSG_VERBOSE( "bi-equidistant : zmin / zmax re-evaluated as = " << zmin << " / " << zmax );
275 // the radialstep
276 double zStep = (zmax-zmin)/(layers-1);
277 double minR = 0.;
278 double maxR = 0.;
279
280 Amg::Transform3D navLayerTransform;
281 double navigationZ = 0.;
282 // loop over layers
283 for (auto& layIter : discLayers) {
284 // get the dimensions
285 const Trk::DiscSurface& layerSurface = layIter->surfaceRepresentation();
286 double currentZ = layerSurface.center().z();
287 // create the navigation Z from current Z
288 navigationZ = currentZ - 0.5*(zStep);
289 navLayerTransform = Amg::Transform3D(Amg::Translation3D(0.,0.,navigationZ));
290 auto navLayerSurface = std::make_unique<Trk::DiscSurface>(navLayerTransform, minR, maxR);
291 // push that layer back
292 ATH_MSG_VERBOSE( "bi-equidistant : creating disc-like NavigationLayer at z-Position : " << navigationZ );
293 const Amg::Vector3D center = navLayerSurface->center();
294 layerOrderVector.emplace_back(
295 std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurface)),
296 center);
297 // and get dimensions
298 const Trk::DiscBounds* dbounds = dynamic_cast<const Trk::DiscBounds*>(&(layerSurface.bounds()));
299 if (dbounds) {
300 minR = dbounds->rMin();
301 maxR = dbounds->rMax();
302 } else { // protection
303 minR = 0.;
304 maxR = 100000.;
305 }
306 // get the material layer first
307 ATH_MSG_VERBOSE( "bi-equidistant : registering disc-like MaterialLayer at z-Position : " << currentZ );
308 layerOrderVector.emplace_back(std::shared_ptr<Trk::Layer>(layIter),
309 layerSurface.center());
310 }
311 // special treatment for last bin
312 ATH_MSG_VERBOSE( "bi-equidistant : creating disc-like NavigationLayer at z-Position : " << navigationZ + zStep );
313 navLayerTransform = Amg::Transform3D(Amg::Translation3D(0.,0.,navigationZ+zStep));
314 auto navLayerSurface = std::make_unique<Trk::DiscSurface>(navLayerTransform, minR, maxR);
315 const Amg::Vector3D center = navLayerSurface->center();
316 layerOrderVector.emplace_back(std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurface)),
317 center);
318 // verbose output
319 ATH_MSG_VERBOSE( layerOrderVector.size() << " disc Layers (material + navigation) built. " );
320
321 // create the binUtility
322 double zminBoundary = zmin-zStep+0.5*layerThickness;
323 double zmaxBoundary = zmax+zStep+0.5*layerThickness;
324 auto binUtility = Trk::BinUtility(layers, layerThickness, zminBoundary, zmaxBoundary, Trk::open, Trk::binZ);
325 ATH_MSG_VERBOSE( "bi-equidistant : created a BinUtility as " << binUtility );
326
327 // create the BinnedArray; BinnedArray now owns the binUtility pointer
328 discLayerArray = std::make_unique<Trk::BinnedArray1D<Trk::Layer>>(layerOrderVector, binUtility);
329
330 } break;
331
332 // arbitrary binning
333 case Trk::arbitrary :
334 {
335 std::vector<float> boundaries;
336
337 // max disc dimension
338 double minR = 10e10;
339 double maxR = 0.;
340
341 // initial boundary
342 boundaries.push_back(zmin);
343
344 // loop over the provided layers and put NavigationLayers in between
345 for (auto& layIter : discLayers ) {
346 // get the cylinder surface
347 const Trk::DiscSurface& layerSurface = layIter->surfaceRepresentation();
348 // and get dimensions
349 const Trk::DiscBounds* dbounds = dynamic_cast<const Trk::DiscBounds*>(&(layerSurface.bounds()));
350 if (dbounds) {
351 double layInnerR = dbounds->rMin();
352 double layOuterR = dbounds->rMax();
353 minR = (layInnerR < minR) ? layInnerR : minR;
354 maxR = (layOuterR > maxR) ? layOuterR : maxR;
355 } else { // protection
356 minR = 0.;
357 maxR = 100000.;
358 }
359 // the radius & position
360 double layerPositionZ = layerSurface.center().z();
361 double layerThickness = layIter->thickness();
362 // navigation Layer
363 double navLayerPositionZ = 0.5*((layerPositionZ-0.5*layerThickness)+boundaries[boundaries.size()-1]);
364 // now fill the layer post slot after navigation layer has been determined
365 // the transform for this
366 Amg::Transform3D navLayerTransform = Amg::Transform3D(Amg::Translation3D(0.,0.,navLayerPositionZ));
367 auto navLayerSurface = std::make_unique<Trk::DiscSurface>(navLayerTransform, minR, maxR);
368
369 // the material layer
370 discLayer = checkAndReplaceEmptyLayer(layIter);
371 if (discLayer) {
372 ATH_MSG_VERBOSE( "arbitrary : creating disc-like NavigationLayer at z-Position : " << navLayerPositionZ );
373 layerOrderVector.emplace_back(std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurface)),
374 Amg::Vector3D(0., 0., navLayerPositionZ));
375 ATH_MSG_VERBOSE( "arbitrary : registering disc-like MaterialLayer at z-Position : " << layerPositionZ );
376 layerOrderVector.emplace_back(
377 std::shared_ptr<Trk::Layer>(discLayer),
378 Amg::Vector3D(0.,0., layerPositionZ));
379 boundaries.push_back(layerPositionZ-0.5*layerThickness);
380 boundaries.push_back(layerPositionZ+0.5*layerThickness);
381 } else {
382 ATH_MSG_VERBOSE( "arbitrary : empty layer configuration cancelled this building of navigation layer.");
383 }
384 }
385 // final material layer
386 double navLayerPositionZFinal = 0.5*(zmax+boundaries[boundaries.size()-1]);
387 Amg::Transform3D navLayerTransformFinal = Amg::Transform3D(
388 Amg::Translation3D(0., 0., navLayerPositionZFinal));
389 auto navLayerSurfaceFinal = std::make_unique<Trk::DiscSurface>(navLayerTransformFinal, minR, maxR);
390 ATH_MSG_VERBOSE( "arbitrary : creating disc-like NavigationLayer at z-Position : " << navLayerPositionZFinal );
391 layerOrderVector.emplace_back(std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurfaceFinal)),
392 Amg::Vector3D(0., 0., navLayerPositionZFinal));
393 ATH_MSG_VERBOSE( layerOrderVector.size() << " disc Layers (material + navigation) built. " );
394 // register the last bounday
395 boundaries.push_back(zmax);
396 // create the BinUtility
397 auto binUtility = Trk::BinUtility(boundaries, Trk::open, Trk::binZ);
398 ATH_MSG_VERBOSE( "arbitrary : created a BinUtility as " << binUtility );
399
400 // create the BinnedArray; BinnedArray now owns the binUtility pointer
401 // cppcheck-suppress memleak
402 discLayerArray = std::make_unique<Trk::BinnedArray1D<Trk::Layer>>(layerOrderVector, binUtility);
403
404 } break;
405
406 // default return 0
407 default : { return nullptr; }
408 }
409
410 return discLayerArray;
411}
412
413
414std::unique_ptr<Trk::BinnedArray1D<Trk::Layer>> Trk::LayerArrayCreator::planeLayerArray(
415 const std::vector<Trk::PlaneLayer*>& planeLayersInput,
416 double posmin,
417 double posmax,
418 Trk::BinningType btype,
419 Trk::BinningValue bv) const
420{
421 ATH_MSG_VERBOSE( " build LayerArray with " << planeLayersInput.size() << " plane-like material layers." );
422
423 // needed for all cases
424 std::unique_ptr<Trk::BinnedArray1D<Trk::Layer>> planeLayerArray = nullptr;
425 std::vector< std::pair< std::shared_ptr<Trk::Layer>, Amg::Vector3D> > layerOrderVector;
426 Amg::Vector3D layerCenter(0.,0.,0.);
427
428 //copy so that you can sort
429 std::vector<Trk::PlaneLayer*> planeLayers(planeLayersInput);
430
431 auto sortBegin = planeLayers.begin();
432 auto sortEnd = planeLayers.end();
433 switch (bv) {
434 case Trk::binX : { std::sort(sortBegin, sortEnd, Trk::PlaneLayerSorterX()); } break;
435 case Trk::binY : { std::sort(sortBegin, sortEnd, Trk::PlaneLayerSorterY()); } break;
436 case Trk::binZ : { std::sort(sortBegin, sortEnd, Trk::PlaneLayerSorterZ()); } break;
437 default : {
438 ATH_MSG_WARNING("Plane Layers can only be sorted in x/y/z. Returning 0.");
439 return nullptr;
440 }
441 }
442
443 // the iterator
444 auto layIter = planeLayers.begin();
445
446 switch (btype) {
447
448 // equidistant binning
449 case Trk::equidistant :
450 {
451 // count the layers
452 unsigned int layers = planeLayers.size();
453 // loop over layers and put them in
454 for ( ; layIter != planeLayers.end(); ++layIter) {
455 // get the X
456 const Trk::PlaneSurface& layerSurface = (*layIter)->surfaceRepresentation();
457 ATH_MSG_VERBOSE( "equidistant : registering plane-like MaterialLayer at position : " << layerSurface.center() );
458
459 layerOrderVector.emplace_back(
460 std::shared_ptr<Layer>(*layIter),
461 layerSurface.center());
462 }
463 // create the binUitlity
464 auto binUtility = Trk::BinUtility(layers,posmin,posmax, Trk::open, bv);
465 // create the BinnedArray
466 planeLayerArray = std::make_unique<Trk::BinnedArray1D<Trk::Layer>>(layerOrderVector, binUtility);
467
468 } break;
469
470 // bi-equidistant binning
471 case Trk::biequidistant :
472 {
473 // count the layers
474 unsigned int layers = planeLayers.size();
475 // the x-step
476 double posStep = (posmax-posmin)/(layers+1);
477
478 double currentPos = posmin + posStep;
479 double lastPos = posmin;
480
481 double minHalfX = 0.;
482 double maxHalfX = 0.;
483 double halfY = 0.;
484
485 double layerThickness = 0.;
486
487 // loop over layers
488 for ( ; layIter != planeLayers.end() ; ++layIter) {
489
490 // get the dimensions
491 const Trk::PlaneSurface& layerSurface = (*layIter)->surfaceRepresentation();
492 // get dimensions
493 const Trk::RectangleBounds* recbounds = dynamic_cast<const Trk::RectangleBounds*>(&(layerSurface.bounds()));
494 // try rectangular hypothesis
495 if (recbounds) {
496 maxHalfX = recbounds->halflengthX();
497 halfY = recbounds->halflengthY();
498 } else {
499 // try trapezoidal hypothesis
500 const Trk::TrapezoidBounds* trapbounds = dynamic_cast<const Trk::TrapezoidBounds*>(&(layerSurface.bounds()));
501 if (trapbounds) {
502 minHalfX = trapbounds->minHalflengthX();
503 maxHalfX = trapbounds->maxHalflengthX();
504 halfY = trapbounds->halflengthY();
505 } else {
506 // protection
507 minHalfX = 0.;
508 maxHalfX = 10e10;
509 halfY = 10e10;
510 }
511 }
512
513 layerThickness = ((*layIter)->thickness() > layerThickness ) ? (*layIter)->thickness() : layerThickness;
514
515 // the navigation Layer
516 double navigationPos = 0.5*(currentPos+lastPos);
517 double navigationX = (bv == Trk::binX) ? navigationPos : 0.;
518 double navigationY = (bv == Trk::binY) ? navigationPos : 0.;
519 double navigationZ = (bv == Trk::binZ) ? navigationPos : 0.;
520 Amg::Translation3D(navigationX,navigationY,navigationZ);
521
522 std::unique_ptr<Trk::PlaneSurface> navLayerSurface = nullptr;
523 Amg::Transform3D navLayerTransform(Amg::Translation3D(navigationX,0.,0.));
524
525 if (std::abs(minHalfX)<10e-5) {
526 navLayerSurface = std::make_unique<Trk::PlaneSurface>(navLayerTransform,
527 maxHalfX,
528 halfY);
529 } else {
530 navLayerSurface = std::make_unique<Trk::PlaneSurface>(navLayerTransform,
531 minHalfX,
532 maxHalfX,
533 halfY);
534 }
535
536 ATH_MSG_VERBOSE( "bi-equidistant : creating plane-like NavigationLayer at position : " << navigationX );
537
538 layerOrderVector.emplace_back(std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurface)),
539 Amg::Vector3D(navigationX, 0.,0.));
540 // restore
541 lastPos = currentPos;
542 // the material Layer
543
544 ATH_MSG_VERBOSE( "bi-equidistant : registering plane-like MaterialLayer at position : " << currentPos );
545 layerOrderVector.emplace_back(
546 std::shared_ptr<Trk::Layer>(*layIter),
547 layerSurface.center());
548
549 // increase the Step
550 currentPos += posStep;
551 }
552
553 // the final navigation layer
554 double navigationPosFinal = 0.5*(currentPos+lastPos);
555 double navigationXFinal = (bv == Trk::binX) ? navigationPosFinal : 0.;
556 double navigationYFinal = (bv == Trk::binY) ? navigationPosFinal : 0.;
557 double navigationZFinal = (bv == Trk::binZ) ? navigationPosFinal : 0.;
558
559 Amg::Transform3D navLayerTransform(Amg::Translation3D(navigationXFinal,navigationYFinal,navigationZFinal));
560
561 auto navLayerSurface = (std::abs(minHalfX)<10e-5) ?
562 std::make_unique<Trk::PlaneSurface>(navLayerTransform, maxHalfX,halfY) :
563 std::make_unique<Trk::PlaneSurface>(navLayerTransform, minHalfX, maxHalfX, halfY);
564
565 ATH_MSG_VERBOSE( "bi-equidistant : creating plane-like NavigationLayer at position : " << navLayerSurface->center() );
566 const Amg::Vector3D center = navLayerSurface->center();
567 layerOrderVector.emplace_back(std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurface)),
568 center);
569
570 // create the binUtility
571 auto binUtility = Trk::BinUtility(layers, layerThickness, posmin, posmax, Trk::open, bv);
572
573 // create the BinnedArray
574 planeLayerArray = std::make_unique<Trk::BinnedArray1D<Trk::Layer>>(layerOrderVector, binUtility);
575
576 } break;
577
578 // arbitrary binning
579 case Trk::arbitrary :
580 {
581
582 std::vector<float> boundaries;
583 boundaries.push_back(posmin);
584 // max plane dimension
585 double minHalfX = 0.;
586 double maxHalfX = 0.;
587 double halfY = 0.;
588
589 // loop over the layers and register navigation layers in between
590 for ( ; layIter != planeLayers.end(); ++layIter) {
591
592 // get the cylinder surface
593 const Trk::PlaneSurface& layerSurface = (*layIter)->surfaceRepresentation();
594 // get dimensions
595 const Trk::RectangleBounds* recbounds = dynamic_cast<const Trk::RectangleBounds*>(&(layerSurface.bounds()));
596 // try rectangular hypothesis
597 if (recbounds) {
598 maxHalfX = recbounds->halflengthX();
599 halfY = recbounds->halflengthY();
600 } else {
601 // try trapezoidal hypothesis
602 const Trk::TrapezoidBounds* trapbounds = dynamic_cast<const Trk::TrapezoidBounds*>(&(layerSurface.bounds()));
603 if (trapbounds) {
604 minHalfX = trapbounds->minHalflengthX();
605 maxHalfX = trapbounds->maxHalflengthX();
606 halfY = trapbounds->halflengthY();
607 } else {
608 // protection
609 minHalfX = 0.;
610 maxHalfX = 10e10;
611 halfY = 10e10;
612 }
613 }
614 // the x position
615 // and get dimensions
616 layerCenter = layerSurface.center();
617 double layerPosition = layerCenter[bv];
618 // get the thickness
619 double layerThickness = (*layIter)->thickness();
620 // register
621 boundaries.push_back(layerPosition-0.5*layerThickness);
622 double navLayerPositionX = (bv == Trk::binX) ? 0.5*(layerPosition+boundaries[boundaries.size()-1]) : layerCenter.x();
623 double navLayerPositionY = (bv == Trk::binY) ? 0.5*(layerPosition+boundaries[boundaries.size()-1]) : layerCenter.y();
624 double navLayerPositionZ = (bv == Trk::binZ) ? 0.5*(layerPosition+boundaries[boundaries.size()-1]) : layerCenter.z();
625 Amg::Translation3D navLayerPosition(navLayerPositionX,navLayerPositionY,navLayerPositionZ);
626 Amg::Transform3D navLayerTransform(navLayerPosition);
627 // create the navigation plane layer
628 auto navLayerSurface = (std::abs(minHalfX)<10e-5) ?
629 std::make_unique<Trk::PlaneSurface>( navLayerTransform, maxHalfX, halfY ) :
630 std::make_unique<Trk::PlaneSurface>( navLayerTransform, minHalfX, maxHalfX, halfY );
631 ATH_MSG_VERBOSE( "arbitrary : creating plane-like NavigationLayer at position : " << navLayerPositionX );
632 layerOrderVector.emplace_back(
633 std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurface)),
634 Amg::Vector3D(navLayerPositionX, navLayerPositionY, navLayerPositionZ));
635 // register the material layer
636 boundaries.push_back(layerPosition+0.5*layerThickness);
637 // material layer
638 layerOrderVector.emplace_back(
639 std::shared_ptr<Trk::Layer>(*layIter),
640 layerSurface.center());
641
642 }
643 // last NavigationLayer
644 double navLayerPositionXFinal = (bv == Trk::binX) ? 0.5*(posmax+boundaries[boundaries.size()-1]) : layerCenter.x();
645 double navLayerPositionYFinal = (bv == Trk::binY) ? 0.5*(posmax+boundaries[boundaries.size()-1]) : layerCenter.y();
646 double navLayerPositionZFinal = (bv == Trk::binZ) ? 0.5*(posmax+boundaries[boundaries.size()-1]) : layerCenter.z();
647 Amg::Translation3D navLayerPositionFinal(navLayerPositionXFinal,navLayerPositionYFinal,navLayerPositionZFinal);
648 Amg::Transform3D navLayerTransformFinal(navLayerPositionFinal);
649 // create the navigation plane layer
650 auto navLayerSurfaceFinal = (std::abs(minHalfX)<10e-5) ?
651 std::make_unique<Trk::PlaneSurface>( navLayerTransformFinal, maxHalfX, halfY ) :
652 std::make_unique<Trk::PlaneSurface>( navLayerTransformFinal, minHalfX, maxHalfX, halfY );
653 ATH_MSG_VERBOSE( "arbitrary : creating plane-like NavigationLayer at position : " << 0.5*(posmax+boundaries[boundaries.size()-1]) );
654 layerOrderVector.emplace_back(std::make_shared<Trk::NavigationLayer>(std::move(navLayerSurfaceFinal)),
655 Amg::Vector3D(navLayerPositionXFinal, navLayerPositionYFinal, navLayerPositionZFinal));
656
657 ATH_MSG_VERBOSE( layerOrderVector.size() << " plane Layers (material + navigation) built. " );
658
659 // create the BinUtility
660 auto binUtility = Trk::BinUtility(boundaries, Trk::open, bv);
661 // and the BinnedArray
662 planeLayerArray = std::make_unique<Trk::BinnedArray1D<Trk::Layer>>(layerOrderVector, binUtility);
663
664 } break;
665 // default return 0
666 default : { return nullptr; }
667 }
668
669 return planeLayerArray;
670 //cppcheck-suppress memleak
671}
672
674 // empty layers will be replaced by navigation layers
675 if (m_emptyLayerMode){
676 if (lay->layerMaterialProperties() || lay->surfaceArray()) return lay;
678 " replacing dummyMaterial layer with "
679 << (m_emptyLayerMode > 1 ? " nothing" : " NavigationLayer."));
680 Trk::NavigationLayer* nLayer =
682 ? nullptr
685 delete lay;
686 return nLayer;
687 }
688 // don't replace - just give back what you had
689 return lay;
690}
691
692
693
#define ATH_MSG_VERBOSE(x)
#define ATH_MSG_WARNING(x)
#define takeBigger(current, test)
AthAlgTool(const std::string &type, const std::string &name, const IInterface *parent)
Constructor with parameters:
Gaudi::Details::PropertyBase & declareProperty(Gaudi::Property< T, V, H > &t)
A generic symmetric BinUtility, for fully symmetric binning in terms of binning grid and binning type...
Definition BinUtility.h:39
virtual double r() const override final
This method returns the radius.
double halflengthZ() const
This method returns the halflengthZ.
Functor for CylinderLayer R-Sorting.
Class for a CylinderSurface in the ATLAS detector.
virtual const CylinderBounds & bounds() const override final
This method returns the CylinderBounds by reference (NoBounds is not possible for cylinder)
Class to describe the bounds for a planar DiscSurface.
Definition DiscBounds.h:44
double rMax() const
This method returns outer radius.
double rMin() const
This method returns inner radius.
simple helper function to allow sorting of DiscLayers in z
Definition DiscLayer.h:152
Class to describe a disc-like detector layer for tracking, it inhertis from both, Layer base class an...
Definition DiscLayer.h:45
Class for a DiscSurface in the ATLAS detector.
Definition DiscSurface.h:54
const SurfaceBounds & bounds() const override final
This method returns the bounds by reference.
std::unique_ptr< Trk::BinnedArray1D< Layer > > cylinderLayerArray(const std::vector< CylinderLayer * > &layers, double rmin, double rmax, BinningType btype=arbitrary) const
LayerArrayCreator interface method - for Barrel-like layers.
std::unique_ptr< Trk::BinnedArray1D< Layer > > discLayerArray(const std::vector< DiscLayer * > &layers, double zmin, double zmax, BinningType btype=arbitrary) const
LayerArrayCreator interface method - for Endcap-like layers.
LayerArrayCreator(const std::string &, const std::string &, const IInterface *)
Constructor.
Trk::Layer * checkAndReplaceEmptyLayer(Trk::Layer *lay) const
std::unique_ptr< Trk::BinnedArray1D< Layer > > planeLayerArray(const std::vector< PlaneLayer * > &layers, double min, double max, BinningType btype=arbitrary, Trk::BinningValue bv=Trk::binX) const
LayerArrayCreator interface method - for Planar-like layers.
int m_emptyLayerMode
0 - do nothing, 1 - replace with navigation layer, 2 - delete
Base Class for a Detector Layer in the Tracking realm.
Definition Layer.h:72
virtual const Surface & surfaceRepresentation() const =0
Transforms the layer into a Surface representation for extrapolation.
const SurfaceArray * surfaceArray() const
Return the entire SurfaceArray, returns nullptr if no SurfaceArray.
const LayerMaterialProperties * layerMaterialProperties() const
getting the LayerMaterialProperties including full/pre/post update
Class to be used for gaps in Volumes as a navigational link.
Functor for PlaneLayer X-Sorting.
Definition PlaneLayer.h:116
Functor for PlaneLayer Y-Sorting.
Definition PlaneLayer.h:129
Functor for PlaneLayer Z-Sorting.
Definition PlaneLayer.h:142
Class for a planaer rectangular or trapezoidal surface in the ATLAS detector.
virtual const SurfaceBounds & bounds() const override final
This method returns the bounds by reference, static NoBounds in case of no boundaries.
Bounds for a rectangular, planar surface.
double halflengthX() const
for consistant naming
double halflengthY() const
for consitant naming
Abstract Base Class for tracking surfaces.
const Amg::Transform3D & transform() const
Returns HepGeom::Transform3D by reference.
const Amg::Vector3D & center() const
Returns the center position of the Surface.
std::unique_ptr< Surface > uniqueClone() const
NVI method returning unique_ptr clone.
Bounds for a trapezoidal, planar Surface.
double halflengthY() const
This method returns the halflength in Y (second coordinate of local surface frame)
double minHalflengthX() const
This method returns the minimal halflength in X (first coordinate of local surface frame)
double maxHalflengthX() const
This method returns the maximal halflength in X (first coordinate of local surface frame)
Eigen::Affine3d Transform3D
Eigen::Matrix< double, 3, 1 > Vector3D
Eigen::Translation< double, 3 > Translation3D
@ open
Definition BinningType.h:40
BinningType
, BinningOption & BinningAccess
Definition BinningType.h:31
@ biequidistant
Definition BinningType.h:33
@ equidistant
Definition BinningType.h:32
@ arbitrary
Definition BinningType.h:34
BinningValue
how to take the global / local position
Definition BinningType.h:46
@ binR
Definition BinningType.h:50
@ binX
Definition BinningType.h:47
@ binZ
Definition BinningType.h:49
@ binY
Definition BinningType.h:48
void sort(typename DataModel_detail::iterator< DVL > beg, typename DataModel_detail::iterator< DVL > end)
Specialization of sort for DataVector/List.