30 std::unique_ptr<Acts::SurfaceArray>
33 std::vector<std::shared_ptr<const Surface>> surfaces,
size_t binsPhi,
34 size_t binsZ, std::optional<ProtoLayer> protoLayerOpt,
35 const std::shared_ptr<const Transform3D>& transformOpt)
const {
39 protoLayerOpt ? *protoLayerOpt :
ProtoLayer(gctx, surfacesRaw);
42 ACTS_VERBOSE(
" -- with " << surfaces.size() <<
" surfaces.")
43 ACTS_VERBOSE(
" -- with phi x z = " << binsPhi <<
" x " << binsZ <<
" = "
44 << binsPhi * binsZ <<
" bins.");
47 transformOpt !=
nullptr ? *transformOpt : Transform3D::Identity();
50 protoLayer, transform, binsPhi);
54 double R = protoLayer.
maxR - protoLayer.
minR;
62 auto localToGlobal = [itransform,
R](
const Vector2D& loc) {
64 Vector3D(R * std::cos(loc[0]), R * std::sin(loc[0]), loc[1]);
67 std::unique_ptr<SurfaceArray::ISurfaceGridLookup> sl =
69 detail::AxisBoundaryType::Bound>(
70 globalToLocal, localToGlobal, pAxisPhi, pAxisZ);
72 sl->fill(gctx, surfacesRaw);
75 return std::make_unique<SurfaceArray>(
76 std::move(sl), std::move(surfaces),
77 std::make_shared<const Transform3D>(
transform));
80 std::unique_ptr<Acts::SurfaceArray>
83 std::vector<std::shared_ptr<const Surface>> surfaces,
BinningType bTypePhi,
84 BinningType bTypeZ, std::optional<ProtoLayer> protoLayerOpt,
85 const std::shared_ptr<const Transform3D>& transformOpt)
const {
89 protoLayerOpt ? *protoLayerOpt :
ProtoLayer(gctx, surfacesRaw);
91 double R = 0.5 * (protoLayer.
maxR - protoLayer.
minR);
93 transformOpt !=
nullptr ? *transformOpt : Transform3D::Identity();
99 pAxisPhi = createEquidistantAxis(gctx, surfacesRaw,
binPhi, protoLayer,
103 createVariableAxis(gctx, surfacesRaw,
binPhi, protoLayer, transform);
108 createEquidistantAxis(gctx, surfacesRaw,
binZ, protoLayer, transform);
110 pAxisZ = createVariableAxis(gctx, surfacesRaw,
binZ, protoLayer, transform);
118 auto localToGlobal = [itransform,
R](
const Vector2D& loc) {
120 Vector3D(R * std::cos(loc[0]), R * std::sin(loc[0]), loc[1]);
123 std::unique_ptr<SurfaceArray::ISurfaceGridLookup> sl =
124 makeSurfaceGridLookup2D<detail::AxisBoundaryType::Closed,
125 detail::AxisBoundaryType::Bound>(
126 globalToLocal, localToGlobal, pAxisPhi, pAxisZ);
128 sl->
fill(gctx, surfacesRaw);
129 completeBinning(gctx, *sl, surfacesRaw);
133 size_t bins0 = axes.at(0)->getNBins();
134 size_t bins1 = axes.at(1)->getNBins();
137 ACTS_VERBOSE(
" -- with " << surfaces.size() <<
" surfaces.")
138 ACTS_VERBOSE(
" -- with phi x z = " << bins0 <<
" x " << bins1 <<
" = "
139 << bins0 * bins1 <<
" bins.");
141 return std::make_unique<SurfaceArray>(
142 std::move(sl), std::move(surfaces),
143 std::make_shared<const Transform3D>(
transform));
146 std::unique_ptr<Acts::SurfaceArray>
149 std::vector<std::shared_ptr<const Surface>> surfaces,
size_t binsR,
150 size_t binsPhi, std::optional<ProtoLayer> protoLayerOpt,
151 const std::shared_ptr<const Transform3D>& transformOpt)
const {
155 protoLayerOpt ? *protoLayerOpt :
ProtoLayer(gctx, surfacesRaw);
160 transformOpt !=
nullptr ? *transformOpt : Transform3D::Identity();
162 ProtoAxis pAxisR = createEquidistantAxis(gctx, surfacesRaw,
binR, protoLayer,
165 protoLayer, transform, binsPhi);
167 double Z = 0.5 * (protoLayer.
minZ + protoLayer.
maxZ);
168 ACTS_VERBOSE(
"- z-position of disk estimated as " << Z);
176 auto localToGlobal = [itransform,
Z](
const Vector2D& loc) {
178 Vector3D(loc[0] * std::cos(loc[1]), loc[0] * std::sin(loc[1]), Z);
181 std::unique_ptr<SurfaceArray::ISurfaceGridLookup> sl =
182 makeSurfaceGridLookup2D<detail::AxisBoundaryType::Bound,
183 detail::AxisBoundaryType::Closed>(
184 globalToLocal, localToGlobal, pAxisR, pAxisPhi);
188 size_t bins0 = axes.at(0)->getNBins();
189 size_t bins1 = axes.at(1)->getNBins();
191 ACTS_VERBOSE(
" -- with " << surfaces.size() <<
" surfaces.")
192 ACTS_VERBOSE(
" -- with r x phi = " << bins0 <<
" x " << bins1 <<
" = "
193 << bins0 * bins1 <<
" bins.");
194 sl->
fill(gctx, surfacesRaw);
195 completeBinning(gctx, *sl, surfacesRaw);
197 return std::make_unique<SurfaceArray>(
198 std::move(sl), std::move(surfaces),
199 std::make_shared<const Transform3D>(
transform));
202 std::unique_ptr<Acts::SurfaceArray>
205 std::vector<std::shared_ptr<const Surface>> surfaces,
BinningType bTypeR,
206 BinningType bTypePhi, std::optional<ProtoLayer> protoLayerOpt,
207 const std::shared_ptr<const Transform3D>& transformOpt)
const {
211 protoLayerOpt ? *protoLayerOpt :
ProtoLayer(gctx, surfacesRaw);
216 transformOpt !=
nullptr ? *transformOpt : Transform3D::Identity();
223 createEquidistantAxis(gctx, surfacesRaw,
binR, protoLayer, transform);
225 pAxisR = createVariableAxis(gctx, surfacesRaw,
binR, protoLayer, transform);
230 if (pAxisR.
nBins > 1) {
233 std::vector<std::vector<const Surface*>> phiModules(pAxisR.
nBins);
234 for (
const auto& srf : surfacesRaw) {
237 phiModules.at(bin).push_back(srf);
240 std::vector<size_t> nPhiModules;
241 auto matcher = m_cfg.surfaceMatcher;
243 return matcher(gctx,
binPhi, a,
b);
247 phiModules.begin(), phiModules.end(), std::back_inserter(nPhiModules),
248 [&equal,
this](std::vector<const Surface*> surfaces_) ->
size_t {
249 return this->findKeySurfaces(surfaces_, equal).size();
259 (*std::min_element(nPhiModules.begin(), nPhiModules.end()));
260 pAxisPhi = createEquidistantAxis(gctx, surfacesRaw,
binPhi, protoLayer,
261 transform, nBinsPhi);
266 pAxisPhi = createEquidistantAxis(gctx, surfacesRaw,
binPhi, protoLayer,
270 createVariableAxis(gctx, surfacesRaw,
binPhi, protoLayer, transform);
274 double Z = 0.5 * (protoLayer.
minZ + protoLayer.
maxZ);
275 ACTS_VERBOSE(
"- z-position of disk estimated as " << Z);
283 auto localToGlobal = [itransform,
Z](
const Vector2D& loc) {
285 Vector3D(loc[0] * std::cos(loc[1]), loc[0] * std::sin(loc[1]), Z);
288 std::unique_ptr<SurfaceArray::ISurfaceGridLookup> sl =
289 makeSurfaceGridLookup2D<detail::AxisBoundaryType::Bound,
290 detail::AxisBoundaryType::Closed>(
291 globalToLocal, localToGlobal, pAxisR, pAxisPhi);
295 size_t bins0 = axes.at(0)->getNBins();
296 size_t bins1 = axes.at(1)->getNBins();
298 ACTS_VERBOSE(
" -- with " << surfaces.size() <<
" surfaces.")
299 ACTS_VERBOSE(
" -- with r x phi = " << bins0 <<
" x " << bins1 <<
" = "
300 << bins0 * bins1 <<
" bins.");
302 sl->
fill(gctx, surfacesRaw);
303 completeBinning(gctx, *sl, surfacesRaw);
305 return std::make_unique<SurfaceArray>(
306 std::move(sl), std::move(surfaces),
307 std::make_shared<const Transform3D>(
transform));
311 std::unique_ptr<Acts::SurfaceArray>
314 std::vector<std::shared_ptr<const Surface>> surfaces,
size_t bins1,
315 size_t bins2,
BinningValue bValue, std::optional<ProtoLayer> protoLayerOpt,
316 const std::shared_ptr<const Transform3D>& transformOpt)
const {
320 protoLayerOpt ? *protoLayerOpt :
ProtoLayer(gctx, surfacesRaw);
323 ACTS_VERBOSE(
" -- with " << surfaces.size() <<
" surfaces.")
324 ACTS_VERBOSE(
" -- with " << bins1 <<
" x " << bins2 <<
" = " << bins1 * bins2
328 transformOpt !=
nullptr ? *transformOpt : Transform3D::Identity();
336 auto localToGlobal = [itransform](
const Vector2D& loc) {
337 return itransform *
Vector3D(loc.x(), loc.y(), 0.);
340 std::unique_ptr<SurfaceArray::ISurfaceGridLookup> sl;
345 ProtoAxis pAxis1 = createEquidistantAxis(gctx, surfacesRaw,
binY,
346 protoLayer, transform, bins1);
347 ProtoAxis pAxis2 = createEquidistantAxis(gctx, surfacesRaw,
binZ,
348 protoLayer, transform, bins2);
349 sl = makeSurfaceGridLookup2D<detail::AxisBoundaryType::Bound,
350 detail::AxisBoundaryType::Bound>(
351 globalToLocal, localToGlobal, pAxis1, pAxis2);
355 ProtoAxis pAxis1 = createEquidistantAxis(gctx, surfacesRaw,
binX,
356 protoLayer, transform, bins1);
357 ProtoAxis pAxis2 = createEquidistantAxis(gctx, surfacesRaw,
binZ,
358 protoLayer, transform, bins2);
359 sl = makeSurfaceGridLookup2D<detail::AxisBoundaryType::Bound,
360 detail::AxisBoundaryType::Bound>(
361 globalToLocal, localToGlobal, pAxis1, pAxis2);
365 ProtoAxis pAxis1 = createEquidistantAxis(gctx, surfacesRaw,
binX,
366 protoLayer, transform, bins1);
367 ProtoAxis pAxis2 = createEquidistantAxis(gctx, surfacesRaw,
binY,
368 protoLayer, transform, bins2);
369 sl = makeSurfaceGridLookup2D<detail::AxisBoundaryType::Bound,
370 detail::AxisBoundaryType::Bound>(
371 globalToLocal, localToGlobal, pAxis1, pAxis2);
375 throw std::invalid_argument(
376 "Acts::SurfaceArrayCreator::"
377 "surfaceArrayOnPlane: Invalid binning "
382 sl->
fill(gctx, surfacesRaw);
383 completeBinning(gctx, *sl, surfacesRaw);
385 return std::make_unique<SurfaceArray>(
386 std::move(sl), std::move(surfaces),
387 std::make_shared<const Transform3D>(
transform));
392 const std::vector<const Surface*>& surfaces,
394 std::vector<const Surface*> keys;
395 for (
const auto& srfA : surfaces) {
397 for (
const auto& srfB : keys) {
398 if (equal(srfA, srfB)) {
404 keys.push_back(srfA);
414 auto matcher = m_cfg.surfaceMatcher;
416 return matcher(gctx, bValue, a,
b);
418 std::vector<const Surface*> keys = findKeySurfaces(surfaces, equal);
427 if (surfaces.empty()) {
428 throw std::logic_error(
429 "No surfaces handed over for creating arbitrary bin utility!");
435 auto matcher = m_cfg.surfaceMatcher;
438 return matcher(gctx, bValue, a,
b);
440 std::vector<const Acts::Surface*> keys = findKeySurfaces(surfaces, equal);
442 std::vector<double> bValues;
444 std::stable_sort(keys.begin(), keys.end(),
450 double maxPhi = 0.5 * (
phi(keys.at(0)->binningPosition(gctx,
binPhi)) +
451 phi(keys.at(1)->binningPosition(gctx,
binPhi)));
460 double previous =
phi(keys.at(0)->binningPosition(gctx,
binPhi));
462 for (
size_t i = 1; i < keys.size(); i++) {
470 bValues.push_back(edge);
478 if (backBounds ==
nullptr)
480 "Given SurfaceBounds are not planar - not implemented for "
481 "other bounds yet! ");
483 std::vector<Acts::Vector3D> backVertices =
484 makeGlobalVertices(gctx, *backSurface, backBounds->
vertices());
485 double maxBValue =
phi(
486 *std::max_element(backVertices.begin(), backVertices.end(),
491 bValues.push_back(maxBValue);
493 bValues.push_back(
M_PI);
496 std::stable_sort(keys.begin(), keys.end(),
499 b->binningPosition(gctx,
binZ).z());
502 bValues.push_back(protoLayer.
minZ);
503 bValues.push_back(protoLayer.
maxZ);
506 double previous = keys.front()->binningPosition(gctx,
binZ).z();
513 0.5 * (previous + (*surface)->binningPosition(gctx,
binZ).z()));
514 previous = (*surface)->binningPosition(gctx,
binZ).z();
517 std::stable_sort(keys.begin(), keys.end(),
523 bValues.push_back(protoLayer.
minR);
524 bValues.push_back(protoLayer.
maxR);
527 double previous =
perp(keys.front()->binningPosition(gctx,
binR));
535 0.5 * (previous +
perp((*surface)->binningPosition(gctx,
binR))));
536 previous =
perp((*surface)->binningPosition(gctx,
binR));
539 std::sort(bValues.begin(), bValues.end());
540 ACTS_VERBOSE(
"Create variable binning Axis for binned SurfaceArray");
543 " (binX = 0, binY = 1, binZ = 2, binR = 3, binPhi = 4, "
544 "binRPhi = 5, binH = 6, binEta = 7)");
545 ACTS_VERBOSE(
" Number of bins: " << (bValues.size() - 1));
547 << bValues.back() <<
")");
551 pAxis.bValue = bValue;
552 pAxis.binEdges = bValues;
553 pAxis.nBins = bValues.size() - 1;
562 size_t nBins)
const {
563 if (surfaces.empty()) {
564 throw std::logic_error(
565 "No surfaces handed over for creating equidistant axis!");
577 std::vector<const Acts::Surface*> keys;
582 binNumber = determineBinCount(gctx, surfaces, bValue);
589 auto matcher = m_cfg.surfaceMatcher;
594 if (m_cfg.doPhiBinningOptimization) {
599 surfaces.begin(), surfaces.end(),
602 phi(
b->binningPosition(gctx,
binR));
606 auto equal = [&
gctx, &bValue, &matcher](
const Surface*
a,
608 return matcher(gctx, bValue, a,
b);
610 keys = findKeySurfaces(surfaces, equal);
613 if (keys.size() > 1) {
631 minimum = protoLayer.
minPhi;
632 maximum = protoLayer.
maxPhi;
647 maximum = protoLayer.
maxR;
648 minimum = protoLayer.
minR;
656 maximum = protoLayer.
maxX;
657 minimum = protoLayer.
minX;
665 maximum = protoLayer.
maxY;
666 minimum = protoLayer.
minY;
674 maximum = protoLayer.
maxZ;
675 minimum = protoLayer.
minZ;
679 throw std::invalid_argument(
680 "Acts::SurfaceArrayCreator::"
681 "createEquidistantAxis: Invalid binning "
686 ACTS_VERBOSE(
"Create equidistant binning Axis for binned SurfaceArray");
689 " (binX = 0, binY = 1, binZ = 2, binR = 3, binPhi = 4, "
690 "binRPhi = 5, binH = 6, binEta = 7)");
692 ACTS_VERBOSE(
" (Min/Max) = (" << minimum <<
"/" << maximum <<
")");
699 pAxis.
nBins = binNumber;
706 const std::vector<Acts::Vector2D>& locVertices)
const {
707 std::vector<Acts::Vector3D> globVertices;
708 for (
auto& vertex : locVertices) {
711 globVertices.push_back(globVertex);