File indexing completed on 2025-01-18 09:13:07
0001
0002
0003
0004
0005
0006
0007
0008
0009 #include <boost/test/unit_test.hpp>
0010
0011 #include "Acts/Geometry/DiscLayer.hpp"
0012 #include "Acts/Geometry/GeometryContext.hpp"
0013 #include "Acts/Geometry/GeometryHierarchyMap.hpp"
0014 #include "Acts/Geometry/Layer.hpp"
0015 #include "Acts/Geometry/LayerCreator.hpp"
0016 #include "Acts/Geometry/SurfaceArrayCreator.hpp"
0017 #include "Acts/Plugins/ActSVG/LayerSvgConverter.hpp"
0018 #include "Acts/Plugins/ActSVG/SvgUtils.hpp"
0019 #include "Acts/Surfaces/DiscSurface.hpp"
0020 #include "Acts/Surfaces/PlaneSurface.hpp"
0021 #include "Acts/Surfaces/RadialBounds.hpp"
0022 #include "Acts/Surfaces/TrapezoidBounds.hpp"
0023 #include "Acts/Tests/CommonHelpers/CylindricalTrackingGeometry.hpp"
0024
0025 #include <fstream>
0026 #include <memory>
0027 #include <numbers>
0028 #include <vector>
0029
0030 BOOST_AUTO_TEST_SUITE(ActSvg)
0031
0032 namespace {
0033
0034 Acts::GeometryContext tgContext;
0035
0036 std::shared_ptr<const Acts::LayerCreator> lCreator(nullptr);
0037
0038 void setupTools() {
0039 if (lCreator == nullptr) {
0040 Acts::LayerCreator::Config lCreatorCfg;
0041 lCreatorCfg.surfaceArrayCreator =
0042 std::make_shared<const Acts::SurfaceArrayCreator>();
0043 lCreator = std::make_shared<const Acts::LayerCreator>(lCreatorCfg);
0044 }
0045 }
0046
0047 std::shared_ptr<Acts::Layer> generateDiscLayer(double rInner, double rOuter,
0048 unsigned int quarterSegments,
0049 unsigned int nRings,
0050 bool useTrapezoids = false) {
0051
0052 setupTools();
0053 unsigned int fullSegments = 4 * quarterSegments;
0054 std::vector<std::shared_ptr<const Acts::Surface>> moduleSurfaces;
0055 double phiStep = 2 * std::numbers::pi / fullSegments;
0056 double rStep = (rOuter - rInner) / nRings;
0057
0058 moduleSurfaces.reserve(fullSegments * nRings);
0059
0060 if (!useTrapezoids) {
0061 for (unsigned int ir = 0; ir < nRings; ++ir) {
0062 std::shared_ptr<const Acts::RadialBounds> rBounds = nullptr;
0063 rBounds = std::make_shared<Acts::RadialBounds>(
0064 rInner + ir * rStep - 0.025 * rInner,
0065 rInner + (ir + 1u) * rStep + 0.025 * rInner, 0.55 * phiStep, 0.);
0066 for (unsigned int is = 0; is < fullSegments; ++is) {
0067
0068 auto placement = Acts::Transform3::Identity();
0069 if ((is % 2) != 0u) {
0070 placement.pretranslate(Acts::Vector3{0., 0., 2.});
0071 }
0072 placement.rotate(
0073 Eigen::AngleAxisd(is * phiStep, Acts::Vector3(0, 0, 1)));
0074 auto dModule =
0075 Acts::Surface::makeShared<Acts::DiscSurface>(placement, rBounds);
0076 moduleSurfaces.push_back(dModule);
0077 }
0078 }
0079 } else {
0080 for (unsigned int ir = 0; ir < nRings; ++ir) {
0081
0082 double radius = rInner + (ir + 0.5) * rStep;
0083 double yHalf = rStep * 0.5125;
0084
0085 double xHalfMin =
0086 1.15 * (rInner + ir * rStep) * std::numbers::pi / fullSegments;
0087 double xHalfMax =
0088 1.15 * (rInner + (ir + 1) * rStep) * std::numbers::pi / fullSegments;
0089
0090 std::shared_ptr<const Acts::TrapezoidBounds> tBounds =
0091 std::make_shared<const Acts::TrapezoidBounds>(xHalfMin, xHalfMax,
0092 yHalf);
0093 for (unsigned int is = 0; is < fullSegments; ++is) {
0094
0095 double cphi = -std::numbers::pi + is * phiStep;
0096 Acts::Vector3 center(radius * std::cos(cphi), radius * std::sin(cphi),
0097 (is % 2) * 2 + (ir % 2) * 5);
0098
0099 Acts::Vector3 localY(std::cos(cphi), std::sin(cphi), 0.);
0100 Acts::Vector3 localZ(0., 0., 1.);
0101 Acts::Vector3 localX = localY.cross(localZ);
0102 Acts::RotationMatrix3 rotation;
0103 rotation.col(0) = localX;
0104 rotation.col(1) = localY;
0105 rotation.col(2) = localZ;
0106 Acts::Transform3 placement(Acts::Translation3(center) * rotation);
0107
0108 auto dModule =
0109 Acts::Surface::makeShared<Acts::PlaneSurface>(placement, tBounds);
0110 moduleSurfaces.push_back(dModule);
0111 }
0112 }
0113 }
0114
0115 return lCreator->discLayer(tgContext, moduleSurfaces, nRings, fullSegments);
0116 }
0117
0118 }
0119
0120 BOOST_AUTO_TEST_CASE(DiscLayerRadialSvg) {
0121
0122 Acts::Svg::Style discLayerStyle;
0123 discLayerStyle.fillColor = {51, 153, 255};
0124 discLayerStyle.fillOpacity = 0.75;
0125 discLayerStyle.highlightColor = {255, 153, 51};
0126 discLayerStyle.highlights = {"mouseover", "mouseout"};
0127 discLayerStyle.strokeColor = {25, 25, 25};
0128 discLayerStyle.strokeWidth = 0.5;
0129 discLayerStyle.quarterSegments = 72u;
0130
0131 Acts::GeometryIdentifier geoID{0};
0132
0133
0134 auto discLayer = generateDiscLayer(100, 250, 32u, 4u);
0135
0136 Acts::Svg::LayerConverter::Options lOptions;
0137 lOptions.name = "disc_layer_sectors";
0138 lOptions.surfaceStyles =
0139 Acts::GeometryHierarchyMap<Acts::Svg::Style>({{geoID, discLayerStyle}});
0140
0141
0142 auto discLayerSheets =
0143 Acts::Svg::LayerConverter::convert(tgContext, *discLayer, lOptions);
0144
0145 for (const auto& s : discLayerSheets) {
0146 Acts::Svg::toFile({s}, s._id + ".svg");
0147 }
0148 }
0149
0150 BOOST_AUTO_TEST_CASE(DiscLayerTrapezoidSvg) {
0151
0152 Acts::Svg::Style discLayerStyle;
0153 discLayerStyle.fillColor = {51, 153, 255};
0154 discLayerStyle.fillOpacity = 0.75;
0155 discLayerStyle.highlightColor = {255, 153, 51};
0156 discLayerStyle.highlights = {"mouseover", "mouseout"};
0157 discLayerStyle.strokeColor = {25, 25, 25};
0158 discLayerStyle.strokeWidth = 0.5;
0159 discLayerStyle.quarterSegments = 72u;
0160
0161 Acts::GeometryIdentifier geoID{0};
0162
0163
0164 auto discLayer = generateDiscLayer(100, 250, 32u, 4u, true);
0165
0166 Acts::Svg::LayerConverter::Options lOptions;
0167 lOptions.name = "disc_layer_trapezoid";
0168 lOptions.surfaceStyles =
0169 Acts::GeometryHierarchyMap<Acts::Svg::Style>({{geoID, discLayerStyle}});
0170
0171
0172 auto discLayerSheets =
0173 Acts::Svg::LayerConverter::convert(tgContext, *discLayer, lOptions);
0174
0175 for (const auto& s : discLayerSheets) {
0176 Acts::Svg::toFile({s}, s._id + ".svg");
0177 }
0178 }
0179
0180 BOOST_AUTO_TEST_CASE(CylinderLayerSvg) {
0181
0182 Acts::Svg::Style cylinderLayerStyle;
0183 cylinderLayerStyle.fillColor = {51, 153, 255};
0184 cylinderLayerStyle.fillOpacity = 0.75;
0185 cylinderLayerStyle.highlightColor = {255, 153, 51};
0186 cylinderLayerStyle.highlights = {"mouseover", "mouseout"};
0187 cylinderLayerStyle.strokeColor = {25, 25, 25};
0188 cylinderLayerStyle.strokeWidth = 0.5;
0189 cylinderLayerStyle.quarterSegments = 72u;
0190
0191 Acts::GeometryIdentifier geoID{0};
0192
0193 Acts::Test::CylindricalTrackingGeometry cGeometry(tgContext);
0194 auto tGeometry = cGeometry();
0195 auto pixelVolume =
0196 tGeometry->lowestTrackingVolume(tgContext, Acts::Vector3(50., 0., 0.));
0197 if (pixelVolume != nullptr && pixelVolume->confinedLayers() != nullptr) {
0198 auto layers = pixelVolume->confinedLayers()->arrayObjects();
0199 std::size_t il = 0;
0200 for (const auto& layer : layers) {
0201 if (layer->surfaceArray() != nullptr) {
0202 Acts::Svg::LayerConverter::Options lOptions;
0203 lOptions.name = "cylinder_layer_" + std::to_string(il++);
0204 lOptions.surfaceStyles = Acts::GeometryHierarchyMap<Acts::Svg::Style>(
0205 {{geoID, cylinderLayerStyle}});
0206
0207
0208 auto layerSheets =
0209 Acts::Svg::LayerConverter::convert(tgContext, *layer, lOptions);
0210 for (const auto& s : layerSheets) {
0211 Acts::Svg::toFile({s}, s._id + ".svg");
0212 }
0213 }
0214 }
0215 }
0216 }
0217
0218 BOOST_AUTO_TEST_CASE(PlaeyLayerSvg) {}
0219
0220 BOOST_AUTO_TEST_SUITE_END()