File indexing completed on 2025-01-18 09:12:45
0001
0002
0003
0004
0005
0006
0007
0008
0009 #include <boost/test/test_tools.hpp>
0010 #include <boost/test/unit_test.hpp>
0011
0012 #include "Acts/Definitions/Algebra.hpp"
0013 #include "Acts/Definitions/Common.hpp"
0014 #include "Acts/Definitions/Direction.hpp"
0015 #include "Acts/Definitions/Tolerance.hpp"
0016 #include "Acts/Definitions/TrackParametrization.hpp"
0017 #include "Acts/Definitions/Units.hpp"
0018 #include "Acts/EventData/GenericBoundTrackParameters.hpp"
0019 #include "Acts/EventData/GenericCurvilinearTrackParameters.hpp"
0020 #include "Acts/EventData/ParticleHypothesis.hpp"
0021 #include "Acts/EventData/TrackParameters.hpp"
0022 #include "Acts/EventData/TransformationHelpers.hpp"
0023 #include "Acts/Geometry/GeometryContext.hpp"
0024 #include "Acts/MagneticField/ConstantBField.hpp"
0025 #include "Acts/MagneticField/MagneticFieldContext.hpp"
0026 #include "Acts/MagneticField/MagneticFieldProvider.hpp"
0027 #include "Acts/Propagator/AtlasStepper.hpp"
0028 #include "Acts/Propagator/ConstrainedStep.hpp"
0029 #include "Acts/Surfaces/BoundaryTolerance.hpp"
0030 #include "Acts/Surfaces/CurvilinearSurface.hpp"
0031 #include "Acts/Surfaces/DiscSurface.hpp"
0032 #include "Acts/Surfaces/PerigeeSurface.hpp"
0033 #include "Acts/Surfaces/PlaneSurface.hpp"
0034 #include "Acts/Surfaces/StrawSurface.hpp"
0035 #include "Acts/Surfaces/Surface.hpp"
0036 #include "Acts/Tests/CommonHelpers/Assertions.hpp"
0037 #include "Acts/Tests/CommonHelpers/FloatComparisons.hpp"
0038 #include "Acts/Utilities/Result.hpp"
0039
0040 #include <algorithm>
0041 #include <array>
0042 #include <iterator>
0043 #include <limits>
0044 #include <memory>
0045 #include <optional>
0046 #include <type_traits>
0047 #include <utility>
0048
0049 using namespace Acts::UnitLiterals;
0050
0051 namespace Acts::Test {
0052
0053 using Acts::VectorHelpers::makeVector4;
0054 using Covariance = BoundSquareMatrix;
0055 using Jacobian = BoundMatrix;
0056 using Stepper = Acts::AtlasStepper;
0057
0058
0059 struct MockPropagatorState {
0060 MockPropagatorState(Stepper::State stepperState)
0061 : stepping(std::move(stepperState)) {}
0062
0063
0064 Stepper::State stepping;
0065
0066 struct {
0067 Direction direction = Direction::Backward();
0068 struct {
0069 double stepTolerance = 10_um;
0070 } stepping;
0071 } options;
0072 };
0073
0074 struct MockNavigator {};
0075
0076 static constexpr MockNavigator navigator;
0077
0078
0079 static constexpr auto eps = 1024 * std::numeric_limits<double>::epsilon();
0080
0081
0082 static constexpr auto stepSize = 10_mm;
0083 static constexpr Direction navDir = Direction::Backward();
0084 static auto magneticField =
0085 std::make_shared<ConstantBField>(Vector3(0.1_T, -0.2_T, 2_T));
0086
0087
0088 static const Vector4 pos4(1_mm, -1_mm, 2_mm, 2_ns);
0089 static const Vector3 pos = pos4.segment<3>(ePos0);
0090 static const auto time = pos4[eTime];
0091 static const Vector3 unitDir = Vector3(-2, 2, 1).normalized();
0092 static constexpr auto absMom = 1_GeV;
0093 static constexpr auto charge = -1_e;
0094 static const auto particleHypothesis = ParticleHypothesis::pion();
0095 static const Covariance cov = Covariance::Identity();
0096
0097
0098 static const GeometryContext geoCtx;
0099 static const MagneticFieldContext magCtx;
0100
0101 BOOST_AUTO_TEST_SUITE(AtlasStepper)
0102
0103
0104 BOOST_AUTO_TEST_CASE(ConstructState) {
0105 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, std::nullopt,
0106 particleHypothesis);
0107
0108 Stepper stepper(magneticField);
0109
0110 Stepper::Options options(geoCtx, magCtx);
0111 options.maxStepSize = stepSize;
0112
0113 Stepper::State state = stepper.makeState(options, cp);
0114
0115 BOOST_CHECK(!state.covTransport);
0116 BOOST_CHECK_EQUAL(state.covariance, nullptr);
0117 BOOST_CHECK_EQUAL(state.pVector[0], pos.x());
0118 BOOST_CHECK_EQUAL(state.pVector[1], pos.y());
0119 BOOST_CHECK_EQUAL(state.pVector[2], pos.z());
0120 BOOST_CHECK_EQUAL(state.pVector[3], time);
0121 CHECK_CLOSE_ABS(state.pVector[4], unitDir.x(), eps);
0122 CHECK_CLOSE_ABS(state.pVector[5], unitDir.y(), eps);
0123 CHECK_CLOSE_ABS(state.pVector[6], unitDir.z(), eps);
0124 BOOST_CHECK_EQUAL(state.pVector[7], charge / absMom);
0125 BOOST_CHECK_EQUAL(state.pathAccumulated, 0.);
0126 BOOST_CHECK_EQUAL(state.stepSize.value(), stepSize);
0127 BOOST_CHECK_EQUAL(state.previousStepSize, 0.);
0128 }
0129
0130
0131 BOOST_AUTO_TEST_CASE(ConstructStateWithCovariance) {
0132 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0133 particleHypothesis);
0134
0135 Stepper stepper(magneticField);
0136
0137 Stepper::Options options(geoCtx, magCtx);
0138 options.maxStepSize = stepSize;
0139
0140 Stepper::State state = stepper.makeState(options, cp);
0141
0142 BOOST_CHECK(state.covTransport);
0143 BOOST_CHECK_EQUAL(*state.covariance, cov);
0144 BOOST_CHECK_EQUAL(state.pVector[0], pos.x());
0145 BOOST_CHECK_EQUAL(state.pVector[1], pos.y());
0146 BOOST_CHECK_EQUAL(state.pVector[2], pos.z());
0147 BOOST_CHECK_EQUAL(state.pVector[3], time);
0148 CHECK_CLOSE_ABS(state.pVector[4], unitDir.x(), eps);
0149 CHECK_CLOSE_ABS(state.pVector[5], unitDir.y(), eps);
0150 CHECK_CLOSE_ABS(state.pVector[6], unitDir.z(), eps);
0151 BOOST_CHECK_EQUAL(state.pVector[7], charge / absMom);
0152 BOOST_CHECK_EQUAL(state.pathAccumulated, 0.);
0153 BOOST_CHECK_EQUAL(state.stepSize.value(), stepSize);
0154 BOOST_CHECK_EQUAL(state.previousStepSize, 0.);
0155 }
0156
0157
0158 BOOST_AUTO_TEST_CASE(Getters) {
0159 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0160 particleHypothesis);
0161
0162 Stepper stepper(magneticField);
0163
0164 Stepper::Options options(geoCtx, magCtx);
0165 options.maxStepSize = stepSize;
0166
0167 Stepper::State state = stepper.makeState(options, cp);
0168
0169 CHECK_CLOSE_ABS(stepper.position(state), pos, eps);
0170 CHECK_CLOSE_ABS(stepper.time(state), time, eps);
0171 CHECK_CLOSE_ABS(stepper.direction(state), unitDir, eps);
0172 CHECK_CLOSE_ABS(stepper.absoluteMomentum(state), absMom, eps);
0173 BOOST_CHECK_EQUAL(stepper.charge(state), charge);
0174 }
0175
0176
0177 BOOST_AUTO_TEST_CASE(UpdateFromBound) {
0178 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0179 particleHypothesis);
0180
0181 Stepper stepper(magneticField);
0182
0183 Stepper::Options options(geoCtx, magCtx);
0184 options.maxStepSize = stepSize;
0185
0186 Stepper::State state = stepper.makeState(options, cp);
0187
0188 auto newPos4 = (pos4 + Vector4(1_mm, 2_mm, 3_mm, 20_ns)).eval();
0189 auto newPos = newPos4.segment<3>(ePos0);
0190 auto newTime = newPos4[eTime];
0191 auto newUnitDir = (unitDir + Vector3(1, -1, -1)).normalized();
0192 auto newAbsMom = 0.9 * absMom;
0193
0194
0195 auto plane = CurvilinearSurface(newPos, newUnitDir).planeSurface();
0196 auto params =
0197 BoundTrackParameters::create(plane, geoCtx, newPos4, newUnitDir,
0198 charge / absMom, cov, particleHypothesis)
0199 .value();
0200 FreeVector freeParams;
0201 freeParams[eFreePos0] = newPos4[ePos0];
0202 freeParams[eFreePos1] = newPos4[ePos1];
0203 freeParams[eFreePos2] = newPos4[ePos2];
0204 freeParams[eFreeTime] = newPos4[eTime];
0205 freeParams[eFreeDir0] = newUnitDir[eMom0];
0206 freeParams[eFreeDir1] = newUnitDir[eMom1];
0207 freeParams[eFreeDir2] = newUnitDir[eMom2];
0208 freeParams[eFreeQOverP] = charge / newAbsMom;
0209
0210
0211
0212 state.state_ready = false;
0213 BOOST_CHECK(params.covariance().has_value());
0214 stepper.update(state, freeParams, params.parameters(), *params.covariance(),
0215 *plane);
0216 CHECK_CLOSE_ABS(stepper.position(state), newPos, eps);
0217 CHECK_CLOSE_ABS(stepper.time(state), newTime, eps);
0218 CHECK_CLOSE_ABS(stepper.direction(state), newUnitDir, eps);
0219 CHECK_CLOSE_ABS(stepper.absoluteMomentum(state), newAbsMom, eps);
0220 BOOST_CHECK_EQUAL(stepper.charge(state), charge);
0221 }
0222
0223
0224 BOOST_AUTO_TEST_CASE(UpdateFromComponents) {
0225 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0226 particleHypothesis);
0227
0228 Stepper stepper(magneticField);
0229
0230 Stepper::Options options(geoCtx, magCtx);
0231 options.maxStepSize = stepSize;
0232
0233 Stepper::State state = stepper.makeState(options, cp);
0234
0235 auto newPos = (pos + Vector3(1_mm, 2_mm, 3_mm)).eval();
0236 auto newTime = time + 20_ns;
0237 auto newUnitDir = (unitDir + Vector3(1, -1, -1)).normalized();
0238 auto newAbsMom = 0.9 * absMom;
0239
0240 stepper.update(state, newPos, newUnitDir, charge / newAbsMom, newTime);
0241 CHECK_CLOSE_ABS(stepper.position(state), newPos, eps);
0242 CHECK_CLOSE_ABS(stepper.time(state), newTime, eps);
0243 CHECK_CLOSE_ABS(stepper.direction(state), newUnitDir, eps);
0244 CHECK_CLOSE_ABS(stepper.absoluteMomentum(state), newAbsMom, eps);
0245 BOOST_CHECK_EQUAL(stepper.charge(state), charge);
0246 }
0247
0248
0249 BOOST_AUTO_TEST_CASE(BuildBound) {
0250 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0251 particleHypothesis);
0252
0253 Stepper stepper(magneticField);
0254
0255 Stepper::Options options(geoCtx, magCtx);
0256 options.maxStepSize = stepSize;
0257
0258 Stepper::State state = stepper.makeState(options, cp);
0259
0260
0261 auto plane = CurvilinearSurface(pos, unitDir).planeSurface();
0262
0263 auto&& [pars, jac, pathLength] = stepper.boundState(state, *plane).value();
0264
0265 CHECK_CLOSE_ABS(pars.position(geoCtx), pos, eps);
0266 CHECK_CLOSE_ABS(pars.time(), time, eps);
0267 CHECK_CLOSE_ABS(pars.momentum(), absMom * unitDir, eps);
0268 BOOST_CHECK_EQUAL(pars.charge(), charge);
0269 BOOST_CHECK(pars.covariance().has_value());
0270 BOOST_CHECK_NE(*pars.covariance(), cov);
0271
0272 CHECK_CLOSE_ABS(jac, Jacobian(Jacobian::Identity()), eps);
0273
0274 CHECK_CLOSE_ABS(pathLength, 0., eps);
0275 }
0276
0277
0278 BOOST_AUTO_TEST_CASE(BuildCurvilinear) {
0279 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0280 particleHypothesis);
0281
0282 Stepper stepper(magneticField);
0283
0284 Stepper::Options options(geoCtx, magCtx);
0285 options.maxStepSize = stepSize;
0286
0287 Stepper::State state = stepper.makeState(options, cp);
0288
0289 auto&& [pars, jac, pathLength] = stepper.curvilinearState(state);
0290
0291 CHECK_CLOSE_ABS(pars.position(geoCtx), pos, eps);
0292 CHECK_CLOSE_ABS(pars.time(), time, eps);
0293 CHECK_CLOSE_ABS(pars.momentum(), absMom * unitDir, eps);
0294 BOOST_CHECK_EQUAL(pars.charge(), charge);
0295 BOOST_CHECK(pars.covariance().has_value());
0296 BOOST_CHECK_NE(*pars.covariance(), cov);
0297
0298 CHECK_CLOSE_ABS(jac, Jacobian(Jacobian::Identity()), eps);
0299
0300 CHECK_CLOSE_ABS(pathLength, 0., eps);
0301 }
0302
0303
0304 BOOST_AUTO_TEST_CASE(Step) {
0305 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0306 particleHypothesis);
0307
0308 Stepper stepper(magneticField);
0309
0310 Stepper::Options options(geoCtx, magCtx);
0311 options.maxStepSize = stepSize;
0312
0313 MockPropagatorState state(stepper.makeState(options, cp));
0314 state.stepping.covTransport = false;
0315
0316
0317 auto res = stepper.step(state, navigator);
0318 BOOST_CHECK(res.ok());
0319
0320
0321 auto h = res.value();
0322 BOOST_CHECK_EQUAL(state.stepping.stepSize.value(), stepSize);
0323 BOOST_CHECK_EQUAL(state.stepping.stepSize.value(), h * navDir);
0324
0325
0326 auto deltaPos = (stepper.position(state.stepping) - pos).eval();
0327 BOOST_CHECK_LT(0, deltaPos.norm());
0328
0329 auto deltaTime = stepper.time(state.stepping) - time;
0330 BOOST_CHECK_LT(0, std::abs(deltaTime));
0331
0332 auto projDir = stepper.direction(state.stepping).dot(unitDir);
0333 BOOST_CHECK_LT(projDir, 1);
0334
0335
0336 CHECK_CLOSE_ABS(stepper.absoluteMomentum(state.stepping), absMom, eps);
0337 BOOST_CHECK_EQUAL(stepper.charge(state.stepping), charge);
0338 }
0339
0340
0341 BOOST_AUTO_TEST_CASE(StepWithCovariance) {
0342 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0343 particleHypothesis);
0344
0345 Stepper stepper(magneticField);
0346
0347 Stepper::Options options(geoCtx, magCtx);
0348 options.maxStepSize = stepSize;
0349
0350 MockPropagatorState state(stepper.makeState(options, cp));
0351 state.stepping.covTransport = true;
0352
0353
0354 auto res = stepper.step(state, navigator);
0355 BOOST_CHECK(res.ok());
0356
0357
0358 auto h = res.value();
0359 BOOST_CHECK_EQUAL(state.stepping.stepSize.value(), stepSize);
0360 BOOST_CHECK_EQUAL(state.stepping.stepSize.value(), h * navDir);
0361
0362
0363 auto deltaPos = (stepper.position(state.stepping) - pos).eval();
0364 BOOST_CHECK_LT(0, deltaPos.norm());
0365
0366 auto deltaTime = stepper.time(state.stepping) - time;
0367 BOOST_CHECK_LT(0, std::abs(deltaTime));
0368
0369 auto projDir = stepper.direction(state.stepping).dot(unitDir);
0370 BOOST_CHECK_LT(projDir, 1);
0371
0372
0373 CHECK_CLOSE_ABS(stepper.absoluteMomentum(state.stepping), absMom, eps);
0374 BOOST_CHECK_EQUAL(stepper.charge(state.stepping), charge);
0375
0376 stepper.transportCovarianceToCurvilinear(state.stepping);
0377 BOOST_CHECK_NE(state.stepping.cov, cov);
0378 }
0379
0380
0381 BOOST_AUTO_TEST_CASE(Reset) {
0382 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0383 particleHypothesis);
0384
0385 Stepper stepper(magneticField);
0386
0387 Stepper::Options options(geoCtx, magCtx);
0388 options.maxStepSize = stepSize;
0389
0390 MockPropagatorState state(stepper.makeState(options, cp));
0391 state.stepping.covTransport = true;
0392
0393
0394 stepper.step(state, navigator);
0395
0396
0397 Vector3 newPos(1.5, -2.5, 3.5);
0398 auto newAbsMom = 4.2 * absMom;
0399 double newTime = 7.5;
0400 double newCharge = 1.;
0401 BoundSquareMatrix newCov = 8.5 * Covariance::Identity();
0402 cp = CurvilinearTrackParameters(makeVector4(newPos, newTime), unitDir,
0403 newCharge / newAbsMom, newCov,
0404 particleHypothesis);
0405 FreeVector freeParams = transformBoundToFreeParameters(
0406 cp.referenceSurface(), geoCtx, cp.parameters());
0407 Direction navDir = Direction::Forward();
0408 double stepSize = -256.;
0409
0410 auto copyState = [&](auto& field, const auto& other) {
0411 using field_t = std::decay_t<decltype(field)>;
0412 std::decay_t<decltype(other)> copy = stepper.makeState(options, cp);
0413
0414 copy.state_ready = other.state_ready;
0415 copy.useJacobian = other.useJacobian;
0416 copy.step = other.step;
0417 copy.maxPathLength = other.maxPathLength;
0418 copy.mcondition = other.mcondition;
0419 copy.needgradient = other.needgradient;
0420 copy.newfield = other.newfield;
0421 copy.field = other.field;
0422 copy.pVector = other.pVector;
0423 std::copy(std::begin(other.parameters), std::end(other.parameters),
0424 std::begin(copy.parameters));
0425 copy.covariance = other.covariance;
0426 copy.covTransport = other.covTransport;
0427 std::copy(std::begin(other.jacobian), std::end(other.jacobian),
0428 std::begin(copy.jacobian));
0429 copy.pathAccumulated = other.pathAccumulated;
0430 copy.stepSize = other.stepSize;
0431 copy.previousStepSize = other.previousStepSize;
0432
0433 copy.fieldCache = MagneticFieldProvider::Cache(
0434 std::in_place_type<typename field_t::Cache>,
0435 other.fieldCache.template as<typename field_t::Cache>());
0436
0437 copy.debug = other.debug;
0438 copy.debugString = other.debugString;
0439 copy.debugPfxWidth = other.debugPfxWidth;
0440 copy.debugMsgWidth = other.debugMsgWidth;
0441
0442 return copy;
0443 };
0444
0445
0446 Stepper::State stateCopy = copyState(*magneticField, state.stepping);
0447 BOOST_CHECK(cp.covariance().has_value());
0448 stepper.resetState(stateCopy, cp.parameters(), *cp.covariance(),
0449 cp.referenceSurface(), stepSize);
0450
0451 BOOST_CHECK(stateCopy.covTransport);
0452 BOOST_CHECK_EQUAL(*stateCopy.covariance, newCov);
0453 BOOST_CHECK_EQUAL(stepper.position(stateCopy),
0454 freeParams.template segment<3>(eFreePos0));
0455 BOOST_CHECK_EQUAL(stepper.direction(stateCopy),
0456 freeParams.template segment<3>(eFreeDir0).normalized());
0457 BOOST_CHECK_EQUAL(stepper.absoluteMomentum(stateCopy),
0458 std::abs(1. / freeParams[eFreeQOverP]));
0459 BOOST_CHECK_EQUAL(stepper.charge(stateCopy), stepper.charge(state.stepping));
0460 BOOST_CHECK_EQUAL(stepper.time(stateCopy), freeParams[eFreeTime]);
0461 BOOST_CHECK_EQUAL(stateCopy.pathAccumulated, 0.);
0462 BOOST_CHECK_EQUAL(stateCopy.stepSize.value(), navDir * stepSize);
0463 BOOST_CHECK_EQUAL(stateCopy.previousStepSize,
0464 state.stepping.previousStepSize);
0465
0466
0467 stateCopy = copyState(*magneticField, state.stepping);
0468 stepper.resetState(stateCopy, cp.parameters(), *cp.covariance(),
0469 cp.referenceSurface());
0470
0471 BOOST_CHECK(stateCopy.covTransport);
0472 BOOST_CHECK_EQUAL(*stateCopy.covariance, newCov);
0473 BOOST_CHECK_EQUAL(stepper.position(stateCopy),
0474 freeParams.template segment<3>(eFreePos0));
0475 BOOST_CHECK_EQUAL(stepper.direction(stateCopy),
0476 freeParams.template segment<3>(eFreeDir0).normalized());
0477 BOOST_CHECK_EQUAL(stepper.absoluteMomentum(stateCopy),
0478 std::abs(1. / freeParams[eFreeQOverP]));
0479 BOOST_CHECK_EQUAL(stepper.charge(stateCopy), stepper.charge(state.stepping));
0480 BOOST_CHECK_EQUAL(stepper.time(stateCopy), freeParams[eFreeTime]);
0481 BOOST_CHECK_EQUAL(stateCopy.pathAccumulated, 0.);
0482 BOOST_CHECK_EQUAL(stateCopy.stepSize.value(),
0483 std::numeric_limits<double>::max());
0484 BOOST_CHECK_EQUAL(stateCopy.previousStepSize,
0485 state.stepping.previousStepSize);
0486
0487
0488 stateCopy = copyState(*magneticField, state.stepping);
0489 stepper.resetState(stateCopy, cp.parameters(), *cp.covariance(),
0490 cp.referenceSurface());
0491
0492 BOOST_CHECK(stateCopy.covTransport);
0493 BOOST_CHECK_EQUAL(*stateCopy.covariance, newCov);
0494 BOOST_CHECK_EQUAL(stepper.position(stateCopy),
0495 freeParams.template segment<3>(eFreePos0));
0496 BOOST_CHECK_EQUAL(stepper.direction(stateCopy),
0497 freeParams.template segment<3>(eFreeDir0).normalized());
0498 BOOST_CHECK_EQUAL(stepper.absoluteMomentum(stateCopy),
0499 std::abs(1. / freeParams[eFreeQOverP]));
0500 BOOST_CHECK_EQUAL(stepper.charge(stateCopy), stepper.charge(state.stepping));
0501 BOOST_CHECK_EQUAL(stepper.time(stateCopy), freeParams[eFreeTime]);
0502 BOOST_CHECK_EQUAL(stateCopy.pathAccumulated, 0.);
0503 BOOST_CHECK_EQUAL(stateCopy.stepSize.value(),
0504 std::numeric_limits<double>::max());
0505 BOOST_CHECK_EQUAL(stateCopy.previousStepSize,
0506 state.stepping.previousStepSize);
0507
0508
0509
0510
0511 newPos << 0.5, -1.5, 0.;
0512 newAbsMom *= 1.23;
0513 newTime = 8.4;
0514 newCharge = -1.;
0515 newCov = 10.9 * Covariance::Identity();
0516 Transform3 trafo = Transform3::Identity();
0517 auto disc = Surface::makeShared<DiscSurface>(trafo);
0518 auto boundDisc = BoundTrackParameters::create(
0519 disc, geoCtx, makeVector4(newPos, newTime), unitDir,
0520 newCharge / newAbsMom, newCov, particleHypothesis)
0521 .value();
0522
0523
0524 Stepper::State stateDisc = copyState(*magneticField, state.stepping);
0525 BOOST_CHECK(boundDisc.covariance().has_value());
0526 stepper.resetState(stateDisc, boundDisc.parameters(), *boundDisc.covariance(),
0527 boundDisc.referenceSurface());
0528
0529 CHECK_NE_COLLECTIONS(stateDisc.pVector, stateCopy.pVector);
0530 CHECK_NE_COLLECTIONS(stateDisc.pVector, state.stepping.pVector);
0531
0532
0533
0534 newPos << -2.06155, -2.06155, 3.5;
0535 newAbsMom *= 0.45;
0536 newTime = 2.3;
0537 newCharge = 1.;
0538 newCov = 8.7 * Covariance::Identity();
0539 auto perigee = Surface::makeShared<PerigeeSurface>(trafo);
0540 auto boundPerigee =
0541 BoundTrackParameters::create(
0542 perigee, geoCtx, makeVector4(newPos, newTime), unitDir,
0543 newCharge / newAbsMom, newCov, particleHypothesis)
0544 .value();
0545
0546
0547 Stepper::State statePerigee = copyState(*magneticField, state.stepping);
0548 BOOST_CHECK(boundPerigee.covariance().has_value());
0549 stepper.resetState(statePerigee, boundPerigee.parameters(),
0550 *boundPerigee.covariance(),
0551 boundPerigee.referenceSurface());
0552 CHECK_NE_COLLECTIONS(statePerigee.pVector, stateCopy.pVector);
0553 CHECK_NE_COLLECTIONS(statePerigee.pVector, state.stepping.pVector);
0554 CHECK_NE_COLLECTIONS(statePerigee.pVector, stateDisc.pVector);
0555
0556
0557
0558 auto straw = Surface::makeShared<StrawSurface>(trafo);
0559 auto boundStraw = BoundTrackParameters::create(
0560 straw, geoCtx, makeVector4(newPos, newTime), unitDir,
0561 newCharge / newAbsMom, newCov, particleHypothesis)
0562 .value();
0563
0564
0565 Stepper::State stateStraw = copyState(*magneticField, state.stepping);
0566 BOOST_CHECK(boundStraw.covariance().has_value());
0567 stepper.resetState(stateStraw, boundStraw.parameters(),
0568 *boundStraw.covariance(), boundStraw.referenceSurface());
0569 CHECK_NE_COLLECTIONS(stateStraw.pVector, stateCopy.pVector);
0570 CHECK_NE_COLLECTIONS(stateStraw.pVector, state.stepping.pVector);
0571 CHECK_NE_COLLECTIONS(stateStraw.pVector, stateDisc.pVector);
0572 BOOST_CHECK_EQUAL_COLLECTIONS(
0573 stateStraw.pVector.begin(), stateStraw.pVector.end(),
0574 statePerigee.pVector.begin(), statePerigee.pVector.end());
0575 }
0576
0577 BOOST_AUTO_TEST_CASE(StepSize) {
0578 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0579 particleHypothesis);
0580
0581 Stepper stepper(magneticField);
0582
0583 Stepper::Options options(geoCtx, magCtx);
0584 options.maxStepSize = stepSize;
0585
0586 Stepper::State state = stepper.makeState(options, cp);
0587
0588 stepper.updateStepSize(state, -5_cm, ConstrainedStep::Type::Navigator);
0589 BOOST_CHECK_EQUAL(state.previousStepSize, stepSize);
0590 BOOST_CHECK_EQUAL(state.stepSize.value(), -5_cm);
0591
0592 stepper.releaseStepSize(state, ConstrainedStep::Type::Navigator);
0593 BOOST_CHECK_EQUAL(state.stepSize.value(), stepSize);
0594 }
0595
0596
0597 BOOST_AUTO_TEST_CASE(StepSizeSurface) {
0598 CurvilinearTrackParameters cp(pos4, unitDir, charge / absMom, cov,
0599 particleHypothesis);
0600
0601 Stepper stepper(magneticField);
0602
0603 Stepper::Options options(geoCtx, magCtx);
0604 options.maxStepSize = stepSize;
0605
0606 Stepper::State state = stepper.makeState(options, cp);
0607
0608 auto distance = 10_mm;
0609 auto target = CurvilinearSurface(pos + navDir * distance * unitDir, unitDir)
0610 .planeSurface();
0611
0612 stepper.updateSurfaceStatus(
0613 state, *target, 0, navDir, BoundaryTolerance::Infinite(),
0614 s_onSurfaceTolerance, ConstrainedStep::Type::Navigator);
0615 BOOST_CHECK_EQUAL(state.stepSize.value(ConstrainedStep::Type::Navigator),
0616 distance);
0617
0618
0619 stepper.updateStepSize(state,
0620 target
0621 ->intersect(geoCtx, stepper.position(state),
0622 navDir * stepper.direction(state),
0623 BoundaryTolerance::Infinite())
0624 .closest(),
0625 navDir, ConstrainedStep::Type::Navigator);
0626 BOOST_CHECK_EQUAL(state.stepSize.value(), distance);
0627
0628
0629 state.stepSize.setUser(navDir * stepSize);
0630 stepper.releaseStepSize(state, ConstrainedStep::Type::Navigator);
0631 stepper.updateStepSize(state,
0632 target
0633 ->intersect(geoCtx, stepper.position(state),
0634 navDir * stepper.direction(state),
0635 BoundaryTolerance::Infinite())
0636 .closest(),
0637 navDir, ConstrainedStep::Type::Navigator);
0638 BOOST_CHECK_EQUAL(state.stepSize.value(), navDir * stepSize);
0639 }
0640
0641 BOOST_AUTO_TEST_SUITE_END()
0642
0643 }