46 void set_note(
float midi_note,
float sample_rate = 48000.0f) {
48 sample_rate_ = sample_rate;
49 recompute_frequencies();
59 note_ = 69.0f + 12.0f * log2f(freq_hz / 440.0f);
69 detune_cents_ = cents;
78 if (spread == stereo_spread_)
return;
79 stereo_spread_ = spread;
93 float per_osc = amp / 3.0f;
110 uint16_t n = (frames > MAX_BLOCK) ? MAX_BLOCK : frames;
112 float fbuf[MAX_BLOCK];
113 float fleft[MAX_BLOCK] = {};
114 float fright[MAX_BLOCK] = {};
129 for (uint16_t i = 0; i < n; ++i) {
131 right[i] += fright[i];
144 uint16_t n = (frames > MAX_BLOCK) ? MAX_BLOCK : frames;
148 float buf[MAX_BLOCK];
150 for (uint16_t i = 0; i < n; ++i) out[i] += buf[i];
153 for (uint16_t i = 0; i < n; ++i) out[i] += buf[i];
167 float detune()
const {
return detune_cents_; }
173 static constexpr uint16_t MAX_BLOCK = 48;
180 float sample_rate_ = 48000.0f;
181 float detune_cents_ = 0.0f;
182 float stereo_spread_ = 0.0f;
183 float amplitude_ = 1.0f;
190 void recompute_frequencies() {
191 center_.
set_note(note_, sample_rate_);
195 void recompute_detuned() {
196 float offset = detune_cents_ / 100.0f;
197 left_.
set_note(note_ - offset, sample_rate_);
198 right_.
set_note(note_ + offset, sample_rate_);
201 void recompute_pan() {
202 float half = stereo_spread_ * 0.5f;
PanGain constant_power(float position)
Compute constant-power pan gains (-3 dB at center)
void pan_mix(const float *mono, float *left, float *right, PanGain gain, uint16_t frames)
Apply pan gains to a mono buffer and accumulate into stereo buffers.