diff --git a/include/dsp.hpp b/include/dsp.hpp index 19b638f4..d0f1e842 100644 --- a/include/dsp.hpp +++ b/include/dsp.hpp @@ -9,6 +9,7 @@ #include "dsp/decimator.hpp" #include "dsp/filter.hpp" #include "dsp/minblep.hpp" +#include "dsp/digital.hpp" #include diff --git a/include/dsp/digital.hpp b/include/dsp/digital.hpp new file mode 100644 index 00000000..67b729d9 --- /dev/null +++ b/include/dsp/digital.hpp @@ -0,0 +1,68 @@ +#pragma once + +#include "math.hpp" + + +namespace rack { + + +/** Turns high when value reaches the high threshold, turns low when value reaches the low threshold */ +struct SchmittTrigger { + // UNKNOWN is used to represent a stable state when the previous state is not yet set + enum {UNKNOWN, LOW, HIGH} state = UNKNOWN; + float low = 0.0; + float high = 1.0; + void setThresholds(float low, float high) { + this->low = low; + this->high = high; + } + /** Returns true if triggered */ + bool process(float in) { + switch (state) { + case LOW: + if (in >= high) { + state = HIGH; + return true; + } + break; + case HIGH: + if (in <= low) { + state = LOW; + } + break; + default: + if (in >= high) { + state = HIGH; + } + else if (in <= low) { + state = LOW; + } + break; + } + return false; + } + void reset() { + state = UNKNOWN; + } +}; + + +/** When triggered, holds a high value for a specified time before going low again */ +struct PulseGenerator { + float time = 0.0; + float pulseTime = 0.0; + bool process(float deltaTime) { + time += deltaTime; + return time < pulseTime; + } + void trigger(float pulseTime) { + // Keep the previous pulseTime if the existing pulse would be held longer than the currently requested one. + if (time + pulseTime >= this->pulseTime) { + time = 0.0; + this->pulseTime = pulseTime; + } + } +}; + + +} // namespace rack diff --git a/include/dsp/filter.hpp b/include/dsp/filter.hpp index ac97fefb..35098ecf 100644 --- a/include/dsp/filter.hpp +++ b/include/dsp/filter.hpp @@ -59,31 +59,4 @@ struct SlewLimiter { }; -struct SchmittTrigger { - /** 0 unknown, 1 low, 2 high */ - int state = 0; - float low = 0.0; - float high = 1.0; - void setThresholds(float low, float high) { - this->low = low; - this->high = high; - } - /** Returns true if triggered */ - bool process(float in) { - bool triggered = false; - if (in >= high) { - if (state == 1) - triggered = true; - state = 2; - } - else if (in <= low) { - state = 1; - } - return triggered; - } - void reset() { - state = 0; - } -}; - } // namespace rack