Vital
Loading...
Searching...
No Matches
slew_limit_modifier.cpp
Go to the documentation of this file.
1/*
2Summary:
3SlewLimitModifier applies slew-rate limiting to the wavetable’s time-domain signal, controlling how quickly the waveform can rise or fall per sample. By adjusting the upward and downward slew parameters, one can achieve smoother transitions and reduce harsh dynamics in the resulting sound. Interpolating between keyframes allows these constraints to evolve across the wavetable.
4 */
5
7
8#include "wave_frame.h"
9
11 // Initialize upward and downward slew limits to zero, meaning no slew limiting.
13 slew_up_run_rise_ = 0.0f;
14}
15
17 const SlewLimitModifierKeyframe* source = dynamic_cast<const SlewLimitModifierKeyframe*>(keyframe);
18 slew_down_run_rise_ = source->slew_down_run_rise_;
19 slew_up_run_rise_ = source->slew_up_run_rise_;
20}
21
23 const WavetableKeyframe* to_keyframe,
24 float t) {
25 // Linearly interpolate upward and downward slew limits.
26 const SlewLimitModifierKeyframe* from = dynamic_cast<const SlewLimitModifierKeyframe*>(from_keyframe);
27 const SlewLimitModifierKeyframe* to = dynamic_cast<const SlewLimitModifierKeyframe*>(to_keyframe);
28
29 slew_down_run_rise_ = linearTween(from->slew_down_run_rise_, to->slew_down_run_rise_, t);
30 slew_up_run_rise_ = linearTween(from->slew_up_run_rise_, to->slew_up_run_rise_, t);
31}
32
34 // Enforce slew limits in time domain by constraining how much the waveform can rise or fall per sample.
35 float min_slew_limit = 1.0f / vital::WaveFrame::kWaveformSize;
36 float max_up_delta = (2.0f / vital::WaveFrame::kWaveformSize) / std::max(slew_up_run_rise_, min_slew_limit);
37 float max_down_delta = (2.0f / vital::WaveFrame::kWaveformSize) / std::max(slew_down_run_rise_, min_slew_limit);
38
39 float current_value = wave_frame->time_domain[0];
40 // Iterate through the waveform's samples, limiting upward and downward changes.
41 for (int i = 1; i < 2 * vital::WaveFrame::kWaveformSize; ++i) {
42 int index = i % vital::WaveFrame::kWaveformSize;
43 float target_value = wave_frame->time_domain[index];
44 float delta = target_value - current_value;
45
46 if (delta > 0.0f)
47 current_value += std::min(delta, max_up_delta);
48 else
49 current_value -= std::min(-delta, max_down_delta);
50
51 wave_frame->time_domain[index] = current_value;
52 }
53 wave_frame->toFrequencyDomain();
54}
55
58 data["up_run_rise"] = slew_up_run_rise_;
59 data["down_run_rise"] = slew_down_run_rise_;
60 return data;
61}
62
65 slew_up_run_rise_ = data["up_run_rise"];
66 slew_down_run_rise_ = data["down_run_rise"];
67}
68
71 interpolate(keyframe, position);
72 return keyframe;
73}
74
75void SlewLimitModifier::render(vital::WaveFrame* wave_frame, float position) {
76 // Interpolate parameters for the given position and apply slew limiting.
77 interpolate(&compute_frame_, position);
78 compute_frame_.render(wave_frame);
79}
80
84
86 WavetableKeyframe* wavetable_keyframe = keyframes_[index].get();
87 return dynamic_cast<SlewLimitModifier::SlewLimitModifierKeyframe*>(wavetable_keyframe);
88}
A keyframe class holding parameters for slew-rate limits at a given position.
Definition slew_limit_modifier.h:27
void interpolate(const WavetableKeyframe *from_keyframe, const WavetableKeyframe *to_keyframe, float t) override
Linearly interpolates between two keyframes.
Definition slew_limit_modifier.cpp:22
SlewLimitModifierKeyframe()
Constructs a keyframe with default slew limit values.
Definition slew_limit_modifier.cpp:10
void jsonToState(json data) override
Restores the keyframe's state from a JSON object.
Definition slew_limit_modifier.cpp:63
json stateToJson() override
Serializes the state of this keyframe to a JSON object.
Definition slew_limit_modifier.cpp:56
void render(vital::WaveFrame *wave_frame) override
Renders the waveform of this keyframe into a WaveFrame.
Definition slew_limit_modifier.cpp:33
void copy(const WavetableKeyframe *keyframe) override
Copies the state from another keyframe of the same type.
Definition slew_limit_modifier.cpp:16
float slew_down_run_rise_
Parameter controlling downward slew rate.
Definition slew_limit_modifier.h:76
float slew_up_run_rise_
Parameter controlling upward slew rate.
Definition slew_limit_modifier.h:75
SlewLimitModifierKeyframe * getKeyframe(int index)
Retrieves a SlewLimitModifierKeyframe by index.
Definition slew_limit_modifier.cpp:85
SlewLimitModifierKeyframe compute_frame_
A keyframe used for intermediate computations.
Definition slew_limit_modifier.h:102
WavetableComponentFactory::ComponentType getType() override
Returns the type of this WavetableComponent.
Definition slew_limit_modifier.cpp:81
WavetableKeyframe * createKeyframe(int position) override
Creates a new keyframe at a given position.
Definition slew_limit_modifier.cpp:69
void render(vital::WaveFrame *wave_frame, float position) override
Renders the waveform at a given position into a WaveFrame.
Definition slew_limit_modifier.cpp:75
ComponentType
Enumerates all known WavetableComponents, including sources and modifiers.
Definition wavetable_component_factory.h:28
@ kSlewLimiter
Modifier that limits slew rate.
Definition wavetable_component_factory.h:39
void interpolate(WavetableKeyframe *dest, float position)
Interpolates a destination keyframe at a given position.
Definition wavetable_component.cpp:68
std::vector< std::unique_ptr< WavetableKeyframe > > keyframes_
The list of keyframes sorted by position.
Definition wavetable_component.h:219
Represents a single state of a waveform at a specific position in a wavetable.
Definition wavetable_keyframe.h:35
virtual json stateToJson()
Serializes the state of this keyframe to a JSON object.
Definition wavetable_keyframe.cpp:37
virtual void jsonToState(json data)
Restores the keyframe's state from a JSON object.
Definition wavetable_keyframe.cpp:41
Represents a single frame of a wavetable, containing both time-domain and frequency-domain data.
Definition wave_frame.h:16
void toFrequencyDomain()
Converts the currently loaded time-domain data into frequency-domain representation.
Definition wave_frame.cpp:64
static constexpr int kWaveformSize
The size of the waveform (number of samples per frame).
Definition wave_frame.h:21
mono_float time_domain[2 *kWaveformSize]
The time-domain data, extended buffer size for FFT alignment.
Definition wave_frame.h:124
nlohmann::json json
Definition line_generator.h:7