File indexing completed on 2025-02-22 10:31:21
0001
0002
0003
0004
0005
0006
0007
0008 #pragma once
0009
0010 #include "corecel/math/Algorithms.hh"
0011 #include "geocel/Types.hh"
0012
0013 namespace celeritas
0014 {
0015
0016
0017
0018
0019 template<class GTV>
0020 class LinearPropagator
0021 {
0022 public:
0023
0024
0025 using result_type = Propagation;
0026
0027
0028 public:
0029
0030 CELER_FUNCTION LinearPropagator(GTV&& track)
0031 : geo_(::celeritas::forward<GTV>(track))
0032 {
0033 }
0034
0035
0036 inline CELER_FUNCTION result_type operator()();
0037
0038
0039 inline CELER_FUNCTION result_type operator()(real_type dist);
0040
0041
0042 static CELER_CONSTEXPR_FUNCTION bool tracks_can_loop() { return false; }
0043
0044 private:
0045 GTV geo_;
0046 };
0047
0048
0049
0050
0051 template<class GTV>
0052 CELER_FUNCTION LinearPropagator(GTV&&) -> LinearPropagator<GTV>;
0053
0054
0055
0056
0057
0058 template<class GTV>
0059 CELER_FUNCTION auto LinearPropagator<GTV>::operator()() -> result_type
0060 {
0061 CELER_EXPECT(!geo_.is_outside());
0062
0063 result_type result = geo_.find_next_step();
0064 CELER_ASSERT(result.boundary);
0065 geo_.move_to_boundary();
0066
0067 return result;
0068 }
0069
0070
0071
0072
0073
0074 template<class GTV>
0075 CELER_FUNCTION auto
0076 LinearPropagator<GTV>::operator()(real_type dist) -> result_type
0077 {
0078 CELER_EXPECT(dist > 0);
0079
0080 result_type result = geo_.find_next_step(dist);
0081
0082 if (result.boundary)
0083 {
0084 geo_.move_to_boundary();
0085 }
0086 else
0087 {
0088 CELER_ASSERT(dist == result.distance);
0089 geo_.move_internal(dist);
0090 }
0091
0092 return result;
0093 }
0094
0095
0096 }