diff options
author | William McPherson <willmcpherson2@gmail.com> | 2020-02-05 01:36:30 +1100 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2020-02-05 17:52:10 +0100 |
commit | 421a34057296fd268a58c9733dca91c96d39219a (patch) | |
tree | db3099c627f896f20c0a0301ade2c4547cd2e83b /Applications | |
parent | 44c81ee9db453c824ed98f697bd67d661b4ee636 (diff) | |
download | serenity-421a34057296fd268a58c9733dca91c96d39219a.zip |
Piano: Make decay more accurate
1. Make decay sample-granular rather than buffer-granular
You only have ~43 buffers per second which can make a jagged signal.
2. Calculate decay in milliseconds
Decay is supposed to be a time value.
Diffstat (limited to 'Applications')
-rw-r--r-- | Applications/Piano/AudioEngine.cpp | 28 | ||||
-rw-r--r-- | Applications/Piano/AudioEngine.h | 3 | ||||
-rw-r--r-- | Applications/Piano/KnobsWidget.cpp | 2 |
3 files changed, 21 insertions, 12 deletions
diff --git a/Applications/Piano/AudioEngine.cpp b/Applications/Piano/AudioEngine.cpp index 15fe0ac609..3378ebaf07 100644 --- a/Applications/Piano/AudioEngine.cpp +++ b/Applications/Piano/AudioEngine.cpp @@ -31,6 +31,7 @@ AudioEngine::AudioEngine() { + set_decay(0); } AudioEngine::~AudioEngine() @@ -45,6 +46,11 @@ void AudioEngine::fill_buffer(FixedArray<Sample>& buffer) for (size_t note = 0; note < note_count; ++note) { if (!m_note_on[note]) continue; + + m_power[note] -= m_decay_step; + if (m_power[note] < 0) + m_power[note] = 0; + double val = 0; switch (m_wave) { case Wave::Sine: @@ -70,16 +76,6 @@ void AudioEngine::fill_buffer(FixedArray<Sample>& buffer) buffer[i].right = buffer[i].left; } - if (m_decay) { - for (size_t note = 0; note < note_count; ++note) { - if (m_note_on[note]) { - m_power[note] -= m_decay / 100.0; - if (m_power[note] < 0) - m_power[note] = 0; - } - } - } - if (m_delay) { if (m_delay_buffers.size() >= m_delay) { auto to_blend = m_delay_buffers.dequeue(); @@ -201,10 +197,22 @@ void AudioEngine::set_wave(Direction direction) } } +static inline double calculate_step(double distance, int milliseconds) +{ + if (milliseconds == 0) + return distance; + + constexpr double samples_per_millisecond = sample_rate / 1000.0; + double samples = milliseconds * samples_per_millisecond; + double step = distance / samples; + return step; +} + void AudioEngine::set_decay(int decay) { ASSERT(decay >= 0); m_decay = decay; + m_decay_step = calculate_step(1, m_decay); } void AudioEngine::set_delay(int delay) diff --git a/Applications/Piano/AudioEngine.h b/Applications/Piano/AudioEngine.h index 14280a716f..4f5bdc1585 100644 --- a/Applications/Piano/AudioEngine.h +++ b/Applications/Piano/AudioEngine.h @@ -77,7 +77,8 @@ private: int m_octave { 4 }; int m_wave { first_wave }; - int m_decay { 0 }; + int m_decay; + double m_decay_step; int m_delay { 0 }; int m_time { 0 }; diff --git a/Applications/Piano/KnobsWidget.cpp b/Applications/Piano/KnobsWidget.cpp index 4ec786ebad..caa9c40cec 100644 --- a/Applications/Piano/KnobsWidget.cpp +++ b/Applications/Piano/KnobsWidget.cpp @@ -91,7 +91,7 @@ KnobsWidget::KnobsWidget(GUI::Widget* parent, AudioEngine& audio_engine, MainWid m_wave_value->set_text(wave_strings[new_wave]); }; - constexpr int max_decay = 20; + constexpr int max_decay = 1000; m_decay_knob = GUI::Slider::construct(Orientation::Vertical, m_knobs_container); m_decay_knob->set_range(0, max_decay); m_decay_knob->set_value(max_decay - m_audio_engine.decay()); |