latest math.hpp APItags/v0.6.0
@@ -20,13 +20,13 @@ struct _8vert : Module { | |||||
}; | }; | ||||
void _8vert::step() { | void _8vert::step() { | ||||
float lastIn = 10.0; | |||||
float lastIn = 10.0f; | |||||
for (int i = 0; i < 8; i++) { | for (int i = 0; i < 8; i++) { | ||||
lastIn = inputs[i].normalize(lastIn); | lastIn = inputs[i].normalize(lastIn); | ||||
float out = lastIn * params[i].value; | float out = lastIn * params[i].value; | ||||
outputs[i].value = out; | outputs[i].value = out; | ||||
lights[2*i + 0].setBrightnessSmooth(fmaxf(0.0, out / 5.0)); | |||||
lights[2*i + 1].setBrightnessSmooth(fmaxf(0.0, -out / 5.0)); | |||||
lights[2*i + 0].setBrightnessSmooth(fmaxf(0.0f, out / 5.0f)); | |||||
lights[2*i + 1].setBrightnessSmooth(fmaxf(0.0f, -out / 5.0f)); | |||||
} | } | ||||
} | } | ||||
@@ -42,14 +42,14 @@ _8vertWidget::_8vertWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x - 30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x - 30, 365))); | ||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 47.753), module, 0, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 86.198), module, 1, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 124.639), module, 2, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 163.084), module, 3, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 201.529), module, 4, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 239.974), module, 5, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 278.415), module, 6, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 316.86), module, 7, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 47.753), module, 0, -1.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 86.198), module, 1, -1.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 124.639), module, 2, -1.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 163.084), module, 3, -1.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 201.529), module, 4, -1.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 239.974), module, 5, -1.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 278.415), module, 6, -1.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(45.308, 316.86), module, 7, -1.0f, 1.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(Vec(9.507, 50.397), module, 0)); | addInput(createInput<PJ301MPort>(Vec(9.507, 50.397), module, 0)); | ||||
addInput(createInput<PJ301MPort>(Vec(9.507, 88.842), module, 1)); | addInput(createInput<PJ301MPort>(Vec(9.507, 88.842), module, 1)); | ||||
@@ -32,29 +32,29 @@ struct ADSR : Module { | |||||
}; | }; | ||||
bool decaying = false; | bool decaying = false; | ||||
float env = 0.0; | |||||
float env = 0.0f; | |||||
SchmittTrigger trigger; | SchmittTrigger trigger; | ||||
ADSR() : Module(NUM_PARAMS, NUM_INPUTS, NUM_OUTPUTS, NUM_LIGHTS) { | ADSR() : Module(NUM_PARAMS, NUM_INPUTS, NUM_OUTPUTS, NUM_LIGHTS) { | ||||
trigger.setThresholds(0.0, 1.0); | |||||
trigger.setThresholds(0.0f, 1.0f); | |||||
} | } | ||||
void step() override; | void step() override; | ||||
}; | }; | ||||
void ADSR::step() { | void ADSR::step() { | ||||
float attack = clampf(params[ATTACK_INPUT].value + inputs[ATTACK_INPUT].value / 10.0, 0.0, 1.0); | |||||
float decay = clampf(params[DECAY_PARAM].value + inputs[DECAY_INPUT].value / 10.0, 0.0, 1.0); | |||||
float sustain = clampf(params[SUSTAIN_PARAM].value + inputs[SUSTAIN_INPUT].value / 10.0, 0.0, 1.0); | |||||
float release = clampf(params[RELEASE_PARAM].value + inputs[RELEASE_PARAM].value / 10.0, 0.0, 1.0); | |||||
float attack = clamp(params[ATTACK_INPUT].value + inputs[ATTACK_INPUT].value / 10.0f, 0.0f, 1.0f); | |||||
float decay = clamp(params[DECAY_PARAM].value + inputs[DECAY_INPUT].value / 10.0f, 0.0f, 1.0f); | |||||
float sustain = clamp(params[SUSTAIN_PARAM].value + inputs[SUSTAIN_INPUT].value / 10.0f, 0.0f, 1.0f); | |||||
float release = clamp(params[RELEASE_PARAM].value + inputs[RELEASE_PARAM].value / 10.0f, 0.0f, 1.0f); | |||||
// Gate and trigger | // Gate and trigger | ||||
bool gated = inputs[GATE_INPUT].value >= 1.0; | |||||
bool gated = inputs[GATE_INPUT].value >= 1.0f; | |||||
if (trigger.process(inputs[TRIG_INPUT].value)) | if (trigger.process(inputs[TRIG_INPUT].value)) | ||||
decaying = false; | decaying = false; | ||||
const float base = 20000.0; | |||||
const float maxTime = 10.0; | |||||
const float base = 20000.0f; | |||||
const float maxTime = 10.0f; | |||||
if (gated) { | if (gated) { | ||||
if (decaying) { | if (decaying) { | ||||
// Decay | // Decay | ||||
@@ -62,20 +62,20 @@ void ADSR::step() { | |||||
env = sustain; | env = sustain; | ||||
} | } | ||||
else { | else { | ||||
env += powf(base, 1 - decay) / maxTime * (sustain - env) / engineGetSampleRate(); | |||||
env += powf(base, 1 - decay) / maxTime * (sustain - env) * engineGetSampleTime(); | |||||
} | } | ||||
} | } | ||||
else { | else { | ||||
// Attack | // Attack | ||||
// Skip ahead if attack is all the way down (infinitely fast) | // Skip ahead if attack is all the way down (infinitely fast) | ||||
if (attack < 1e-4) { | if (attack < 1e-4) { | ||||
env = 1.0; | |||||
env = 1.0f; | |||||
} | } | ||||
else { | else { | ||||
env += powf(base, 1 - attack) / maxTime * (1.01 - env) / engineGetSampleRate(); | |||||
env += powf(base, 1 - attack) / maxTime * (1.01f - env) * engineGetSampleTime(); | |||||
} | } | ||||
if (env >= 1.0) { | |||||
env = 1.0; | |||||
if (env >= 1.0f) { | |||||
env = 1.0f; | |||||
decaying = true; | decaying = true; | ||||
} | } | ||||
} | } | ||||
@@ -83,24 +83,24 @@ void ADSR::step() { | |||||
else { | else { | ||||
// Release | // Release | ||||
if (release < 1e-4) { | if (release < 1e-4) { | ||||
env = 0.0; | |||||
env = 0.0f; | |||||
} | } | ||||
else { | else { | ||||
env += powf(base, 1 - release) / maxTime * (0.0 - env) / engineGetSampleRate(); | |||||
env += powf(base, 1 - release) / maxTime * (0.0f - env) * engineGetSampleTime(); | |||||
} | } | ||||
decaying = false; | decaying = false; | ||||
} | } | ||||
bool sustaining = nearf(env, sustain, 1e-3); | |||||
bool resting = nearf(env, 0.0, 1e-3); | |||||
bool sustaining = near(env, sustain, 1e-3); | |||||
bool resting = near(env, 0.0f, 1e-3); | |||||
outputs[ENVELOPE_OUTPUT].value = 10.0 * env; | |||||
outputs[ENVELOPE_OUTPUT].value = 10.0f * env; | |||||
// Lights | // Lights | ||||
lights[ATTACK_LIGHT].value = (gated && !decaying) ? 1.0 : 0.0; | |||||
lights[DECAY_LIGHT].value = (gated && decaying && !sustaining) ? 1.0 : 0.0; | |||||
lights[SUSTAIN_LIGHT].value = (gated && decaying && sustaining) ? 1.0 : 0.0; | |||||
lights[RELEASE_LIGHT].value = (!gated && !resting) ? 1.0 : 0.0; | |||||
lights[ATTACK_LIGHT].value = (gated && !decaying) ? 1.0f : 0.0f; | |||||
lights[DECAY_LIGHT].value = (gated && decaying && !sustaining) ? 1.0f : 0.0f; | |||||
lights[SUSTAIN_LIGHT].value = (gated && decaying && sustaining) ? 1.0f : 0.0f; | |||||
lights[RELEASE_LIGHT].value = (!gated && !resting) ? 1.0f : 0.0f; | |||||
} | } | ||||
@@ -121,10 +121,10 @@ ADSRWidget::ADSRWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<RoundBlackKnob>(Vec(62, 57), module, ADSR::ATTACK_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(62, 124), module, ADSR::DECAY_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(62, 191), module, ADSR::SUSTAIN_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(62, 257), module, ADSR::RELEASE_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(62, 57), module, ADSR::ATTACK_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(62, 124), module, ADSR::DECAY_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(62, 191), module, ADSR::SUSTAIN_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(62, 257), module, ADSR::RELEASE_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addInput(createInput<PJ301MPort>(Vec(9, 63), module, ADSR::ATTACK_INPUT)); | addInput(createInput<PJ301MPort>(Vec(9, 63), module, ADSR::ATTACK_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(9, 129), module, ADSR::DECAY_INPUT)); | addInput(createInput<PJ301MPort>(Vec(9, 129), module, ADSR::DECAY_INPUT)); | ||||
@@ -30,7 +30,7 @@ struct Delay : Module { | |||||
DoubleRingBuffer<float, HISTORY_SIZE> historyBuffer; | DoubleRingBuffer<float, HISTORY_SIZE> historyBuffer; | ||||
DoubleRingBuffer<float, 16> outBuffer; | DoubleRingBuffer<float, 16> outBuffer; | ||||
SampleRateConverter<1> src; | SampleRateConverter<1> src; | ||||
float lastWet = 0.0; | |||||
float lastWet = 0.0f; | |||||
RCFilter lowpassFilter; | RCFilter lowpassFilter; | ||||
RCFilter highpassFilter; | RCFilter highpassFilter; | ||||
@@ -43,15 +43,15 @@ struct Delay : Module { | |||||
void Delay::step() { | void Delay::step() { | ||||
// Get input to delay block | // Get input to delay block | ||||
float in = inputs[IN_INPUT].value; | float in = inputs[IN_INPUT].value; | ||||
float feedback = clampf(params[FEEDBACK_PARAM].value + inputs[FEEDBACK_INPUT].value / 10.0, 0.0, 1.0); | |||||
float feedback = clamp(params[FEEDBACK_PARAM].value + inputs[FEEDBACK_INPUT].value / 10.0f, 0.0f, 1.0f); | |||||
float dry = in + lastWet * feedback; | float dry = in + lastWet * feedback; | ||||
// Compute delay time in seconds | // Compute delay time in seconds | ||||
float delay = 1e-3 * powf(10.0 / 1e-3, clampf(params[TIME_PARAM].value + inputs[TIME_INPUT].value / 10.0, 0.0, 1.0)); | |||||
float delay = 1e-3 * powf(10.0f / 1e-3, clamp(params[TIME_PARAM].value + inputs[TIME_INPUT].value / 10.0f, 0.0f, 1.0f)); | |||||
// Number of delay samples | // Number of delay samples | ||||
float index = delay * engineGetSampleRate(); | float index = delay * engineGetSampleRate(); | ||||
// TODO This is a horrible digital delay algorithm. Rewrite later. | |||||
// TODO Rewrite this digital delay algorithm. | |||||
// Push dry sample into history buffer | // Push dry sample into history buffer | ||||
if (!historyBuffer.full()) { | if (!historyBuffer.full()) { | ||||
@@ -64,15 +64,14 @@ void Delay::step() { | |||||
// printf("wanted: %f\tactual: %d\tdiff: %d\tratio: %f\n", index, historyBuffer.size(), consume, index / historyBuffer.size()); | // printf("wanted: %f\tactual: %d\tdiff: %d\tratio: %f\n", index, historyBuffer.size(), consume, index / historyBuffer.size()); | ||||
if (outBuffer.empty()) { | if (outBuffer.empty()) { | ||||
// Idk wtf I'm doing | |||||
double ratio = 1.0; | |||||
double ratio = 1.0f; | |||||
if (consume <= -16) | if (consume <= -16) | ||||
ratio = 0.5; | |||||
ratio = 0.5f; | |||||
else if (consume >= 16) | else if (consume >= 16) | ||||
ratio = 2.0; | |||||
ratio = 2.0f; | |||||
// printf("%f\t%lf\n", consume, ratio); | // printf("%f\t%lf\n", consume, ratio); | ||||
int inFrames = mini(historyBuffer.size(), 16); | |||||
int inFrames = min(historyBuffer.size(), 16); | |||||
int outFrames = outBuffer.capacity(); | int outFrames = outBuffer.capacity(); | ||||
// printf(">\t%d\t%d\n", inFrames, outFrames); | // printf(">\t%d\t%d\n", inFrames, outFrames); | ||||
src.setRates(ratio * engineGetSampleRate(), engineGetSampleRate()); | src.setRates(ratio * engineGetSampleRate(), engineGetSampleRate()); | ||||
@@ -83,27 +82,27 @@ void Delay::step() { | |||||
// printf("====================================\n"); | // printf("====================================\n"); | ||||
} | } | ||||
float wet = 0.0; | |||||
float wet = 0.0f; | |||||
if (!outBuffer.empty()) { | if (!outBuffer.empty()) { | ||||
wet = outBuffer.shift(); | wet = outBuffer.shift(); | ||||
} | } | ||||
// Apply color to delay wet output | // Apply color to delay wet output | ||||
// TODO Make it sound better | // TODO Make it sound better | ||||
float color = clampf(params[COLOR_PARAM].value + inputs[COLOR_INPUT].value / 10.0, 0.0, 1.0); | |||||
float lowpassFreq = 10000.0 * powf(10.0, clampf(2.0*color, 0.0, 1.0)); | |||||
float color = clamp(params[COLOR_PARAM].value + inputs[COLOR_INPUT].value / 10.0f, 0.0f, 1.0f); | |||||
float lowpassFreq = 10000.0f * powf(10.0f, clamp(2.0f*color, 0.0f, 1.0f)); | |||||
lowpassFilter.setCutoff(lowpassFreq / engineGetSampleRate()); | lowpassFilter.setCutoff(lowpassFreq / engineGetSampleRate()); | ||||
lowpassFilter.process(wet); | lowpassFilter.process(wet); | ||||
wet = lowpassFilter.lowpass(); | wet = lowpassFilter.lowpass(); | ||||
float highpassFreq = 10.0 * powf(100.0, clampf(2.0*color - 1.0, 0.0, 1.0)); | |||||
float highpassFreq = 10.0f * powf(100.0f, clamp(2.0f*color - 1.0f, 0.0f, 1.0f)); | |||||
highpassFilter.setCutoff(highpassFreq / engineGetSampleRate()); | highpassFilter.setCutoff(highpassFreq / engineGetSampleRate()); | ||||
highpassFilter.process(wet); | highpassFilter.process(wet); | ||||
wet = highpassFilter.highpass(); | wet = highpassFilter.highpass(); | ||||
lastWet = wet; | lastWet = wet; | ||||
float mix = clampf(params[MIX_PARAM].value + inputs[MIX_INPUT].value / 10.0, 0.0, 1.0); | |||||
float out = crossf(in, wet, mix); | |||||
float mix = clamp(params[MIX_PARAM].value + inputs[MIX_INPUT].value / 10.0f, 0.0f, 1.0f); | |||||
float out = crossfade(in, wet, mix); | |||||
outputs[OUT_OUTPUT].value = out; | outputs[OUT_OUTPUT].value = out; | ||||
} | } | ||||
@@ -125,10 +124,10 @@ DelayWidget::DelayWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<RoundBlackKnob>(Vec(67, 57), module, Delay::TIME_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(67, 123), module, Delay::FEEDBACK_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(67, 190), module, Delay::COLOR_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(67, 257), module, Delay::MIX_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(67, 57), module, Delay::TIME_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(67, 123), module, Delay::FEEDBACK_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(67, 190), module, Delay::COLOR_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(67, 257), module, Delay::MIX_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addInput(createInput<PJ301MPort>(Vec(14, 63), module, Delay::TIME_INPUT)); | addInput(createInput<PJ301MPort>(Vec(14, 63), module, Delay::TIME_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(14, 129), module, Delay::FEEDBACK_INPUT)); | addInput(createInput<PJ301MPort>(Vec(14, 129), module, Delay::FEEDBACK_INPUT)); | ||||
@@ -3,61 +3,61 @@ | |||||
struct LowFrequencyOscillator { | struct LowFrequencyOscillator { | ||||
float phase = 0.0; | |||||
float pw = 0.5; | |||||
float freq = 1.0; | |||||
float phase = 0.0f; | |||||
float pw = 0.5f; | |||||
float freq = 1.0f; | |||||
bool offset = false; | bool offset = false; | ||||
bool invert = false; | bool invert = false; | ||||
SchmittTrigger resetTrigger; | SchmittTrigger resetTrigger; | ||||
LowFrequencyOscillator() { | LowFrequencyOscillator() { | ||||
resetTrigger.setThresholds(0.0, 0.01); | |||||
resetTrigger.setThresholds(0.0f, 0.01f); | |||||
} | } | ||||
void setPitch(float pitch) { | void setPitch(float pitch) { | ||||
pitch = fminf(pitch, 8.0); | |||||
freq = powf(2.0, pitch); | |||||
pitch = fminf(pitch, 8.0f); | |||||
freq = powf(2.0f, pitch); | |||||
} | } | ||||
void setPulseWidth(float pw_) { | void setPulseWidth(float pw_) { | ||||
const float pwMin = 0.01; | |||||
pw = clampf(pw_, pwMin, 1.0 - pwMin); | |||||
const float pwMin = 0.01f; | |||||
pw = clamp(pw_, pwMin, 1.0f - pwMin); | |||||
} | } | ||||
void setReset(float reset) { | void setReset(float reset) { | ||||
if (resetTrigger.process(reset)) { | if (resetTrigger.process(reset)) { | ||||
phase = 0.0; | |||||
phase = 0.0f; | |||||
} | } | ||||
} | } | ||||
void step(float dt) { | void step(float dt) { | ||||
float deltaPhase = fminf(freq * dt, 0.5); | |||||
float deltaPhase = fminf(freq * dt, 0.5f); | |||||
phase += deltaPhase; | phase += deltaPhase; | ||||
if (phase >= 1.0) | |||||
phase -= 1.0; | |||||
if (phase >= 1.0f) | |||||
phase -= 1.0f; | |||||
} | } | ||||
float sin() { | float sin() { | ||||
if (offset) | if (offset) | ||||
return 1.0 - cosf(2*M_PI * phase) * (invert ? -1.0 : 1.0); | |||||
return 1.0f - cosf(2*M_PI * phase) * (invert ? -1.0f : 1.0f); | |||||
else | else | ||||
return sinf(2*M_PI * phase) * (invert ? -1.0 : 1.0); | |||||
return sinf(2*M_PI * phase) * (invert ? -1.0f : 1.0f); | |||||
} | } | ||||
float tri(float x) { | float tri(float x) { | ||||
return 4.0 * fabsf(x - roundf(x)); | |||||
return 4.0f * fabsf(x - roundf(x)); | |||||
} | } | ||||
float tri() { | float tri() { | ||||
if (offset) | if (offset) | ||||
return tri(invert ? phase - 0.5 : phase); | |||||
return tri(invert ? phase - 0.5f : phase); | |||||
else | else | ||||
return -1.0 + tri(invert ? phase - 0.25 : phase - 0.75); | |||||
return -1.0f + tri(invert ? phase - 0.25f : phase - 0.75f); | |||||
} | } | ||||
float saw(float x) { | float saw(float x) { | ||||
return 2.0 * (x - roundf(x)); | |||||
return 2.0f * (x - roundf(x)); | |||||
} | } | ||||
float saw() { | float saw() { | ||||
if (offset) | if (offset) | ||||
return invert ? 2.0 * (1.0 - phase) : 2.0 * phase; | |||||
return invert ? 2.0f * (1.0f - phase) : 2.0f * phase; | |||||
else | else | ||||
return saw(phase) * (invert ? -1.0 : 1.0); | |||||
return saw(phase) * (invert ? -1.0f : 1.0f); | |||||
} | } | ||||
float sqr() { | float sqr() { | ||||
float sqr = (phase < pw) ^ invert ? 1.0 : -1.0; | |||||
return offset ? sqr + 1.0 : sqr; | |||||
float sqr = (phase < pw) ^ invert ? 1.0f : -1.0f; | |||||
return offset ? sqr + 1.0f : sqr; | |||||
} | } | ||||
float light() { | float light() { | ||||
return sinf(2*M_PI * phase); | return sinf(2*M_PI * phase); | ||||
@@ -105,19 +105,19 @@ struct LFO : Module { | |||||
void LFO::step() { | void LFO::step() { | ||||
oscillator.setPitch(params[FREQ_PARAM].value + params[FM1_PARAM].value * inputs[FM1_INPUT].value + params[FM2_PARAM].value * inputs[FM2_INPUT].value); | oscillator.setPitch(params[FREQ_PARAM].value + params[FM1_PARAM].value * inputs[FM1_INPUT].value + params[FM2_PARAM].value * inputs[FM2_INPUT].value); | ||||
oscillator.setPulseWidth(params[PW_PARAM].value + params[PWM_PARAM].value * inputs[PW_INPUT].value / 10.0); | |||||
oscillator.offset = (params[OFFSET_PARAM].value > 0.0); | |||||
oscillator.invert = (params[INVERT_PARAM].value <= 0.0); | |||||
oscillator.step(1.0 / engineGetSampleRate()); | |||||
oscillator.setPulseWidth(params[PW_PARAM].value + params[PWM_PARAM].value * inputs[PW_INPUT].value / 10.0f); | |||||
oscillator.offset = (params[OFFSET_PARAM].value > 0.0f); | |||||
oscillator.invert = (params[INVERT_PARAM].value <= 0.0f); | |||||
oscillator.step(engineGetSampleTime()); | |||||
oscillator.setReset(inputs[RESET_INPUT].value); | oscillator.setReset(inputs[RESET_INPUT].value); | ||||
outputs[SIN_OUTPUT].value = 5.0 * oscillator.sin(); | |||||
outputs[TRI_OUTPUT].value = 5.0 * oscillator.tri(); | |||||
outputs[SAW_OUTPUT].value = 5.0 * oscillator.saw(); | |||||
outputs[SQR_OUTPUT].value = 5.0 * oscillator.sqr(); | |||||
outputs[SIN_OUTPUT].value = 5.0f * oscillator.sin(); | |||||
outputs[TRI_OUTPUT].value = 5.0f * oscillator.tri(); | |||||
outputs[SAW_OUTPUT].value = 5.0f * oscillator.saw(); | |||||
outputs[SQR_OUTPUT].value = 5.0f * oscillator.sqr(); | |||||
lights[PHASE_POS_LIGHT].setBrightnessSmooth(fmaxf(0.0, oscillator.light())); | |||||
lights[PHASE_NEG_LIGHT].setBrightnessSmooth(fmaxf(0.0, -oscillator.light())); | |||||
lights[PHASE_POS_LIGHT].setBrightnessSmooth(fmaxf(0.0f, oscillator.light())); | |||||
lights[PHASE_NEG_LIGHT].setBrightnessSmooth(fmaxf(0.0f, -oscillator.light())); | |||||
} | } | ||||
@@ -138,14 +138,14 @@ LFOWidget::LFOWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<CKSS>(Vec(15, 77), module, LFO::OFFSET_PARAM, 0.0, 1.0, 1.0)); | |||||
addParam(createParam<CKSS>(Vec(119, 77), module, LFO::INVERT_PARAM, 0.0, 1.0, 1.0)); | |||||
addParam(createParam<CKSS>(Vec(15, 77), module, LFO::OFFSET_PARAM, 0.0f, 1.0f, 1.0f)); | |||||
addParam(createParam<CKSS>(Vec(119, 77), module, LFO::INVERT_PARAM, 0.0f, 1.0f, 1.0f)); | |||||
addParam(createParam<RoundHugeBlackKnob>(Vec(47, 61), module, LFO::FREQ_PARAM, -8.0, 6.0, -1.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(23, 143), module, LFO::FM1_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(91, 143), module, LFO::PW_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(23, 208), module, LFO::FM2_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(91, 208), module, LFO::PWM_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundHugeBlackKnob>(Vec(47, 61), module, LFO::FREQ_PARAM, -8.0f, 6.0f, -1.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(23, 143), module, LFO::FM1_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(91, 143), module, LFO::PW_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(23, 208), module, LFO::FM2_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(91, 208), module, LFO::PWM_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(Vec(11, 276), module, LFO::FM1_INPUT)); | addInput(createInput<PJ301MPort>(Vec(11, 276), module, LFO::FM1_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(45, 276), module, LFO::FM2_INPUT)); | addInput(createInput<PJ301MPort>(Vec(45, 276), module, LFO::FM2_INPUT)); | ||||
@@ -157,7 +157,7 @@ LFOWidget::LFOWidget() { | |||||
addOutput(createOutput<PJ301MPort>(Vec(80, 320), module, LFO::SAW_OUTPUT)); | addOutput(createOutput<PJ301MPort>(Vec(80, 320), module, LFO::SAW_OUTPUT)); | ||||
addOutput(createOutput<PJ301MPort>(Vec(114, 320), module, LFO::SQR_OUTPUT)); | addOutput(createOutput<PJ301MPort>(Vec(114, 320), module, LFO::SQR_OUTPUT)); | ||||
addChild(createLight<SmallLight<GreenRedLight>>(Vec(99, 42.5), module, LFO::PHASE_POS_LIGHT)); | |||||
addChild(createLight<SmallLight<GreenRedLight>>(Vec(99, 42.5f), module, LFO::PHASE_POS_LIGHT)); | |||||
} | } | ||||
@@ -196,24 +196,24 @@ struct LFO2 : Module { | |||||
void LFO2::step() { | void LFO2::step() { | ||||
oscillator.setPitch(params[FREQ_PARAM].value + params[FM_PARAM].value * inputs[FM_INPUT].value); | oscillator.setPitch(params[FREQ_PARAM].value + params[FM_PARAM].value * inputs[FM_INPUT].value); | ||||
oscillator.offset = (params[OFFSET_PARAM].value > 0.0); | |||||
oscillator.invert = (params[INVERT_PARAM].value <= 0.0); | |||||
oscillator.step(1.0 / engineGetSampleRate()); | |||||
oscillator.offset = (params[OFFSET_PARAM].value > 0.0f); | |||||
oscillator.invert = (params[INVERT_PARAM].value <= 0.0f); | |||||
oscillator.step(engineGetSampleTime()); | |||||
oscillator.setReset(inputs[RESET_INPUT].value); | oscillator.setReset(inputs[RESET_INPUT].value); | ||||
float wave = params[WAVE_PARAM].value + inputs[WAVE_INPUT].value; | float wave = params[WAVE_PARAM].value + inputs[WAVE_INPUT].value; | ||||
wave = clampf(wave, 0.0, 3.0); | |||||
wave = clamp(wave, 0.0f, 3.0f); | |||||
float interp; | float interp; | ||||
if (wave < 1.0) | |||||
interp = crossf(oscillator.sin(), oscillator.tri(), wave); | |||||
else if (wave < 2.0) | |||||
interp = crossf(oscillator.tri(), oscillator.saw(), wave - 1.0); | |||||
if (wave < 1.0f) | |||||
interp = crossfade(oscillator.sin(), oscillator.tri(), wave); | |||||
else if (wave < 2.0f) | |||||
interp = crossfade(oscillator.tri(), oscillator.saw(), wave - 1.0f); | |||||
else | else | ||||
interp = crossf(oscillator.saw(), oscillator.sqr(), wave - 2.0); | |||||
outputs[INTERP_OUTPUT].value = 5.0 * interp; | |||||
interp = crossfade(oscillator.saw(), oscillator.sqr(), wave - 2.0f); | |||||
outputs[INTERP_OUTPUT].value = 5.0f * interp; | |||||
lights[PHASE_POS_LIGHT].setBrightnessSmooth(fmaxf(0.0, oscillator.light())); | |||||
lights[PHASE_NEG_LIGHT].setBrightnessSmooth(fmaxf(0.0, -oscillator.light())); | |||||
lights[PHASE_POS_LIGHT].setBrightnessSmooth(fmaxf(0.0f, oscillator.light())); | |||||
lights[PHASE_NEG_LIGHT].setBrightnessSmooth(fmaxf(0.0f, -oscillator.light())); | |||||
} | } | ||||
@@ -234,12 +234,12 @@ LFO2Widget::LFO2Widget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<CKSS>(Vec(62, 150), module, LFO2::OFFSET_PARAM, 0.0, 1.0, 1.0)); | |||||
addParam(createParam<CKSS>(Vec(62, 215), module, LFO2::INVERT_PARAM, 0.0, 1.0, 1.0)); | |||||
addParam(createParam<CKSS>(Vec(62, 150), module, LFO2::OFFSET_PARAM, 0.0f, 1.0f, 1.0f)); | |||||
addParam(createParam<CKSS>(Vec(62, 215), module, LFO2::INVERT_PARAM, 0.0f, 1.0f, 1.0f)); | |||||
addParam(createParam<RoundHugeBlackKnob>(Vec(18, 60), module, LFO2::FREQ_PARAM, -8.0, 6.0, -1.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(11, 142), module, LFO2::WAVE_PARAM, 0.0, 3.0, 1.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(11, 207), module, LFO2::FM_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundHugeBlackKnob>(Vec(18, 60), module, LFO2::FREQ_PARAM, -8.0f, 6.0f, -1.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(11, 142), module, LFO2::WAVE_PARAM, 0.0f, 3.0f, 1.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(11, 207), module, LFO2::FM_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addInput(createInput<PJ301MPort>(Vec(11, 276), module, LFO2::FM_INPUT)); | addInput(createInput<PJ301MPort>(Vec(11, 276), module, LFO2::FM_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(54, 276), module, LFO2::RESET_INPUT)); | addInput(createInput<PJ301MPort>(Vec(54, 276), module, LFO2::RESET_INPUT)); | ||||
@@ -247,5 +247,5 @@ LFO2Widget::LFO2Widget() { | |||||
addOutput(createOutput<PJ301MPort>(Vec(54, 319), module, LFO2::INTERP_OUTPUT)); | addOutput(createOutput<PJ301MPort>(Vec(54, 319), module, LFO2::INTERP_OUTPUT)); | ||||
addChild(createLight<SmallLight<GreenRedLight>>(Vec(68, 42.5), module, LFO2::PHASE_POS_LIGHT)); | |||||
addChild(createLight<SmallLight<GreenRedLight>>(Vec(68, 42.5f), module, LFO2::PHASE_POS_LIGHT)); | |||||
} | } |
@@ -38,7 +38,7 @@ struct Mutes : Module { | |||||
} | } | ||||
void onRandomize() override { | void onRandomize() override { | ||||
for (int i = 0; i < NUM_CHANNELS; i++) { | for (int i = 0; i < NUM_CHANNELS; i++) { | ||||
state[i] = (randomf() < 0.5); | |||||
state[i] = (randomf() < 0.5f); | |||||
} | } | ||||
} | } | ||||
@@ -67,14 +67,14 @@ struct Mutes : Module { | |||||
}; | }; | ||||
void Mutes::step() { | void Mutes::step() { | ||||
float out = 0.0; | |||||
float out = 0.0f; | |||||
for (int i = 0; i < NUM_CHANNELS; i++) { | for (int i = 0; i < NUM_CHANNELS; i++) { | ||||
if (muteTrigger[i].process(params[MUTE_PARAM + i].value)) | if (muteTrigger[i].process(params[MUTE_PARAM + i].value)) | ||||
state[i] ^= true; | state[i] ^= true; | ||||
if (inputs[IN_INPUT + i].active) | if (inputs[IN_INPUT + i].active) | ||||
out = inputs[IN_INPUT + i].value; | out = inputs[IN_INPUT + i].value; | ||||
outputs[OUT_OUTPUT + i].value = state[i] ? out : 0.0; | |||||
lights[MUTE_LIGHT + i].setBrightness(state[i] ? 0.9 : 0.0); | |||||
outputs[OUT_OUTPUT + i].value = state[i] ? out : 0.0f; | |||||
lights[MUTE_LIGHT + i].setBrightness(state[i] ? 0.9f : 0.0f); | |||||
} | } | ||||
} | } | ||||
@@ -82,7 +82,7 @@ void Mutes::step() { | |||||
template <typename BASE> | template <typename BASE> | ||||
struct MuteLight : BASE { | struct MuteLight : BASE { | ||||
MuteLight() { | MuteLight() { | ||||
this->box.size = mm2px(Vec(6.0, 6.0)); | |||||
this->box.size = mm2px(Vec(6.0f, 6.0f)); | |||||
} | } | ||||
}; | }; | ||||
@@ -96,16 +96,16 @@ MutesWidget::MutesWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x - 30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x - 30, 365))); | ||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 18.165)), module, Mutes::MUTE_PARAM + 0, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 28.164)), module, Mutes::MUTE_PARAM + 1, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 38.164)), module, Mutes::MUTE_PARAM + 2, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 48.165)), module, Mutes::MUTE_PARAM + 3, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 58.164)), module, Mutes::MUTE_PARAM + 4, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 68.165)), module, Mutes::MUTE_PARAM + 5, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 78.164)), module, Mutes::MUTE_PARAM + 6, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 88.164)), module, Mutes::MUTE_PARAM + 7, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 98.165)), module, Mutes::MUTE_PARAM + 8, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 108.166)), module, Mutes::MUTE_PARAM + 9, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 18.165)), module, Mutes::MUTE_PARAM + 0, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 28.164)), module, Mutes::MUTE_PARAM + 1, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 38.164)), module, Mutes::MUTE_PARAM + 2, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 48.165)), module, Mutes::MUTE_PARAM + 3, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 58.164)), module, Mutes::MUTE_PARAM + 4, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 68.165)), module, Mutes::MUTE_PARAM + 5, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 78.164)), module, Mutes::MUTE_PARAM + 6, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 88.164)), module, Mutes::MUTE_PARAM + 7, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 98.165)), module, Mutes::MUTE_PARAM + 8, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<LEDBezel>(mm2px(Vec(16.57, 108.166)), module, Mutes::MUTE_PARAM + 9, 0.0f, 1.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(mm2px(Vec(4.214, 17.81)), module, Mutes::IN_INPUT + 0)); | addInput(createInput<PJ301MPort>(mm2px(Vec(4.214, 17.81)), module, Mutes::IN_INPUT + 0)); | ||||
addInput(createInput<PJ301MPort>(mm2px(Vec(4.214, 27.809)), module, Mutes::IN_INPUT + 1)); | addInput(createInput<PJ301MPort>(mm2px(Vec(4.214, 27.809)), module, Mutes::IN_INPUT + 1)); | ||||
@@ -44,10 +44,10 @@ struct SEQ3 : Module { | |||||
SchmittTrigger runningTrigger; | SchmittTrigger runningTrigger; | ||||
SchmittTrigger resetTrigger; | SchmittTrigger resetTrigger; | ||||
SchmittTrigger gateTriggers[8]; | SchmittTrigger gateTriggers[8]; | ||||
float phase = 0.0; | |||||
float phase = 0.0f; | |||||
int index = 0; | int index = 0; | ||||
bool gateState[8] = {}; | bool gateState[8] = {}; | ||||
float resetLight = 0.0; | |||||
float resetLight = 0.0f; | |||||
float stepLights[8] = {}; | float stepLights[8] = {}; | ||||
enum GateMode { | enum GateMode { | ||||
@@ -114,19 +114,19 @@ struct SEQ3 : Module { | |||||
void onRandomize() override { | void onRandomize() override { | ||||
for (int i = 0; i < 8; i++) { | for (int i = 0; i < 8; i++) { | ||||
gateState[i] = (randomf() > 0.5); | |||||
gateState[i] = (randomf() > 0.5f); | |||||
} | } | ||||
} | } | ||||
}; | }; | ||||
void SEQ3::step() { | void SEQ3::step() { | ||||
const float lightLambda = 0.075; | |||||
const float lightLambda = 0.075f; | |||||
// Run | // Run | ||||
if (runningTrigger.process(params[RUN_PARAM].value)) { | if (runningTrigger.process(params[RUN_PARAM].value)) { | ||||
running = !running; | running = !running; | ||||
} | } | ||||
lights[RUNNING_LIGHT].value = running ? 1.0 : 0.0; | |||||
lights[RUNNING_LIGHT].value = running ? 1.0f : 0.0f; | |||||
bool nextStep = false; | bool nextStep = false; | ||||
@@ -134,16 +134,16 @@ void SEQ3::step() { | |||||
if (inputs[EXT_CLOCK_INPUT].active) { | if (inputs[EXT_CLOCK_INPUT].active) { | ||||
// External clock | // External clock | ||||
if (clockTrigger.process(inputs[EXT_CLOCK_INPUT].value)) { | if (clockTrigger.process(inputs[EXT_CLOCK_INPUT].value)) { | ||||
phase = 0.0; | |||||
phase = 0.0f; | |||||
nextStep = true; | nextStep = true; | ||||
} | } | ||||
} | } | ||||
else { | else { | ||||
// Internal clock | // Internal clock | ||||
float clockTime = powf(2.0, params[CLOCK_PARAM].value + inputs[CLOCK_INPUT].value); | |||||
phase += clockTime / engineGetSampleRate(); | |||||
if (phase >= 1.0) { | |||||
phase -= 1.0; | |||||
float clockTime = powf(2.0f, params[CLOCK_PARAM].value + inputs[CLOCK_INPUT].value); | |||||
phase += clockTime * engineGetSampleTime(); | |||||
if (phase >= 1.0f) { | |||||
phase -= 1.0f; | |||||
nextStep = true; | nextStep = true; | ||||
} | } | ||||
} | } | ||||
@@ -151,26 +151,26 @@ void SEQ3::step() { | |||||
// Reset | // Reset | ||||
if (resetTrigger.process(params[RESET_PARAM].value + inputs[RESET_INPUT].value)) { | if (resetTrigger.process(params[RESET_PARAM].value + inputs[RESET_INPUT].value)) { | ||||
phase = 0.0; | |||||
phase = 0.0f; | |||||
index = 8; | index = 8; | ||||
nextStep = true; | nextStep = true; | ||||
resetLight = 1.0; | |||||
resetLight = 1.0f; | |||||
} | } | ||||
if (nextStep) { | if (nextStep) { | ||||
// Advance step | // Advance step | ||||
int numSteps = clampi(roundf(params[STEPS_PARAM].value + inputs[STEPS_INPUT].value), 1, 8); | |||||
int numSteps = clamp(roundf(params[STEPS_PARAM].value + inputs[STEPS_INPUT].value), 1.0f, 8.0f); | |||||
index += 1; | index += 1; | ||||
if (index >= numSteps) { | if (index >= numSteps) { | ||||
index = 0; | index = 0; | ||||
} | } | ||||
stepLights[index] = 1.0; | |||||
stepLights[index] = 1.0f; | |||||
gatePulse.trigger(1e-3); | gatePulse.trigger(1e-3); | ||||
} | } | ||||
resetLight -= resetLight / lightLambda / engineGetSampleRate(); | |||||
resetLight -= resetLight / lightLambda * engineGetSampleTime(); | |||||
bool pulse = gatePulse.process(1.0 / engineGetSampleRate()); | |||||
bool pulse = gatePulse.process(engineGetSampleTime()); | |||||
// Gate buttons | // Gate buttons | ||||
for (int i = 0; i < 8; i++) { | for (int i = 0; i < 8; i++) { | ||||
@@ -183,9 +183,9 @@ void SEQ3::step() { | |||||
else if (gateMode == RETRIGGER) | else if (gateMode == RETRIGGER) | ||||
gateOn = gateOn && !pulse; | gateOn = gateOn && !pulse; | ||||
outputs[GATE_OUTPUT + i].value = gateOn ? 10.0 : 0.0; | |||||
stepLights[i] -= stepLights[i] / lightLambda / engineGetSampleRate(); | |||||
lights[GATE_LIGHTS + i].value = gateState[i] ? 1.0 - stepLights[i] : stepLights[i]; | |||||
outputs[GATE_OUTPUT + i].value = gateOn ? 10.0f : 0.0f; | |||||
stepLights[i] -= stepLights[i] / lightLambda * engineGetSampleTime(); | |||||
lights[GATE_LIGHTS + i].value = gateState[i] ? 1.0f - stepLights[i] : stepLights[i]; | |||||
} | } | ||||
// Rows | // Rows | ||||
@@ -202,12 +202,12 @@ void SEQ3::step() { | |||||
outputs[ROW1_OUTPUT].value = row1; | outputs[ROW1_OUTPUT].value = row1; | ||||
outputs[ROW2_OUTPUT].value = row2; | outputs[ROW2_OUTPUT].value = row2; | ||||
outputs[ROW3_OUTPUT].value = row3; | outputs[ROW3_OUTPUT].value = row3; | ||||
outputs[GATES_OUTPUT].value = gatesOn ? 10.0 : 0.0; | |||||
outputs[GATES_OUTPUT].value = gatesOn ? 10.0f : 0.0f; | |||||
lights[RESET_LIGHT].value = resetLight; | lights[RESET_LIGHT].value = resetLight; | ||||
lights[GATES_LIGHT].value = gatesOn ? 1.0 : 0.0; | |||||
lights[ROW_LIGHTS].value = row1 / 10.0; | |||||
lights[ROW_LIGHTS + 1].value = row2 / 10.0; | |||||
lights[ROW_LIGHTS + 2].value = row3 / 10.0; | |||||
lights[GATES_LIGHT].value = gatesOn ? 1.0f : 0.0f; | |||||
lights[ROW_LIGHTS].value = row1 / 10.0f; | |||||
lights[ROW_LIGHTS + 1].value = row2 / 10.0f; | |||||
lights[ROW_LIGHTS + 2].value = row3 / 10.0f; | |||||
} | } | ||||
@@ -228,16 +228,16 @@ SEQ3Widget::SEQ3Widget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<RoundSmallBlackKnob>(Vec(18, 56), module, SEQ3::CLOCK_PARAM, -2.0, 6.0, 2.0)); | |||||
addParam(createParam<LEDButton>(Vec(60, 61-1), module, SEQ3::RUN_PARAM, 0.0, 1.0, 0.0)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(64.4, 64.4), module, SEQ3::RUNNING_LIGHT)); | |||||
addParam(createParam<LEDButton>(Vec(99, 61-1), module, SEQ3::RESET_PARAM, 0.0, 1.0, 0.0)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(103.4, 64.4), module, SEQ3::RESET_LIGHT)); | |||||
addParam(createParam<RoundSmallBlackSnapKnob>(Vec(132, 56), module, SEQ3::STEPS_PARAM, 1.0, 8.0, 8.0)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(179.4, 64.4), module, SEQ3::GATES_LIGHT)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(218.4, 64.4), module, SEQ3::ROW_LIGHTS)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(256.4, 64.4), module, SEQ3::ROW_LIGHTS + 1)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(295.4, 64.4), module, SEQ3::ROW_LIGHTS + 2)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(18, 56), module, SEQ3::CLOCK_PARAM, -2.0f, 6.0f, 2.0f)); | |||||
addParam(createParam<LEDButton>(Vec(60, 61-1), module, SEQ3::RUN_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(64.4f, 64.4f), module, SEQ3::RUNNING_LIGHT)); | |||||
addParam(createParam<LEDButton>(Vec(99, 61-1), module, SEQ3::RESET_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(103.4f, 64.4f), module, SEQ3::RESET_LIGHT)); | |||||
addParam(createParam<RoundSmallBlackSnapKnob>(Vec(132, 56), module, SEQ3::STEPS_PARAM, 1.0f, 8.0f, 8.0f)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(179.4f, 64.4f), module, SEQ3::GATES_LIGHT)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(218.4f, 64.4f), module, SEQ3::ROW_LIGHTS)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(256.4f, 64.4f), module, SEQ3::ROW_LIGHTS + 1)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(295.4f, 64.4f), module, SEQ3::ROW_LIGHTS + 2)); | |||||
static const float portX[8] = {20, 58, 96, 135, 173, 212, 250, 289}; | static const float portX[8] = {20, 58, 96, 135, 173, 212, 250, 289}; | ||||
addInput(createInput<PJ301MPort>(Vec(portX[0]-1, 98), module, SEQ3::CLOCK_INPUT)); | addInput(createInput<PJ301MPort>(Vec(portX[0]-1, 98), module, SEQ3::CLOCK_INPUT)); | ||||
@@ -250,11 +250,11 @@ SEQ3Widget::SEQ3Widget() { | |||||
addOutput(createOutput<PJ301MPort>(Vec(portX[7]-1, 98), module, SEQ3::ROW3_OUTPUT)); | addOutput(createOutput<PJ301MPort>(Vec(portX[7]-1, 98), module, SEQ3::ROW3_OUTPUT)); | ||||
for (int i = 0; i < 8; i++) { | for (int i = 0; i < 8; i++) { | ||||
addParam(createParam<RoundSmallBlackKnob>(Vec(portX[i]-2, 157), module, SEQ3::ROW1_PARAM + i, 0.0, 10.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(portX[i]-2, 198), module, SEQ3::ROW2_PARAM + i, 0.0, 10.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(portX[i]-2, 240), module, SEQ3::ROW3_PARAM + i, 0.0, 10.0, 0.0)); | |||||
addParam(createParam<LEDButton>(Vec(portX[i]+2, 278-1), module, SEQ3::GATE_PARAM + i, 0.0, 1.0, 0.0)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(portX[i]+6.4, 281.4), module, SEQ3::GATE_LIGHTS + i)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(portX[i]-2, 157), module, SEQ3::ROW1_PARAM + i, 0.0f, 10.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(portX[i]-2, 198), module, SEQ3::ROW2_PARAM + i, 0.0f, 10.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(portX[i]-2, 240), module, SEQ3::ROW3_PARAM + i, 0.0f, 10.0f, 0.0f)); | |||||
addParam(createParam<LEDButton>(Vec(portX[i]+2, 278-1), module, SEQ3::GATE_PARAM + i, 0.0f, 1.0f, 0.0f)); | |||||
addChild(createLight<MediumLight<GreenLight>>(Vec(portX[i]+6.4f, 281.4f), module, SEQ3::GATE_LIGHTS + i)); | |||||
addOutput(createOutput<PJ301MPort>(Vec(portX[i]-1, 307), module, SEQ3::GATE_OUTPUT + i)); | addOutput(createOutput<PJ301MPort>(Vec(portX[i]-1, 307), module, SEQ3::GATE_OUTPUT + i)); | ||||
} | } | ||||
} | } | ||||
@@ -266,7 +266,7 @@ struct SEQ3GateModeItem : MenuItem { | |||||
seq3->gateMode = gateMode; | seq3->gateMode = gateMode; | ||||
} | } | ||||
void step() override { | void step() override { | ||||
rightText = (seq3->gateMode == gateMode) ? "âś”" : ""; | |||||
rightText = CHECKMARK(seq3->gateMode == gateMode); | |||||
} | } | ||||
}; | }; | ||||
@@ -77,17 +77,17 @@ void Scope::step() { | |||||
if (sumTrigger.process(params[LISSAJOUS_PARAM].value)) { | if (sumTrigger.process(params[LISSAJOUS_PARAM].value)) { | ||||
lissajous = !lissajous; | lissajous = !lissajous; | ||||
} | } | ||||
lights[PLOT_LIGHT].value = lissajous ? 0.0 : 1.0; | |||||
lights[LISSAJOUS_LIGHT].value = lissajous ? 1.0 : 0.0; | |||||
lights[PLOT_LIGHT].value = lissajous ? 0.0f : 1.0f; | |||||
lights[LISSAJOUS_LIGHT].value = lissajous ? 1.0f : 0.0f; | |||||
if (extTrigger.process(params[EXTERNAL_PARAM].value)) { | if (extTrigger.process(params[EXTERNAL_PARAM].value)) { | ||||
external = !external; | external = !external; | ||||
} | } | ||||
lights[INTERNAL_LIGHT].value = external ? 0.0 : 1.0; | |||||
lights[EXTERNAL_LIGHT].value = external ? 1.0 : 0.0; | |||||
lights[INTERNAL_LIGHT].value = external ? 0.0f : 1.0f; | |||||
lights[EXTERNAL_LIGHT].value = external ? 1.0f : 0.0f; | |||||
// Compute time | // Compute time | ||||
float deltaTime = powf(2.0, params[TIME_PARAM].value); | |||||
float deltaTime = powf(2.0f, params[TIME_PARAM].value); | |||||
int frameCount = (int)ceilf(deltaTime * engineGetSampleRate()); | int frameCount = (int)ceilf(deltaTime * engineGetSampleRate()); | ||||
// Add frame to buffer | // Add frame to buffer | ||||
@@ -115,12 +115,12 @@ void Scope::step() { | |||||
} | } | ||||
frameIndex++; | frameIndex++; | ||||
// Must go below 0.1V to trigger | |||||
resetTrigger.setThresholds(params[TRIG_PARAM].value - 0.1, params[TRIG_PARAM].value); | |||||
// Must go below 0.1fV to trigger | |||||
resetTrigger.setThresholds(params[TRIG_PARAM].value - 0.1f, params[TRIG_PARAM].value); | |||||
float gate = external ? inputs[TRIG_INPUT].value : inputs[X_INPUT].value; | float gate = external ? inputs[TRIG_INPUT].value : inputs[X_INPUT].value; | ||||
// Reset if triggered | // Reset if triggered | ||||
float holdTime = 0.1; | |||||
float holdTime = 0.1f; | |||||
if (resetTrigger.process(gate) || (frameIndex >= engineGetSampleRate() * holdTime)) { | if (resetTrigger.process(gate) || (frameIndex >= engineGetSampleRate() * holdTime)) { | ||||
bufferIndex = 0; frameIndex = 0; return; | bufferIndex = 0; frameIndex = 0; return; | ||||
} | } | ||||
@@ -141,7 +141,7 @@ struct ScopeDisplay : TransparentWidget { | |||||
struct Stats { | struct Stats { | ||||
float vrms, vpp, vmin, vmax; | float vrms, vpp, vmin, vmax; | ||||
void calculate(float *values) { | void calculate(float *values) { | ||||
vrms = 0.0; | |||||
vrms = 0.0f; | |||||
vmax = -INFINITY; | vmax = -INFINITY; | ||||
vmin = INFINITY; | vmin = INFINITY; | ||||
for (int i = 0; i < BUFFER_SIZE; i++) { | for (int i = 0; i < BUFFER_SIZE; i++) { | ||||
@@ -171,24 +171,24 @@ struct ScopeDisplay : TransparentWidget { | |||||
for (int i = 0; i < BUFFER_SIZE; i++) { | for (int i = 0; i < BUFFER_SIZE; i++) { | ||||
float x, y; | float x, y; | ||||
if (valuesY) { | if (valuesY) { | ||||
x = valuesX[i] / 2.0 + 0.5; | |||||
y = valuesY[i] / 2.0 + 0.5; | |||||
x = valuesX[i] / 2.0f + 0.5f; | |||||
y = valuesY[i] / 2.0f + 0.5f; | |||||
} | } | ||||
else { | else { | ||||
x = (float)i / (BUFFER_SIZE - 1); | x = (float)i / (BUFFER_SIZE - 1); | ||||
y = valuesX[i] / 2.0 + 0.5; | |||||
y = valuesX[i] / 2.0f + 0.5f; | |||||
} | } | ||||
Vec p; | Vec p; | ||||
p.x = b.pos.x + b.size.x * x; | p.x = b.pos.x + b.size.x * x; | ||||
p.y = b.pos.y + b.size.y * (1.0 - y); | |||||
p.y = b.pos.y + b.size.y * (1.0f - y); | |||||
if (i == 0) | if (i == 0) | ||||
nvgMoveTo(vg, p.x, p.y); | nvgMoveTo(vg, p.x, p.y); | ||||
else | else | ||||
nvgLineTo(vg, p.x, p.y); | nvgLineTo(vg, p.x, p.y); | ||||
} | } | ||||
nvgLineCap(vg, NVG_ROUND); | nvgLineCap(vg, NVG_ROUND); | ||||
nvgMiterLimit(vg, 2.0); | |||||
nvgStrokeWidth(vg, 1.5); | |||||
nvgMiterLimit(vg, 2.0f); | |||||
nvgStrokeWidth(vg, 1.5f); | |||||
nvgGlobalCompositeOperation(vg, NVG_LIGHTER); | nvgGlobalCompositeOperation(vg, NVG_LIGHTER); | ||||
nvgStroke(vg); | nvgStroke(vg); | ||||
nvgResetScissor(vg); | nvgResetScissor(vg); | ||||
@@ -199,8 +199,8 @@ struct ScopeDisplay : TransparentWidget { | |||||
Rect b = Rect(Vec(0, 15), box.size.minus(Vec(0, 15*2))); | Rect b = Rect(Vec(0, 15), box.size.minus(Vec(0, 15*2))); | ||||
nvgScissor(vg, b.pos.x, b.pos.y, b.size.x, b.size.y); | nvgScissor(vg, b.pos.x, b.pos.y, b.size.x, b.size.y); | ||||
value = value / 2.0 + 0.5; | |||||
Vec p = Vec(box.size.x, b.pos.y + b.size.y * (1.0 - value)); | |||||
value = value / 2.0f + 0.5f; | |||||
Vec p = Vec(box.size.x, b.pos.y + b.size.y * (1.0f - value)); | |||||
// Draw line | // Draw line | ||||
nvgStrokeColor(vg, nvgRGBA(0xff, 0xff, 0xff, 0x10)); | nvgStrokeColor(vg, nvgRGBA(0xff, 0xff, 0xff, 0x10)); | ||||
@@ -247,8 +247,8 @@ struct ScopeDisplay : TransparentWidget { | |||||
} | } | ||||
void draw(NVGcontext *vg) override { | void draw(NVGcontext *vg) override { | ||||
float gainX = powf(2.0, roundf(module->params[Scope::X_SCALE_PARAM].value)); | |||||
float gainY = powf(2.0, roundf(module->params[Scope::Y_SCALE_PARAM].value)); | |||||
float gainX = powf(2.0f, roundf(module->params[Scope::X_SCALE_PARAM].value)); | |||||
float gainY = powf(2.0f, roundf(module->params[Scope::Y_SCALE_PARAM].value)); | |||||
float offsetX = module->params[Scope::X_POS_PARAM].value; | float offsetX = module->params[Scope::X_POS_PARAM].value; | ||||
float offsetY = module->params[Scope::Y_POS_PARAM].value; | float offsetY = module->params[Scope::Y_POS_PARAM].value; | ||||
@@ -259,8 +259,8 @@ struct ScopeDisplay : TransparentWidget { | |||||
// Lock display to buffer if buffer update deltaTime <= 2^-11 | // Lock display to buffer if buffer update deltaTime <= 2^-11 | ||||
if (module->lissajous) | if (module->lissajous) | ||||
j = (i + module->bufferIndex) % BUFFER_SIZE; | j = (i + module->bufferIndex) % BUFFER_SIZE; | ||||
valuesX[i] = (module->bufferX[j] + offsetX) * gainX / 10.0; | |||||
valuesY[i] = (module->bufferY[j] + offsetY) * gainY / 10.0; | |||||
valuesX[i] = (module->bufferX[j] + offsetX) * gainX / 10.0f; | |||||
valuesY[i] = (module->bufferY[j] + offsetY) * gainY / 10.0f; | |||||
} | } | ||||
// Draw waveforms | // Draw waveforms | ||||
@@ -284,7 +284,7 @@ struct ScopeDisplay : TransparentWidget { | |||||
drawWaveform(vg, valuesX, NULL); | drawWaveform(vg, valuesX, NULL); | ||||
} | } | ||||
float valueTrig = (module->params[Scope::TRIG_PARAM].value + offsetX) * gainX / 10.0; | |||||
float valueTrig = (module->params[Scope::TRIG_PARAM].value + offsetX) * gainX / 10.0f; | |||||
drawTrig(vg, valueTrig); | drawTrig(vg, valueTrig); | ||||
} | } | ||||
@@ -325,14 +325,14 @@ ScopeWidget::ScopeWidget() { | |||||
addChild(display); | addChild(display); | ||||
} | } | ||||
addParam(createParam<RoundSmallBlackSnapKnob>(Vec(15, 209), module, Scope::X_SCALE_PARAM, -2.0, 8.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(15, 263), module, Scope::X_POS_PARAM, -10.0, 10.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackSnapKnob>(Vec(61, 209), module, Scope::Y_SCALE_PARAM, -2.0, 8.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(61, 263), module, Scope::Y_POS_PARAM, -10.0, 10.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(107, 209), module, Scope::TIME_PARAM, -6.0, -16.0, -14.0)); | |||||
addParam(createParam<CKD6>(Vec(106, 262), module, Scope::LISSAJOUS_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(153, 209), module, Scope::TRIG_PARAM, -10.0, 10.0, 0.0)); | |||||
addParam(createParam<CKD6>(Vec(152, 262), module, Scope::EXTERNAL_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundSmallBlackSnapKnob>(Vec(15, 209), module, Scope::X_SCALE_PARAM, -2.0f, 8.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(15, 263), module, Scope::X_POS_PARAM, -10.0f, 10.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackSnapKnob>(Vec(61, 209), module, Scope::Y_SCALE_PARAM, -2.0f, 8.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(61, 263), module, Scope::Y_POS_PARAM, -10.0f, 10.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(107, 209), module, Scope::TIME_PARAM, -6.0f, -16.0f, -14.0f)); | |||||
addParam(createParam<CKD6>(Vec(106, 262), module, Scope::LISSAJOUS_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundSmallBlackKnob>(Vec(153, 209), module, Scope::TRIG_PARAM, -10.0f, 10.0f, 0.0f)); | |||||
addParam(createParam<CKD6>(Vec(152, 262), module, Scope::EXTERNAL_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(Vec(17, 319), module, Scope::X_INPUT)); | addInput(createInput<PJ301MPort>(Vec(17, 319), module, Scope::X_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(63, 319), module, Scope::Y_INPUT)); | addInput(createInput<PJ301MPort>(Vec(63, 319), module, Scope::Y_INPUT)); | ||||
@@ -30,11 +30,11 @@ struct SequentialSwitch : Module { | |||||
SlewLimiter channelFilter[4]; | SlewLimiter channelFilter[4]; | ||||
SequentialSwitch() : Module(NUM_PARAMS, NUM_INPUTS, NUM_OUTPUTS, NUM_LIGHTS) { | SequentialSwitch() : Module(NUM_PARAMS, NUM_INPUTS, NUM_OUTPUTS, NUM_LIGHTS) { | ||||
clockTrigger.setThresholds(0.0, 2.0); | |||||
resetTrigger.setThresholds(0.0, 2.0); | |||||
clockTrigger.setThresholds(0.0f, 2.0f); | |||||
resetTrigger.setThresholds(0.0f, 2.0f); | |||||
for (int i = 0; i < 4; i++) { | for (int i = 0; i < 4; i++) { | ||||
channelFilter[i].rise = 0.01; | |||||
channelFilter[i].fall = 0.01; | |||||
channelFilter[i].rise = 0.01f; | |||||
channelFilter[i].fall = 0.01f; | |||||
} | } | ||||
} | } | ||||
@@ -51,7 +51,7 @@ struct SequentialSwitch : Module { | |||||
// Filter channels | // Filter channels | ||||
for (int i = 0; i < 4; i++) { | for (int i = 0; i < 4; i++) { | ||||
channelFilter[i].process(channel == i ? 1.0 : 0.0); | |||||
channelFilter[i].process(channel == i ? 1.0f : 0.0f); | |||||
} | } | ||||
// Set outputs | // Set outputs | ||||
@@ -62,7 +62,7 @@ struct SequentialSwitch : Module { | |||||
} | } | ||||
} | } | ||||
else { | else { | ||||
float out = 0.0; | |||||
float out = 0.0f; | |||||
for (int i = 0; i < 4; i++) { | for (int i = 0; i < 4; i++) { | ||||
out += channelFilter[i].out * inputs[IN_INPUT + i].value; | out += channelFilter[i].out * inputs[IN_INPUT + i].value; | ||||
} | } | ||||
@@ -86,7 +86,7 @@ SequentialSwitch1Widget::SequentialSwitch1Widget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(RACK_GRID_WIDTH, 0))); | addChild(createScrew<ScrewSilver>(Vec(RACK_GRID_WIDTH, 0))); | ||||
addChild(createScrew<ScrewSilver>(Vec(RACK_GRID_WIDTH, RACK_GRID_HEIGHT - RACK_GRID_WIDTH))); | addChild(createScrew<ScrewSilver>(Vec(RACK_GRID_WIDTH, RACK_GRID_HEIGHT - RACK_GRID_WIDTH))); | ||||
addParam(createParam<CKSSThree>(mm2px(Vec(5.24619, 46.9153)), module, TSequentialSwitch::CHANNELS_PARAM, 0.0, 2.0, 0.0)); | |||||
addParam(createParam<CKSSThree>(mm2px(Vec(5.24619, 46.9153)), module, TSequentialSwitch::CHANNELS_PARAM, 0.0f, 2.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(mm2px(Vec(3.51398, 17.694)), module, TSequentialSwitch::CLOCK_INPUT)); | addInput(createInput<PJ301MPort>(mm2px(Vec(3.51398, 17.694)), module, TSequentialSwitch::CLOCK_INPUT)); | ||||
addInput(createInput<PJ301MPort>(mm2px(Vec(3.51398, 32.1896)), module, TSequentialSwitch::RESET_INPUT)); | addInput(createInput<PJ301MPort>(mm2px(Vec(3.51398, 32.1896)), module, TSequentialSwitch::RESET_INPUT)); | ||||
@@ -113,7 +113,7 @@ SequentialSwitch2Widget::SequentialSwitch2Widget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(RACK_GRID_WIDTH, 0))); | addChild(createScrew<ScrewSilver>(Vec(RACK_GRID_WIDTH, 0))); | ||||
addChild(createScrew<ScrewSilver>(Vec(RACK_GRID_WIDTH, RACK_GRID_HEIGHT - RACK_GRID_WIDTH))); | addChild(createScrew<ScrewSilver>(Vec(RACK_GRID_WIDTH, RACK_GRID_HEIGHT - RACK_GRID_WIDTH))); | ||||
addParam(createParam<CKSSThree>(mm2px(Vec(5.24619, 46.9153)), module, TSequentialSwitch::CHANNELS_PARAM, 0.0, 2.0, 0.0)); | |||||
addParam(createParam<CKSSThree>(mm2px(Vec(5.24619, 46.9153)), module, TSequentialSwitch::CHANNELS_PARAM, 0.0f, 2.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(mm2px(Vec(3.51398, 17.694)), module, TSequentialSwitch::CLOCK_INPUT)); | addInput(createInput<PJ301MPort>(mm2px(Vec(3.51398, 17.694)), module, TSequentialSwitch::CLOCK_INPUT)); | ||||
addInput(createInput<PJ301MPort>(mm2px(Vec(3.51398, 32.191)), module, TSequentialSwitch::RESET_INPUT)); | addInput(createInput<PJ301MPort>(mm2px(Vec(3.51398, 32.191)), module, TSequentialSwitch::RESET_INPUT)); | ||||
@@ -81,8 +81,8 @@ void Unity::step() { | |||||
outputs[INV1_OUTPUT + 2*i].value = -mix[i]; | outputs[INV1_OUTPUT + 2*i].value = -mix[i]; | ||||
// Lights | // Lights | ||||
VUMeter vuMeter; | VUMeter vuMeter; | ||||
vuMeter.dBInterval = 6.0; | |||||
vuMeter.setValue(mix[i] / 10.0); | |||||
vuMeter.dBInterval = 6.0f; | |||||
vuMeter.setValue(mix[i] / 10.0f); | |||||
for (int j = 0; j < 5; j++) { | for (int j = 0; j < 5; j++) { | ||||
lights[VU1_LIGHT + 5*i + j].setBrightnessSmooth(vuMeter.getBrightness(j)); | lights[VU1_LIGHT + 5*i + j].setBrightnessSmooth(vuMeter.getBrightness(j)); | ||||
} | } | ||||
@@ -100,8 +100,8 @@ UnityWidget::UnityWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x - 30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x - 30, 365))); | ||||
addParam(createParam<CKSS>(mm2px(Vec(12.867, 52.961)), module, Unity::AVG1_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<CKSS>(mm2px(Vec(12.867, 107.006)), module, Unity::AVG2_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<CKSS>(mm2px(Vec(12.867, 52.961)), module, Unity::AVG1_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<CKSS>(mm2px(Vec(12.867, 107.006)), module, Unity::AVG2_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(mm2px(Vec(2.361, 17.144)), module, Unity::IN1_INPUT + 0)); | addInput(createInput<PJ301MPort>(mm2px(Vec(2.361, 17.144)), module, Unity::IN1_INPUT + 0)); | ||||
addInput(createInput<PJ301MPort>(mm2px(Vec(19.907, 17.144)), module, Unity::IN1_INPUT + 1)); | addInput(createInput<PJ301MPort>(mm2px(Vec(19.907, 17.144)), module, Unity::IN1_INPUT + 1)); | ||||
@@ -140,7 +140,7 @@ struct UnityMergeItem : MenuItem { | |||||
unity->merge ^= true; | unity->merge ^= true; | ||||
} | } | ||||
void step() override { | void step() override { | ||||
rightText = (unity->merge) ? "âś”" : ""; | |||||
rightText = CHECKMARK(unity->merge); | |||||
} | } | ||||
}; | }; | ||||
@@ -30,10 +30,10 @@ struct VCA : Module { | |||||
static void stepChannel(Input &in, Param &level, Input &lin, Input &exp, Output &out) { | static void stepChannel(Input &in, Param &level, Input &lin, Input &exp, Output &out) { | ||||
float v = in.value * level.value; | float v = in.value * level.value; | ||||
if (lin.active) | if (lin.active) | ||||
v *= clampf(lin.value / 10.0, 0.0, 1.0); | |||||
const float expBase = 50.0; | |||||
v *= clamp(lin.value / 10.0f, 0.0f, 1.0f); | |||||
const float expBase = 50.0f; | |||||
if (exp.active) | if (exp.active) | ||||
v *= rescalef(powf(expBase, clampf(exp.value / 10.0, 0.0, 1.0)), 1.0, expBase, 0.0, 1.0); | |||||
v *= rescale(powf(expBase, clamp(exp.value / 10.0f, 0.0f, 1.0f)), 1.0f, expBase, 0.0f, 1.0f); | |||||
out.value = v; | out.value = v; | ||||
} | } | ||||
@@ -60,8 +60,8 @@ VCAWidget::VCAWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<RoundBlackKnob>(Vec(27, 57), module, VCA::LEVEL1_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(27, 222), module, VCA::LEVEL2_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(27, 57), module, VCA::LEVEL1_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(27, 222), module, VCA::LEVEL2_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addInput(createInput<PJ301MPort>(Vec(11, 113), module, VCA::EXP1_INPUT)); | addInput(createInput<PJ301MPort>(Vec(11, 113), module, VCA::EXP1_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(54, 113), module, VCA::LIN1_INPUT)); | addInput(createInput<PJ301MPort>(Vec(54, 113), module, VCA::LIN1_INPUT)); | ||||
@@ -39,8 +39,8 @@ inline float clip(float x) { | |||||
} | } | ||||
struct LadderFilter { | struct LadderFilter { | ||||
float cutoff = 1000.0; | |||||
float resonance = 1.0; | |||||
float cutoff = 1000.0f; | |||||
float resonance = 1.0f; | |||||
float state[4] = {}; | float state[4] = {}; | ||||
void calculateDerivatives(float input, float *dstate, const float *state) { | void calculateDerivatives(float input, float *dstate, const float *state) { | ||||
@@ -61,11 +61,11 @@ struct LadderFilter { | |||||
calculateDerivatives(input, deriv1, state); | calculateDerivatives(input, deriv1, state); | ||||
for (int i = 0; i < 4; i++) | for (int i = 0; i < 4; i++) | ||||
tempState[i] = state[i] + 0.5 * dt * deriv1[i]; | |||||
tempState[i] = state[i] + 0.5f * dt * deriv1[i]; | |||||
calculateDerivatives(input, deriv2, tempState); | calculateDerivatives(input, deriv2, tempState); | ||||
for (int i = 0; i < 4; i++) | for (int i = 0; i < 4; i++) | ||||
tempState[i] = state[i] + 0.5 * dt * deriv2[i]; | |||||
tempState[i] = state[i] + 0.5f * dt * deriv2[i]; | |||||
calculateDerivatives(input, deriv3, tempState); | calculateDerivatives(input, deriv3, tempState); | ||||
for (int i = 0; i < 4; i++) | for (int i = 0; i < 4; i++) | ||||
@@ -73,11 +73,11 @@ struct LadderFilter { | |||||
calculateDerivatives(input, deriv4, tempState); | calculateDerivatives(input, deriv4, tempState); | ||||
for (int i = 0; i < 4; i++) | for (int i = 0; i < 4; i++) | ||||
state[i] += (1.0 / 6.0) * dt * (deriv1[i] + 2.0 * deriv2[i] + 2.0 * deriv3[i] + deriv4[i]); | |||||
state[i] += (1.0f / 6.0f) * dt * (deriv1[i] + 2.0f * deriv2[i] + 2.0f * deriv3[i] + deriv4[i]); | |||||
} | } | ||||
void reset() { | void reset() { | ||||
for (int i = 0; i < 4; i++) { | for (int i = 0; i < 4; i++) { | ||||
state[i] = 0.0; | |||||
state[i] = 0.0f; | |||||
} | } | ||||
} | } | ||||
}; | }; | ||||
@@ -116,31 +116,31 @@ struct VCF : Module { | |||||
void VCF::step() { | void VCF::step() { | ||||
float input = inputs[IN_INPUT].value / 5.0; | |||||
float drive = params[DRIVE_PARAM].value + inputs[DRIVE_INPUT].value / 10.0; | |||||
float gain = powf(100.0, drive); | |||||
float input = inputs[IN_INPUT].value / 5.0f; | |||||
float drive = params[DRIVE_PARAM].value + inputs[DRIVE_INPUT].value / 10.0f; | |||||
float gain = powf(100.0f, drive); | |||||
input *= gain; | input *= gain; | ||||
// Add -60dB noise to bootstrap self-oscillation | // Add -60dB noise to bootstrap self-oscillation | ||||
input += 1.0e-6 * (2.0*randomf() - 1.0); | |||||
input += 1e-6f * (2.0f*randomf() - 1.0f); | |||||
// Set resonance | // Set resonance | ||||
float res = params[RES_PARAM].value + inputs[RES_INPUT].value / 5.0; | |||||
res = 5.5 * clampf(res, 0.0, 1.0); | |||||
float res = params[RES_PARAM].value + inputs[RES_INPUT].value / 5.0f; | |||||
res = 5.5f * clamp(res, 0.0f, 1.0f); | |||||
filter.resonance = res; | filter.resonance = res; | ||||
// Set cutoff frequency | // Set cutoff frequency | ||||
float cutoffExp = params[FREQ_PARAM].value + params[FREQ_CV_PARAM].value * inputs[FREQ_INPUT].value / 5.0; | |||||
cutoffExp = clampf(cutoffExp, 0.0, 1.0); | |||||
const float minCutoff = 15.0; | |||||
const float maxCutoff = 8400.0; | |||||
float cutoffExp = params[FREQ_PARAM].value + params[FREQ_CV_PARAM].value * inputs[FREQ_INPUT].value / 5.0f; | |||||
cutoffExp = clamp(cutoffExp, 0.0f, 1.0f); | |||||
const float minCutoff = 15.0f; | |||||
const float maxCutoff = 8400.0f; | |||||
filter.cutoff = minCutoff * powf(maxCutoff / minCutoff, cutoffExp); | filter.cutoff = minCutoff * powf(maxCutoff / minCutoff, cutoffExp); | ||||
// Push a sample to the state filter | // Push a sample to the state filter | ||||
filter.process(input, 1.0/engineGetSampleRate()); | |||||
filter.process(input, 1.0f/engineGetSampleRate()); | |||||
// Set outputs | // Set outputs | ||||
outputs[LPF_OUTPUT].value = 5.0 * filter.state[3]; | |||||
outputs[HPF_OUTPUT].value = 5.0 * (input - filter.state[3]); | |||||
outputs[LPF_OUTPUT].value = 5.0f * filter.state[3]; | |||||
outputs[HPF_OUTPUT].value = 5.0f * (input - filter.state[3]); | |||||
} | } | ||||
@@ -161,11 +161,11 @@ VCFWidget::VCFWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<RoundHugeBlackKnob>(Vec(33, 61), module, VCF::FREQ_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(12, 143), module, VCF::FINE_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(71, 143), module, VCF::RES_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(12, 208), module, VCF::FREQ_CV_PARAM, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(71, 208), module, VCF::DRIVE_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundHugeBlackKnob>(Vec(33, 61), module, VCF::FREQ_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(12, 143), module, VCF::FINE_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(71, 143), module, VCF::RES_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(12, 208), module, VCF::FREQ_CV_PARAM, -1.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(71, 208), module, VCF::DRIVE_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(Vec(10, 276), module, VCF::FREQ_INPUT)); | addInput(createInput<PJ301MPort>(Vec(10, 276), module, VCF::FREQ_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(48, 276), module, VCF::RES_INPUT)); | addInput(createInput<PJ301MPort>(Vec(48, 276), module, VCF::RES_INPUT)); | ||||
@@ -33,10 +33,10 @@ struct VCMixer : Module { | |||||
void VCMixer::step() { | void VCMixer::step() { | ||||
float ch1 = inputs[CH1_INPUT].value * params[CH1_PARAM].value * clampf(inputs[CH1_CV_INPUT].normalize(10.0) / 10.0, 0.0, 1.0); | |||||
float ch2 = inputs[CH2_INPUT].value * params[CH2_PARAM].value * clampf(inputs[CH2_CV_INPUT].normalize(10.0) / 10.0, 0.0, 1.0); | |||||
float ch3 = inputs[CH3_INPUT].value * params[CH3_PARAM].value * clampf(inputs[CH3_CV_INPUT].normalize(10.0) / 10.0, 0.0, 1.0); | |||||
float cv = fmaxf(inputs[MIX_CV_INPUT].normalize(10.0) / 10.0, 0.0); | |||||
float ch1 = inputs[CH1_INPUT].value * params[CH1_PARAM].value * clamp(inputs[CH1_CV_INPUT].normalize(10.0f) / 10.0f, 0.0f, 1.0f); | |||||
float ch2 = inputs[CH2_INPUT].value * params[CH2_PARAM].value * clamp(inputs[CH2_CV_INPUT].normalize(10.0f) / 10.0f, 0.0f, 1.0f); | |||||
float ch3 = inputs[CH3_INPUT].value * params[CH3_PARAM].value * clamp(inputs[CH3_CV_INPUT].normalize(10.0f) / 10.0f, 0.0f, 1.0f); | |||||
float cv = fmaxf(inputs[MIX_CV_INPUT].normalize(10.0f) / 10.0f, 0.0f); | |||||
float mix = (ch1 + ch2 + ch3) * params[MIX_PARAM].value * cv; | float mix = (ch1 + ch2 + ch3) * params[MIX_PARAM].value * cv; | ||||
outputs[CH1_OUTPUT].value = ch1; | outputs[CH1_OUTPUT].value = ch1; | ||||
@@ -63,10 +63,10 @@ VCMixerWidget::VCMixerWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<RoundLargeBlackKnob>(Vec(52, 58), module, VCMixer::MIX_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(57, 139), module, VCMixer::CH1_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(57, 219), module, VCMixer::CH2_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(57, 300), module, VCMixer::CH3_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundLargeBlackKnob>(Vec(52, 58), module, VCMixer::MIX_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(57, 139), module, VCMixer::CH1_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(57, 219), module, VCMixer::CH2_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(57, 300), module, VCMixer::CH3_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(Vec(16, 69), module, VCMixer::MIX_CV_INPUT)); | addInput(createInput<PJ301MPort>(Vec(16, 69), module, VCMixer::MIX_CV_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(22, 129), module, VCMixer::CH1_INPUT)); | addInput(createInput<PJ301MPort>(Vec(22, 129), module, VCMixer::CH1_INPUT)); | ||||
@@ -11,10 +11,10 @@ template <int OVERSAMPLE, int QUALITY> | |||||
struct VoltageControlledOscillator { | struct VoltageControlledOscillator { | ||||
bool analog = false; | bool analog = false; | ||||
bool soft = false; | bool soft = false; | ||||
float lastSyncValue = 0.0; | |||||
float phase = 0.0; | |||||
float lastSyncValue = 0.0f; | |||||
float phase = 0.0f; | |||||
float freq; | float freq; | ||||
float pw = 0.5; | |||||
float pw = 0.5f; | |||||
float pitch; | float pitch; | ||||
bool syncEnabled = false; | bool syncEnabled = false; | ||||
bool syncDirection = false; | bool syncDirection = false; | ||||
@@ -26,7 +26,7 @@ struct VoltageControlledOscillator { | |||||
RCFilter sqrFilter; | RCFilter sqrFilter; | ||||
// For analog detuning effect | // For analog detuning effect | ||||
float pitchSlew = 0.0; | |||||
float pitchSlew = 0.0f; | |||||
int pitchSlewIndex = 0; | int pitchSlewIndex = 0; | ||||
float sinBuffer[OVERSAMPLE] = {}; | float sinBuffer[OVERSAMPLE] = {}; | ||||
@@ -39,7 +39,7 @@ struct VoltageControlledOscillator { | |||||
pitch = pitchKnob; | pitch = pitchKnob; | ||||
if (analog) { | if (analog) { | ||||
// Apply pitch slew | // Apply pitch slew | ||||
const float pitchSlewAmount = 3.0; | |||||
const float pitchSlewAmount = 3.0f; | |||||
pitch += pitchSlew * pitchSlewAmount; | pitch += pitchSlew * pitchSlewAmount; | ||||
} | } | ||||
else { | else { | ||||
@@ -48,34 +48,34 @@ struct VoltageControlledOscillator { | |||||
} | } | ||||
pitch += pitchCv; | pitch += pitchCv; | ||||
// Note C4 | // Note C4 | ||||
freq = 261.626 * powf(2.0, pitch / 12.0); | |||||
freq = 261.626f * powf(2.0f, pitch / 12.0f); | |||||
} | } | ||||
void setPulseWidth(float pulseWidth) { | void setPulseWidth(float pulseWidth) { | ||||
const float pwMin = 0.01; | |||||
pw = clampf(pulseWidth, pwMin, 1.0 - pwMin); | |||||
const float pwMin = 0.01f; | |||||
pw = clamp(pulseWidth, pwMin, 1.0f - pwMin); | |||||
} | } | ||||
void process(float deltaTime, float syncValue) { | void process(float deltaTime, float syncValue) { | ||||
if (analog) { | if (analog) { | ||||
// Adjust pitch slew | // Adjust pitch slew | ||||
if (++pitchSlewIndex > 32) { | if (++pitchSlewIndex > 32) { | ||||
const float pitchSlewTau = 100.0; // Time constant for leaky integrator in seconds | |||||
pitchSlew += (randomNormal() - pitchSlew / pitchSlewTau) / engineGetSampleRate(); | |||||
const float pitchSlewTau = 100.0f; // Time constant for leaky integrator in seconds | |||||
pitchSlew += (randomNormal() - pitchSlew / pitchSlewTau) * engineGetSampleTime(); | |||||
pitchSlewIndex = 0; | pitchSlewIndex = 0; | ||||
} | } | ||||
} | } | ||||
// Advance phase | // Advance phase | ||||
float deltaPhase = clampf(freq * deltaTime, 1e-6, 0.5); | |||||
float deltaPhase = clamp(freq * deltaTime, 1e-6, 0.5f); | |||||
// Detect sync | // Detect sync | ||||
int syncIndex = -1; // Index in the oversample loop where sync occurs [0, OVERSAMPLE) | int syncIndex = -1; // Index in the oversample loop where sync occurs [0, OVERSAMPLE) | ||||
float syncCrossing = 0.0; // Offset that sync occurs [0.0, 1.0) | |||||
float syncCrossing = 0.0f; // Offset that sync occurs [0.0f, 1.0f) | |||||
if (syncEnabled) { | if (syncEnabled) { | ||||
syncValue -= 0.01; | |||||
if (syncValue > 0.0 && lastSyncValue <= 0.0) { | |||||
syncValue -= 0.01f; | |||||
if (syncValue > 0.0f && lastSyncValue <= 0.0f) { | |||||
float deltaSync = syncValue - lastSyncValue; | float deltaSync = syncValue - lastSyncValue; | ||||
syncCrossing = 1.0 - syncValue / deltaSync; | |||||
syncCrossing = 1.0f - syncValue / deltaSync; | |||||
syncCrossing *= OVERSAMPLE; | syncCrossing *= OVERSAMPLE; | ||||
syncIndex = (int)syncCrossing; | syncIndex = (int)syncCrossing; | ||||
syncCrossing -= syncIndex; | syncCrossing -= syncIndex; | ||||
@@ -84,19 +84,19 @@ struct VoltageControlledOscillator { | |||||
} | } | ||||
if (syncDirection) | if (syncDirection) | ||||
deltaPhase *= -1.0; | |||||
deltaPhase *= -1.0f; | |||||
sqrFilter.setCutoff(40.0 * deltaTime); | |||||
sqrFilter.setCutoff(40.0f * deltaTime); | |||||
for (int i = 0; i < OVERSAMPLE; i++) { | for (int i = 0; i < OVERSAMPLE; i++) { | ||||
if (syncIndex == i) { | if (syncIndex == i) { | ||||
if (soft) { | if (soft) { | ||||
syncDirection = !syncDirection; | syncDirection = !syncDirection; | ||||
deltaPhase *= -1.0; | |||||
deltaPhase *= -1.0f; | |||||
} | } | ||||
else { | else { | ||||
// phase = syncCrossing * deltaPhase / OVERSAMPLE; | // phase = syncCrossing * deltaPhase / OVERSAMPLE; | ||||
phase = 0.0; | |||||
phase = 0.0f; | |||||
} | } | ||||
} | } | ||||
@@ -112,7 +112,7 @@ struct VoltageControlledOscillator { | |||||
sinBuffer[i] = sinf(2.f*M_PI * phase); | sinBuffer[i] = sinf(2.f*M_PI * phase); | ||||
} | } | ||||
if (analog) { | if (analog) { | ||||
triBuffer[i] = 1.25f * interpf(triTable, phase * 2047.f); | |||||
triBuffer[i] = 1.25f * interp(triTable, phase * 2047.f); | |||||
} | } | ||||
else { | else { | ||||
if (phase < 0.25f) | if (phase < 0.25f) | ||||
@@ -123,7 +123,7 @@ struct VoltageControlledOscillator { | |||||
triBuffer[i] = -4.f + 4.f * phase; | triBuffer[i] = -4.f + 4.f * phase; | ||||
} | } | ||||
if (analog) { | if (analog) { | ||||
sawBuffer[i] = 1.66f * interpf(sawTable, phase * 2047.f); | |||||
sawBuffer[i] = 1.66f * interp(sawTable, phase * 2047.f); | |||||
} | } | ||||
else { | else { | ||||
if (phase < 0.5f) | if (phase < 0.5f) | ||||
@@ -140,7 +140,7 @@ struct VoltageControlledOscillator { | |||||
// Advance phase | // Advance phase | ||||
phase += deltaPhase / OVERSAMPLE; | phase += deltaPhase / OVERSAMPLE; | ||||
phase = eucmodf(phase, 1.0); | |||||
phase = eucmod(phase, 1.0f); | |||||
} | } | ||||
} | } | ||||
@@ -201,32 +201,32 @@ struct VCO : Module { | |||||
void VCO::step() { | void VCO::step() { | ||||
oscillator.analog = params[MODE_PARAM].value > 0.0; | |||||
oscillator.soft = params[SYNC_PARAM].value <= 0.0; | |||||
oscillator.analog = params[MODE_PARAM].value > 0.0f; | |||||
oscillator.soft = params[SYNC_PARAM].value <= 0.0f; | |||||
float pitchFine = 3.0 * quadraticBipolar(params[FINE_PARAM].value); | |||||
float pitchCv = 12.0 * inputs[PITCH_INPUT].value; | |||||
float pitchFine = 3.0f * quadraticBipolar(params[FINE_PARAM].value); | |||||
float pitchCv = 12.0f * inputs[PITCH_INPUT].value; | |||||
if (inputs[FM_INPUT].active) { | if (inputs[FM_INPUT].active) { | ||||
pitchCv += quadraticBipolar(params[FM_PARAM].value) * 12.0 * inputs[FM_INPUT].value; | |||||
pitchCv += quadraticBipolar(params[FM_PARAM].value) * 12.0f * inputs[FM_INPUT].value; | |||||
} | } | ||||
oscillator.setPitch(params[FREQ_PARAM].value, pitchFine + pitchCv); | oscillator.setPitch(params[FREQ_PARAM].value, pitchFine + pitchCv); | ||||
oscillator.setPulseWidth(params[PW_PARAM].value + params[PWM_PARAM].value * inputs[PW_INPUT].value / 10.0); | |||||
oscillator.setPulseWidth(params[PW_PARAM].value + params[PWM_PARAM].value * inputs[PW_INPUT].value / 10.0f); | |||||
oscillator.syncEnabled = inputs[SYNC_INPUT].active; | oscillator.syncEnabled = inputs[SYNC_INPUT].active; | ||||
oscillator.process(1.0 / engineGetSampleRate(), inputs[SYNC_INPUT].value); | |||||
oscillator.process(engineGetSampleTime(), inputs[SYNC_INPUT].value); | |||||
// Set output | // Set output | ||||
if (outputs[SIN_OUTPUT].active) | if (outputs[SIN_OUTPUT].active) | ||||
outputs[SIN_OUTPUT].value = 5.0 * oscillator.sin(); | |||||
outputs[SIN_OUTPUT].value = 5.0f * oscillator.sin(); | |||||
if (outputs[TRI_OUTPUT].active) | if (outputs[TRI_OUTPUT].active) | ||||
outputs[TRI_OUTPUT].value = 5.0 * oscillator.tri(); | |||||
outputs[TRI_OUTPUT].value = 5.0f * oscillator.tri(); | |||||
if (outputs[SAW_OUTPUT].active) | if (outputs[SAW_OUTPUT].active) | ||||
outputs[SAW_OUTPUT].value = 5.0 * oscillator.saw(); | |||||
outputs[SAW_OUTPUT].value = 5.0f * oscillator.saw(); | |||||
if (outputs[SQR_OUTPUT].active) | if (outputs[SQR_OUTPUT].active) | ||||
outputs[SQR_OUTPUT].value = 5.0 * oscillator.sqr(); | |||||
outputs[SQR_OUTPUT].value = 5.0f * oscillator.sqr(); | |||||
lights[PHASE_POS_LIGHT].setBrightnessSmooth(fmaxf(0.0, oscillator.light())); | |||||
lights[PHASE_NEG_LIGHT].setBrightnessSmooth(fmaxf(0.0, -oscillator.light())); | |||||
lights[PHASE_POS_LIGHT].setBrightnessSmooth(fmaxf(0.0f, oscillator.light())); | |||||
lights[PHASE_NEG_LIGHT].setBrightnessSmooth(fmaxf(0.0f, -oscillator.light())); | |||||
} | } | ||||
@@ -247,14 +247,14 @@ VCOWidget::VCOWidget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<CKSS>(Vec(15, 77), module, VCO::MODE_PARAM, 0.0, 1.0, 1.0)); | |||||
addParam(createParam<CKSS>(Vec(119, 77), module, VCO::SYNC_PARAM, 0.0, 1.0, 1.0)); | |||||
addParam(createParam<CKSS>(Vec(15, 77), module, VCO::MODE_PARAM, 0.0f, 1.0f, 1.0f)); | |||||
addParam(createParam<CKSS>(Vec(119, 77), module, VCO::SYNC_PARAM, 0.0f, 1.0f, 1.0f)); | |||||
addParam(createParam<RoundHugeBlackKnob>(Vec(47, 61), module, VCO::FREQ_PARAM, -54.0, 54.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(23, 143), module, VCO::FINE_PARAM, -1.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(91, 143), module, VCO::PW_PARAM, 0.0, 1.0, 0.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(23, 208), module, VCO::FM_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(91, 208), module, VCO::PWM_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundHugeBlackKnob>(Vec(47, 61), module, VCO::FREQ_PARAM, -54.0f, 54.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(23, 143), module, VCO::FINE_PARAM, -1.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(91, 143), module, VCO::PW_PARAM, 0.0f, 1.0f, 0.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(23, 208), module, VCO::FM_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(91, 208), module, VCO::PWM_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(Vec(11, 276), module, VCO::PITCH_INPUT)); | addInput(createInput<PJ301MPort>(Vec(11, 276), module, VCO::PITCH_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(45, 276), module, VCO::FM_INPUT)); | addInput(createInput<PJ301MPort>(Vec(45, 276), module, VCO::FM_INPUT)); | ||||
@@ -266,7 +266,7 @@ VCOWidget::VCOWidget() { | |||||
addOutput(createOutput<PJ301MPort>(Vec(80, 320), module, VCO::SAW_OUTPUT)); | addOutput(createOutput<PJ301MPort>(Vec(80, 320), module, VCO::SAW_OUTPUT)); | ||||
addOutput(createOutput<PJ301MPort>(Vec(114, 320), module, VCO::SQR_OUTPUT)); | addOutput(createOutput<PJ301MPort>(Vec(114, 320), module, VCO::SQR_OUTPUT)); | ||||
addChild(createLight<SmallLight<GreenRedLight>>(Vec(99, 42.5), module, VCO::PHASE_POS_LIGHT)); | |||||
addChild(createLight<SmallLight<GreenRedLight>>(Vec(99, 42.5f), module, VCO::PHASE_POS_LIGHT)); | |||||
} | } | ||||
@@ -303,28 +303,28 @@ struct VCO2 : Module { | |||||
void VCO2::step() { | void VCO2::step() { | ||||
oscillator.analog = params[MODE_PARAM].value > 0.0; | |||||
oscillator.soft = params[SYNC_PARAM].value <= 0.0; | |||||
oscillator.analog = params[MODE_PARAM].value > 0.0f; | |||||
oscillator.soft = params[SYNC_PARAM].value <= 0.0f; | |||||
float pitchCv = params[FREQ_PARAM].value + quadraticBipolar(params[FM_PARAM].value) * 12.0 * inputs[FM_INPUT].value; | |||||
oscillator.setPitch(0.0, pitchCv); | |||||
float pitchCv = params[FREQ_PARAM].value + quadraticBipolar(params[FM_PARAM].value) * 12.0f * inputs[FM_INPUT].value; | |||||
oscillator.setPitch(0.0f, pitchCv); | |||||
oscillator.syncEnabled = inputs[SYNC_INPUT].active; | oscillator.syncEnabled = inputs[SYNC_INPUT].active; | ||||
oscillator.process(1.0 / engineGetSampleRate(), inputs[SYNC_INPUT].value); | |||||
oscillator.process(engineGetSampleTime(), inputs[SYNC_INPUT].value); | |||||
// Set output | // Set output | ||||
float wave = clampf(params[WAVE_PARAM].value + inputs[WAVE_INPUT].value, 0.0, 3.0); | |||||
float wave = clamp(params[WAVE_PARAM].value + inputs[WAVE_INPUT].value, 0.0f, 3.0f); | |||||
float out; | float out; | ||||
if (wave < 1.0) | |||||
out = crossf(oscillator.sin(), oscillator.tri(), wave); | |||||
else if (wave < 2.0) | |||||
out = crossf(oscillator.tri(), oscillator.saw(), wave - 1.0); | |||||
if (wave < 1.0f) | |||||
out = crossfade(oscillator.sin(), oscillator.tri(), wave); | |||||
else if (wave < 2.0f) | |||||
out = crossfade(oscillator.tri(), oscillator.saw(), wave - 1.0f); | |||||
else | else | ||||
out = crossf(oscillator.saw(), oscillator.sqr(), wave - 2.0); | |||||
outputs[OUT_OUTPUT].value = 5.0 * out; | |||||
out = crossfade(oscillator.saw(), oscillator.sqr(), wave - 2.0f); | |||||
outputs[OUT_OUTPUT].value = 5.0f * out; | |||||
lights[PHASE_POS_LIGHT].setBrightnessSmooth(fmaxf(0.0, oscillator.light())); | |||||
lights[PHASE_NEG_LIGHT].setBrightnessSmooth(fmaxf(0.0, -oscillator.light())); | |||||
lights[PHASE_POS_LIGHT].setBrightnessSmooth(fmaxf(0.0f, oscillator.light())); | |||||
lights[PHASE_NEG_LIGHT].setBrightnessSmooth(fmaxf(0.0f, -oscillator.light())); | |||||
} | } | ||||
@@ -345,12 +345,12 @@ VCO2Widget::VCO2Widget() { | |||||
addChild(createScrew<ScrewSilver>(Vec(15, 365))); | addChild(createScrew<ScrewSilver>(Vec(15, 365))); | ||||
addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | addChild(createScrew<ScrewSilver>(Vec(box.size.x-30, 365))); | ||||
addParam(createParam<CKSS>(Vec(62, 150), module, VCO2::MODE_PARAM, 0.0, 1.0, 1.0)); | |||||
addParam(createParam<CKSS>(Vec(62, 215), module, VCO2::SYNC_PARAM, 0.0, 1.0, 1.0)); | |||||
addParam(createParam<CKSS>(Vec(62, 150), module, VCO2::MODE_PARAM, 0.0f, 1.0f, 1.0f)); | |||||
addParam(createParam<CKSS>(Vec(62, 215), module, VCO2::SYNC_PARAM, 0.0f, 1.0f, 1.0f)); | |||||
addParam(createParam<RoundHugeBlackKnob>(Vec(17, 60), module, VCO2::FREQ_PARAM, -54.0, 54.0, 0.0)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(12, 143), module, VCO2::WAVE_PARAM, 0.0, 3.0, 1.5)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(12, 208), module, VCO2::FM_PARAM, 0.0, 1.0, 0.0)); | |||||
addParam(createParam<RoundHugeBlackKnob>(Vec(17, 60), module, VCO2::FREQ_PARAM, -54.0f, 54.0f, 0.0f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(12, 143), module, VCO2::WAVE_PARAM, 0.0f, 3.0f, 1.5f)); | |||||
addParam(createParam<RoundBlackKnob>(Vec(12, 208), module, VCO2::FM_PARAM, 0.0f, 1.0f, 0.0f)); | |||||
addInput(createInput<PJ301MPort>(Vec(11, 276), module, VCO2::FM_INPUT)); | addInput(createInput<PJ301MPort>(Vec(11, 276), module, VCO2::FM_INPUT)); | ||||
addInput(createInput<PJ301MPort>(Vec(54, 276), module, VCO2::SYNC_INPUT)); | addInput(createInput<PJ301MPort>(Vec(54, 276), module, VCO2::SYNC_INPUT)); | ||||
@@ -358,7 +358,7 @@ VCO2Widget::VCO2Widget() { | |||||
addOutput(createOutput<PJ301MPort>(Vec(54, 320), module, VCO2::OUT_OUTPUT)); | addOutput(createOutput<PJ301MPort>(Vec(54, 320), module, VCO2::OUT_OUTPUT)); | ||||
addChild(createLight<SmallLight<GreenRedLight>>(Vec(68, 42.5), module, VCO2::PHASE_POS_LIGHT)); | |||||
addChild(createLight<SmallLight<GreenRedLight>>(Vec(68, 42.5f), module, VCO2::PHASE_POS_LIGHT)); | |||||
} | } | ||||