2#include "../../CalcWindow.h"
18constexpr float anchor_spacing_buffer_ms = 10.F;
19constexpr float anchor_speed_increase_cutoff_factor = 2.34F;
20static const int anchor_len_cap = 50;
23constexpr float jack_spacing_buffer_ms = 10.F;
24constexpr float jack_speed_increase_cutoff_factor = 1.9F;
25static const int jack_len_cap = 4;
29constexpr float guaranteed_reset_buffer_ms = 1000.F;
47 col_type _ct = col_init;
48 anch_status _status = anch_init;
77 float _start = s_init;
79 inline virtual void full_reset()
127 inline virtual void operator()(
const col_type ct,
const float& now) = 0;
140 _status = reset_too_slow;
141 }
else if (
_sc_ms * jack_speed_increase_cutoff_factor <
_max_ms) {
142 _status = reset_too_fast;
148 inline void operator()(
const col_type ct,
const float& now)
override
153 if (ct == col_init) {
172 if (
_len > jack_len_cap) {
176 static const auto avg_ms_mult = 1.5F;
177 static const auto anchor_time_buffer_ms = 30.F;
178 static const auto min_ms = 95.F;
181 const auto total_ms = ms_from(
_last, _start);
184 const auto len =
static_cast<float>(
_len - 1);
187 const auto avg_ms = total_ms / len;
191 const auto adj_total_ms =
192 total_ms + anchor_time_buffer_ms + avg_ms * avg_ms_mult;
195 auto ms = adj_total_ms / len;
200 ms = ms < 180.F ? 180.F : ms;
203 ms = ms < min_ms ? min_ms : ms;
208 if (
_len == jack_len_cap) {
228 _status = reset_too_slow;
229 }
else if (
_sc_ms * anchor_speed_increase_cutoff_factor <
_max_ms) {
230 _status = reset_too_fast;
236 inline void operator()(
const col_type ct,
const float& now)
override
241 if (ct == col_init) {
261 if (
_len > anchor_len_cap) {
265 static const auto avg_ms_mult = 1.F;
266 static const auto anchor_time_buffer_ms = 0.F;
267 static const auto min_ms = 0.F;
270 const auto total_ms = ms_from(
_last, _start);
273 const auto len =
static_cast<float>(
_len - 1);
276 const auto avg_ms = total_ms / len;
280 const auto adj_total_ms =
281 total_ms + anchor_time_buffer_ms + avg_ms * avg_ms_mult;
284 auto ms = adj_total_ms / len;
289 ms = ms < 155.F ? 155.F : ms;
292 ms = ms < min_ms ? min_ms : ms;
297 if (
_len == anchor_len_cap) {
310 std::array<std::unique_ptr<Anchor_Sequencing>, num_cols_per_hand>
anch;
312 std::array<std::unique_ptr<Jack_Sequencing>, num_cols_per_hand>
jack;
315 std::array<int, num_cols_per_hand>
max_seen = { 0, 0 };
317 std::array<CalcMovingWindow<int>, num_cols_per_hand>
_mw_max;
321 for (
const auto& c : ct_loop_no_jumps) {
334 for (
const auto& c : ct_loop_no_jumps) {
335 anch.at(c)->full_reset();
336 jack.at(c)->full_reset();
342 void operator()(
const col_type ct,
const float& row_time)
345 if (ct == col_left || ct == col_right) {
346 auto opposite_col = ct == col_left ? col_right : col_left;
347 (*
anch.at(ct))(ct, row_time);
348 (*
jack.at(ct))(ct, row_time);
358 if (ms_from(row_time,
anch.at(opposite_col)->_last) >
359 guaranteed_reset_buffer_ms) {
360 anch.at(opposite_col)->full_reset();
361 jack.at(opposite_col)->full_reset();
363 }
else if (ct == col_ohjump) {
366 for (
const auto& c : ct_loop_no_jumps) {
367 (*
anch.at(c))(c, row_time);
368 (*
jack.at(c))(c, row_time);
379 [[nodiscard]]
auto get_max_for_window_and_col(
const col_type& ct,
380 const int& window)
const
383 assert(ct < num_cols_per_hand);
384 return _mw_max.at(ct).get_max_for_window(window);
389 for (
const auto& c : ct_loop_no_jumps) {
395 auto get_lowest_anchor_ms() ->
float
397 return std::min(
anch.at(col_left)->get_ms(),
398 anch.at(col_right)->get_ms());
401 auto get_lowest_jack_ms() ->
float
403 return std::min(
jack.at(col_left)->get_ms(),
404 jack.at(col_right)->get_ms());
435 std::array<CalcMovingWindow<float>, num_cols_per_hand>
_mw_sc_ms;
446 if (ct == col_left || ct == col_right) {
453 if (ct == col_ohjump) {
454 for (
const auto& c : ct_loop_no_jumps) {
464 void set_cc_ms(
const col_type& ct,
const float& row_time)
467 if (ct == col_left || ct == col_right) {
481 if (ct == col_ohjump) {
487 void advance_sequencing(
const col_type& ct,
488 const float& row_time,
491 if (ct != col_ohjump) {
492 auto reset_sequencer = ms_from(row_time,
_as.
anch.at(ct)->_last) >
493 guaranteed_reset_buffer_ms;
494 if (reset_sequencer) {
511 set_cc_ms(ct, row_time);
515 [[nodiscard]]
auto get_sc_ms_now(
const col_type& ct,
516 const bool lower =
true) const ->
float
518 if (ct == col_init) {
523 if (ct == col_ohjump) {
542 auto get_mw_sc_ms(
const col_type& ct)
544 if (ct == col_left || ct == col_ohjump) {
550 [[nodiscard]]
auto get_any_ms_now() const ->
float
554 [[nodiscard]]
auto get_cc_ms_now() const ->
float
559 void interval_end() {
_as.interval_end(); }
566 for (
const auto& c : ct_loop_no_jumps) {
Definition GenericSequencing.h:308
std::array< std::unique_ptr< Anchor_Sequencing >, num_cols_per_hand > anch
anchor sequencers for each finger
Definition GenericSequencing.h:310
std::array< int, num_cols_per_hand > max_seen
information for each column to store in the movingwindow_max, this interval
Definition GenericSequencing.h:315
std::array< std::unique_ptr< Jack_Sequencing >, num_cols_per_hand > jack
jack sequencers for each finger
Definition GenericSequencing.h:312
std::array< CalcMovingWindow< int >, num_cols_per_hand > _mw_max
track windows of highest anchor per col seen during an interval
Definition GenericSequencing.h:317
Definition GenericSequencing.h:224
void operator()(const col_type ct, const float &now) override
sequence updating given the column type and time of current row
Definition GenericSequencing.h:236
float get_ms() override
Definition GenericSequencing.h:255
void set_status() override
Definition GenericSequencing.h:225
Definition CalcWindow.h:15
auto get_now() const -> T
get most recent value in moving window
Definition CalcWindow.h:38
Individual anchors, 2 objects per hand on 4k.
Definition GenericSequencing.h:45
virtual float get_ms()=0
returns an adjusted MS average value, not converted to nps
float _len_cap_ms
Definition GenericSequencing.h:73
virtual void set_status()=0
int _len
Definition GenericSequencing.h:63
virtual void check_status()
based on the anchoring status, do an action
Definition GenericSequencing.h:92
virtual void operator()(const col_type ct, const float &now)=0
sequence updating given the column type and time of current row
float _last
row_time of last note on this col
Definition GenericSequencing.h:76
float _sc_ms
same-column ms: time between now and previous tap
Definition GenericSequencing.h:65
float _max_ms
Definition GenericSequencing.h:69
Individual jacks, rather than anchors, with more nuance.
Definition GenericSequencing.h:136
void set_status() override
Definition GenericSequencing.h:137
void operator()(const col_type ct, const float &now) override
sequence updating given the column type and time of current row
Definition GenericSequencing.h:148
float get_ms() override
returns an adjusted MS average value, not converted to nps
Definition GenericSequencing.h:166
Definition GenericSequencing.h:422
AnchorSequencer _as
Definition GenericSequencing.h:438
void set_sc_ms(const col_type &ct)
Definition GenericSequencing.h:443
std::array< CalcMovingWindow< float >, num_cols_per_hand > _mw_sc_ms
Definition GenericSequencing.h:435
CalcMovingWindow< float > _mw_cc_ms
moving window of cc_ms values
Definition GenericSequencing.h:431
CalcMovingWindow< float > _mw_any_ms
Definition GenericSequencing.h:428