Etterna 0.74.4
Loading...
Searching...
No Matches
WideRangeAnchor.h
1#pragma once
2#include "../IntervalHandInfo.h"
3#include "../HD_Sequencers/GenericSequencing.h"
4
8{
9 const CalcPatternMod _pmod = WideRangeAnchor;
10 const std::string name = "WideRangeAnchorMod";
11
12#pragma region params
13
14 float window_param = 2.F;
15
16 float min_mod = 1.F;
17 float max_mod = 1.1F;
18 float base = 1.F;
19
20 float diff_min = 4.F;
21 float diff_max = 16.F;
22 float scaler = 0.5F;
23
24 const std::vector<std::pair<std::string, float*>> _params{
25 { "window_param", &window_param },
26
27 { "min_mod", &min_mod },
28 { "max_mod", &max_mod },
29 { "base", &base },
30
31 { "diff_min", &diff_min },
32 { "diff_max", &diff_max },
33 { "scaler", &scaler },
34 };
35#pragma endregion params and param map
36
37 int window = 0;
38 int a = 0;
39 int b = 0;
40 int diff = 0;
41
42 // set in setup
43 float divisor = 0.F;
44 float pmod = min_mod;
45
46 void full_reset()
47 {
48 interval_end();
49 pmod = neutral;
50 }
51
52 void setup()
53 {
54 // setup should be run after loading params from disk
55 window =
56 std::clamp(static_cast<int>(window_param), 1, max_moving_window_size);
57 divisor = static_cast<float>(static_cast<int>(diff_max) -
58 static_cast<int>(diff_min));
59
60 // /0 lul
61 if (divisor < 0.1F)
62 divisor = 0.1F;
63 }
64
65 void set_pmod(const ItvHandInfo& itvhi, const AnchorSequencer& as)
66 {
67 a = as.get_max_for_window_and_col(col_left, window);
68 b = as.get_max_for_window_and_col(col_right, window);
69
70 diff = diff_high_by_low(a, b);
71
72 // nothing here
73 if (a == 0 && b == 0) {
74 pmod = neutral;
75 return;
76 }
77
78 // set max mod if either is 0
79 if (a == 0 || b == 0) {
80 pmod = max_mod;
81 return;
82 }
83
84 // difference won't matter
85 if (diff <= static_cast<int>(diff_min)) {
86 pmod = min_mod;
87 return;
88 }
89
90 // would max anyway
91 if (diff > static_cast<int>(diff_max)) {
92 pmod = max_mod;
93 return;
94 }
95
96 pmod =
97 base + (scaler * ((static_cast<float>(diff) - diff_min) / divisor));
98 pmod = std::clamp(pmod, min_mod, max_mod);
99 }
100
101 auto operator()(const ItvHandInfo& itvhi, const AnchorSequencer& as)
102 -> float
103 {
104 set_pmod(itvhi, as);
105
106 interval_end();
107 return pmod;
108 }
109
110 /* ok technically not necessary since we don't ever do anything before these
111 * values are updated, however, supposing we do add anything like shortcut
112 * case handling prior to calculating these values, better this is already
113 * in place */
114 void interval_end()
115 {
116 diff = 0;
117 a = 0;
118 b = 0;
119 }
120};
Definition GenericSequencing.h:308
accumulates hand specific info across an interval as it's processed by row
Definition IntervalHandInfo.h:6
Definition WideRangeAnchor.h:8