67 constexpr explicit operator bool() const noexcept {
76constexpr std::uint64_t
rhythm_mix(std::uint64_t value)
noexcept {
77 value += 0x9E3779B97F4A7C15ull;
78 value = (value ^ (value >> 30u)) * 0xBF58476D1CE4E5B9ull;
79 value = (value ^ (value >> 27u)) * 0x94D049BB133111EBull;
80 return value ^ (value >> 31u);
84 std::size_t target_step)
noexcept {
86 value =
rhythm_mix(value ^
static_cast<std::uint64_t
>(coordinate.cycle));
87 value =
rhythm_mix(value ^ (
static_cast<std::uint64_t
>(coordinate.lane) << 32u));
88 return rhythm_mix(value ^
static_cast<std::uint64_t
>(target_step));
110constexpr std::size_t
delayed_step(std::size_t step, std::size_t length,
111 std::int64_t phase_steps)
noexcept {
112 const auto magnitude = phase_steps >= 0
113 ?
static_cast<std::uint64_t
>(phase_steps)
114 :
static_cast<std::uint64_t
>(-(phase_steps + 1)) + 1u;
115 const auto phase =
static_cast<std::size_t
>(magnitude % length);
116 if (phase_steps >= 0)
117 return step >= phase ? step - phase : length - (phase - step);
118 return step < length - phase ? step + phase : step - (length - phase);
125 std::size_t multiplier,
126 std::size_t divisor)
noexcept {
127 std::size_t quotient = 0;
128 std::size_t remainder = 0;
129 auto bit = std::size_t{1} << (std::numeric_limits<std::size_t>::digits - 1);
130 for (; bit != 0; bit >>= 1u) {
132 if (remainder >= divisor - remainder) {
133 remainder -= divisor - remainder;
136 remainder += remainder;
138 if ((multiplier & bit) == 0)
140 if (remainder >= divisor - multiplicand) {
141 remainder -= divisor - multiplicand;
144 remainder += multiplicand;
150template <std::
size_t MaxSteps>
153 std::size_t target_step)
noexcept {
154 const auto shifted =
delayed_step(target_step, config.target_steps, config.phase_steps);
156 return shifted % source.size();
160template <std::
size_t MaxSteps>
163 std::size_t target_step)
noexcept {
165 const bool source_onset = *source.at(source_step);
166 bool candidate =
false;
167 switch (config.relationship) {
169 candidate = source_onset;
172 candidate = !source_onset;
187template <std::
size_t MaxSteps = 64>
188[[nodiscard]]
constexpr RhythmRelationshipResult<MaxSteps>
192 if (source.empty()) {
196 if (config.target_steps == 0 || config.target_steps > MaxSteps) {
218 (void)result.
pattern.resize(config.target_steps);
219 std::size_t candidate_count = 0;
220 for (std::size_t step = 0; step < config.target_steps; ++step)
224 config.target_onsets > candidate_count) {
229 for (std::size_t step = 0; step < config.target_steps; ++step) {
233 (void)result.
pattern.set(step,
true);
238 std::size_t rank = 0;
239 for (std::size_t other = 0; other < config.target_steps; ++other) {
243 rank += other_priority < priority || (other_priority == priority && other < step);
245 if (rank < config.target_onsets)
246 (void)result.
pattern.set(step,
true);
Definition pattern.hpp:25
constexpr std::size_t multiply_divide_floor(std::size_t multiplicand, std::size_t multiplier, std::size_t divisor) noexcept
Definition rhythm_relationship.hpp:124
constexpr bool valid_relationship(RhythmRelationship value) noexcept
Definition rhythm_relationship.hpp:91
constexpr bool valid_collision_policy(RhythmCollisionPolicy value) noexcept
Definition rhythm_relationship.hpp:100
constexpr bool valid_density_policy(RhythmDensityPolicy value) noexcept
Definition rhythm_relationship.hpp:105
constexpr std::size_t delayed_step(std::size_t step, std::size_t length, std::int64_t phase_steps) noexcept
Definition rhythm_relationship.hpp:110
constexpr bool relationship_candidate(const BinaryPattern< MaxSteps > &source, const RhythmRelationshipConfig &config, std::size_t target_step) noexcept
Definition rhythm_relationship.hpp:161
constexpr bool valid_length_mapping(RhythmLengthMapping value) noexcept
Definition rhythm_relationship.hpp:96
constexpr std::uint64_t rhythm_mix(std::uint64_t value) noexcept
Definition rhythm_relationship.hpp:76
constexpr std::uint64_t rhythm_draw(RhythmDrawCoordinate coordinate, std::size_t target_step) noexcept
Definition rhythm_relationship.hpp:83
constexpr std::size_t mapped_source_step(const BinaryPattern< MaxSteps > &source, const RhythmRelationshipConfig &config, std::size_t target_step) noexcept
Definition rhythm_relationship.hpp:151
constexpr RhythmRelationshipResult< MaxSteps > derive_rhythm_relationship(const BinaryPattern< MaxSteps > &source, const RhythmRelationshipConfig &config) noexcept
Definition rhythm_relationship.hpp:189
RhythmDensityPolicy
Definition rhythm_relationship.hpp:28
@ exact_onsets
Definition rhythm_relationship.hpp:30
@ preserve_candidates
Definition rhythm_relationship.hpp:29
@ none
Definition markov.hpp:15
@ capacity_exceeded
Definition markov.hpp:17
RhythmRelationshipError
Definition rhythm_relationship.hpp:33
@ invalid_collision_policy
Definition rhythm_relationship.hpp:40
@ none
Definition rhythm_relationship.hpp:34
@ invalid_relationship
Definition rhythm_relationship.hpp:38
@ empty_source
Definition rhythm_relationship.hpp:35
@ insufficient_candidates
Definition rhythm_relationship.hpp:42
@ empty_target
Definition rhythm_relationship.hpp:36
@ invalid_length_mapping
Definition rhythm_relationship.hpp:39
@ capacity_exceeded
Definition rhythm_relationship.hpp:37
@ invalid_density_policy
Definition rhythm_relationship.hpp:41
@ wrap
Definition pattern.hpp:266
RhythmCollisionPolicy
Definition rhythm_relationship.hpp:23
@ avoid_source_overlap
Definition rhythm_relationship.hpp:25
@ allow_source_overlap
Definition rhythm_relationship.hpp:24
RhythmLengthMapping
Definition rhythm_relationship.hpp:18
@ proportional
Definition rhythm_relationship.hpp:20
@ wrap
Definition rhythm_relationship.hpp:19
RhythmRelationship
Definition rhythm_relationship.hpp:12
@ complementary
Definition rhythm_relationship.hpp:14
@ independent
Definition rhythm_relationship.hpp:15
@ coincident
Definition rhythm_relationship.hpp:13
Definition rhythm_relationship.hpp:45
std::uint32_t lane
Definition rhythm_relationship.hpp:48
std::int64_t cycle
Definition rhythm_relationship.hpp:47
std::uint64_t seed
Definition rhythm_relationship.hpp:46
constexpr auto operator<=>(const RhythmDrawCoordinate &) const =default
Definition rhythm_relationship.hpp:53
RhythmLengthMapping length_mapping
Definition rhythm_relationship.hpp:56
RhythmDrawCoordinate draw
Definition rhythm_relationship.hpp:61
std::size_t target_steps
Definition rhythm_relationship.hpp:54
RhythmDensityPolicy density
Definition rhythm_relationship.hpp:59
std::size_t target_onsets
Definition rhythm_relationship.hpp:60
std::int64_t phase_steps
Definition rhythm_relationship.hpp:57
RhythmRelationship relationship
Definition rhythm_relationship.hpp:55
RhythmCollisionPolicy collision
Definition rhythm_relationship.hpp:58
Definition rhythm_relationship.hpp:64
BinaryPattern< MaxSteps > pattern
Definition rhythm_relationship.hpp:65
RhythmRelationshipError error
Definition rhythm_relationship.hpp:66