74 currentParameters = newParameters;
76 sustainLevel = newParameters.
sustain;
77 calculateRates (newParameters);
79 if (currentState != State::idle)
90 bool isActive() const noexcept {
return currentState != State::idle; }
99 jassert (sampleRate > 0.0);
108 currentState = State::idle;
114 if (attackRate > 0.0f) currentState = State::attack;
115 else if (decayRate > 0.0f) currentState = State::decay;
116 else currentState = State::sustain;
122 if (currentState != State::idle)
124 if (releaseRate > 0.0f)
126 if (currentState != State::sustain)
127 releaseRate =
static_cast<float> (envelopeVal / (currentParameters.
release * sr));
129 currentState = State::release;
145 if (currentState == State::idle)
148 if (currentState == State::attack)
150 envelopeVal += attackRate;
152 if (envelopeVal >= 1.0f)
156 if (decayRate > 0.0f)
157 currentState = State::decay;
159 currentState = State::sustain;
162 else if (currentState == State::decay)
164 envelopeVal -= decayRate;
166 if (envelopeVal <= sustainLevel)
168 envelopeVal = sustainLevel;
169 currentState = State::sustain;
172 else if (currentState == State::sustain)
174 envelopeVal = sustainLevel;
176 else if (currentState == State::release)
178 envelopeVal -= releaseRate;
180 if (envelopeVal <= 0.0f)
192 template<
typename FloatType>
195 jassert (startSample + numSamples <= buffer.
getNumSamples());
199 while (--numSamples >= 0)
203 for (
int i = 0; i < numChannels; ++i)
212 void calculateRates (
const Parameters& parameters)
217 attackRate = (parameters.attack > 0.0f ?
static_cast<float> (1.0f / (parameters.attack * sr)) : -1.0f);
218 decayRate = (parameters.decay > 0.0f ?
static_cast<float> ((1.0f - sustainLevel) / (parameters.decay * sr)) : -1.0f);
219 releaseRate = (parameters.release > 0.0f ?
static_cast<float> (sustainLevel / (parameters.release * sr)) : -1.0f);
222 void checkCurrentState()
224 if (currentState == State::attack && attackRate <= 0.0f) currentState = decayRate > 0.0f ? State::decay : State::sustain;
225 else if (currentState == State::decay && decayRate <= 0.0f) currentState = State::sustain;
226 else if (currentState == State::release && releaseRate <= 0.0f)
reset();
230 enum class State { idle, attack, decay, sustain, release };
232 State currentState = State::idle;
233 Parameters currentParameters;
237 float envelopeVal = 0.0f;
239 float sustainLevel = 0.0f;
240 float attackRate = 0.0f, decayRate = 0.0f, releaseRate = 0.0f;