chore: land janitor round 1 and graft integration
Round 1 findings and fixes, all previously uncommitted: - FXProcessor per-slot DSP history repair (HEAD does not compile without it) - SynthVoice::getModulationValue, editor control-lock guard - ExactCompare.h naming the deliberate exact float comparisons - KnobLookAndFeel replacing the never-installed SerumLookAndFeel - 55 first-party compiler warnings to 0 - AGENT.md renamed to AGENTS.md across Source/ - graft repository context graph and its hooks - JANITOR_TASKS.md and UI_UX_AUDIT.md records
This commit is contained in:
1 parent
5c942cad0c
commit
e4cea300db
63 files changed
+2360
-805
No files matched your search
+29
-16
@@ -1,4 +1,5 @@
|
||||
#include "LFO.h"
|
||||
#include "ExactCompare.h"
|
||||
|
||||
namespace serum
|
||||
{
|
||||
@@ -40,7 +41,7 @@ void LFO::setParams (float rateNorm, bool s, float b, int shp, float ph,
|
||||
|
||||
// Only restart the delay/fade timing when those knobs actually change,
|
||||
// so repeated block-rate setParams calls don't keep resetting the LFO.
|
||||
if (delay != prevDelayParam || fade != prevFadeParam)
|
||||
if (changed (delay, prevDelayParam) || changed (fade, prevFadeParam))
|
||||
{
|
||||
delayCounter = delaySeconds * sr;
|
||||
fadeCounter = 0.0;
|
||||
@@ -62,39 +63,51 @@ void LFO::setShapeData (const std::vector<float>& data, int steps)
|
||||
? juce::jlimit (-1.0f, 1.0f, data[i]) : 0.0f;
|
||||
}
|
||||
|
||||
float LFO::shapeValue() noexcept
|
||||
float lfoShapeValue (float phase, LfoShape shape, int steps,
|
||||
const float* data, int dataSize, float sampleHoldValue) noexcept
|
||||
{
|
||||
const float p = getPhase();
|
||||
switch ((LfoShape) shape)
|
||||
const int numSteps = juce::jlimit (2, LFO::kShapePoints, steps);
|
||||
const int numData = data != nullptr ? juce::jlimit (0, LFO::kShapePoints, dataSize) : 0;
|
||||
|
||||
auto point = [data, numData] (int index) noexcept
|
||||
{
|
||||
return numData > 0 ? data[(size_t) juce::jlimit (0, numData - 1, index)] : 0.0f;
|
||||
};
|
||||
|
||||
switch (shape)
|
||||
{
|
||||
case LfoShape::Sine:
|
||||
return std::sin (p * juce::MathConstants<float>::twoPi);
|
||||
return std::sin (phase * juce::MathConstants<float>::twoPi);
|
||||
case LfoShape::Triangle:
|
||||
return 1.0f - 4.0f * std::abs (p - 0.5f);
|
||||
return 1.0f - 4.0f * std::abs (phase - 0.5f);
|
||||
case LfoShape::Saw:
|
||||
return 2.0f * p - 1.0f;
|
||||
return 2.0f * phase - 1.0f;
|
||||
case LfoShape::Square:
|
||||
return (p < 0.5f) ? 1.0f : -1.0f;
|
||||
return (phase < 0.5f) ? 1.0f : -1.0f;
|
||||
case LfoShape::SampleHold:
|
||||
return holdValue;
|
||||
return sampleHoldValue;
|
||||
case LfoShape::StepSeq:
|
||||
{
|
||||
const int idx = juce::jlimit (0, shapeSteps - 1, (int) (p * shapeSteps));
|
||||
return shapeBuffer[(size_t) idx];
|
||||
}
|
||||
return point (juce::jlimit (0, numSteps - 1, (int) (phase * (float) numSteps)));
|
||||
case LfoShape::Freehand:
|
||||
{
|
||||
const float pos = p * (float) (shapeSteps - 1);
|
||||
const float pos = phase * (float) (numSteps - 1);
|
||||
const int i0 = (int) pos;
|
||||
const int i1 = juce::jmin (i0 + 1, shapeSteps - 1);
|
||||
const int i1 = juce::jmin (i0 + 1, numSteps - 1);
|
||||
const float frac = pos - (float) i0;
|
||||
return shapeBuffer[(size_t) i0] * (1.0f - frac) + shapeBuffer[(size_t) i1] * frac;
|
||||
return point (i0) * (1.0f - frac) + point (i1) * frac;
|
||||
}
|
||||
case LfoShape::Count:
|
||||
default:
|
||||
return 0.0f;
|
||||
}
|
||||
}
|
||||
|
||||
float LFO::shapeValue() noexcept
|
||||
{
|
||||
return lfoShapeValue (getPhase(), (LfoShape) shape, shapeSteps,
|
||||
shapeBuffer.data(), (int) shapeBuffer.size(), holdValue);
|
||||
}
|
||||
|
||||
float LFO::process() noexcept
|
||||
{
|
||||
return advance (1);
|
||||
|
||||
Reference in new issue
Block a user