Full support for VCO droplet resizing

This commit is contained in:
Christian Colglazier 2020-09-27 17:16:49 -04:00
parent 4292ede452
commit 50a0281a5a
3 changed files with 88 additions and 30 deletions

View File

@ -8,53 +8,82 @@ VCODroplet::VCODroplet(DaisyPatch* m_patch,
int num_waves = Oscillator::WAVE_LAST; int num_waves = Oscillator::WAVE_LAST;
SetAnimationRate(10); SetAnimationRate(10);
osc.Init(sample_rate); osc.Init(sample_rate);
freqctrl.Init(Patch()->controls[Patch()->CTRL_1], 10.0,
110.0f, Parameter::LINEAR); wave = Oscillator::WAVE_SAW;
finectrl.Init(Patch()->controls[Patch()->CTRL_2], 0.f,
7.f, Parameter::LINEAR); DaisyPatch::Ctrl freq, fine;
switch (GetState()){
default:
case DropletState::kFull:
wavectrl.Init(Patch()->controls[Patch()->CTRL_3], 0.0, wavectrl.Init(Patch()->controls[Patch()->CTRL_3], 0.0,
num_waves, Parameter::LINEAR); num_waves, Parameter::LINEAR);
ampctrl.Init(Patch()->controls[Patch()->CTRL_4], 0.0, ampctrl.Init(Patch()->controls[Patch()->CTRL_4], 0.0,
0.5f, Parameter::LINEAR); 0.5f, Parameter::LINEAR);
freq = Patch()->CTRL_1;
fine = Patch()->CTRL_2;
SetWaveShape(wavectrl.Process());
break;
case DropletState::kLeft:
freq = Patch()->CTRL_1;
fine = Patch()->CTRL_2;
break;
case DropletState::kRight:
freq = Patch()->CTRL_3;
fine = Patch()->CTRL_4;
break;
}
freqctrl.Init(Patch()->controls[freq], 10.0,
110.0f, Parameter::LINEAR);
finectrl.Init(Patch()->controls[fine], 0.f,
7.f, Parameter::LINEAR);
} }
VCODroplet::~VCODroplet() { VCODroplet::~VCODroplet() {
delete wave; delete wave_graphic;
} }
void VCODroplet::Control() {} void VCODroplet::Control() {
Patch()->UpdateAnalogControls();
Patch()->DebounceControls();
AdjustWaveShape(Patch()->encoder.Increment());
}
void VCODroplet::Process(float** in, float** out, size_t size) { void VCODroplet::Process(float** in, float** out, size_t size) {
float sig, freq, amp; float sig, freq, amp = 1.0;
size_t wave;
Patch()->UpdateAnalogControls(); Patch()->UpdateAnalogControls();
for (size_t i = 0; i < size; i += 2) { for (size_t i = 0; i < size; i += 2) {
// Read Knobs // Read Knobs
freq = mtof(freqctrl.Process() + finectrl.Process()); freq = mtof(freqctrl.Process() + finectrl.Process());
wave = wavectrl.Process(); if (GetState() == DropletState::kFull) {
if((size_t) wavectrl.Process() != last_wave_ctrl) {
AdjustWaveShape((size_t)wavectrl.Process()-last_wave_ctrl);
last_wave_ctrl = wavectrl.Process();
}
amp = ampctrl.Process(); amp = ampctrl.Process();
}
// Set osc params // Set osc params
osc.SetFreq(freq); osc.SetFreq(freq);
osc.SetWaveform(wave); osc.SetWaveform(wave);
osc.SetAmp(amp); osc.SetAmp(amp);
// Process // Process
sig = osc.Process(); sig = osc.Process();
// Assign Synthesized Waveform to all four outputs. // Assign Synthesized Waveform to outputs.
for (size_t chn = 0; chn < 4; chn++) { for (size_t chn = GetChannelMin(); chn < GetChannelMax(); chn++) {
out[chn][i] = sig; out[chn][i] = sig;
} }
} }
} }
void VCODroplet::Draw() { void VCODroplet::Draw() {
SetWaveState(wave);
if (GetState() == DropletState::kFull) { if (GetState() == DropletState::kFull) {
WriteCenteredString(*Patch(), WriteCenteredString(*Patch(),
(GetScreenMax()-GetScreenMin())/2, (GetScreenMax()-GetScreenMin())/2,
54, 54,
Font_6x8, Font_6x8,
WaveToString(wavectrl.Process())); WaveToString(wave));
} else { } else {
WriteDoubleCentered(*Patch(), WriteDoubleCentered(*Patch(),
GetScreenMin() + GetScreenMin() +
@ -62,16 +91,15 @@ void VCODroplet::Draw() {
54, 54,
GetScreenMax()-GetScreenMin(), GetScreenMax()-GetScreenMin(),
Font_6x8, Font_6x8,
WaveToString(wavectrl.Process())); WaveToString(wave));
} }
SetWaveState(wavectrl.Process()); wave_graphic->DrawTile(*Patch(),
wave->DrawTile(*Patch(),
GetScreenMin(), GetScreenMin(),
0, 0,
GetScreenMax(), GetScreenMax(),
GetTitleHeight()); GetTitleHeight());
if(NeedUpdate()) { if(NeedUpdate()) {
wave->AdjustXShift(1); wave_graphic->AdjustXShift(1);
} }
DrawName("VCO"); DrawName("VCO");
AnimationInc(); AnimationInc();
@ -102,29 +130,39 @@ std::string VCODroplet::WaveToString(uint8_t wf) {
void VCODroplet::SetWaveState(uint8_t wf) { void VCODroplet::SetWaveState(uint8_t wf) {
switch(wf){ switch(wf){
case Oscillator::WAVE_TRI: case Oscillator::WAVE_TRI:
wave->SetWaveShape(WaveShape::kTriangle); wave_graphic->SetWaveShape(WaveShape::kTriangle);
return; return;
case Oscillator::WAVE_SQUARE: case Oscillator::WAVE_SQUARE:
wave->SetWaveShape(WaveShape::kSquare); wave_graphic->SetWaveShape(WaveShape::kSquare);
return; return;
case Oscillator::WAVE_SIN: case Oscillator::WAVE_SIN:
wave->SetWaveShape(WaveShape::kSine); wave_graphic->SetWaveShape(WaveShape::kSine);
return; return;
case Oscillator::WAVE_SAW: case Oscillator::WAVE_SAW:
wave->SetWaveShape(WaveShape::kSaw); wave_graphic->SetWaveShape(WaveShape::kSaw);
return; return;
case Oscillator::WAVE_RAMP: case Oscillator::WAVE_RAMP:
wave->SetWaveShape(WaveShape::kRamp); wave_graphic->SetWaveShape(WaveShape::kRamp);
return; return;
case Oscillator::WAVE_POLYBLEP_TRI: case Oscillator::WAVE_POLYBLEP_TRI:
wave->SetWaveShape(WaveShape::kTriangle); wave_graphic->SetWaveShape(WaveShape::kTriangle);
return; return;
case Oscillator::WAVE_POLYBLEP_SQUARE: case Oscillator::WAVE_POLYBLEP_SQUARE:
wave->SetWaveShape(WaveShape::kSquare); wave_graphic->SetWaveShape(WaveShape::kSquare);
return; return;
default: default:
case Oscillator::WAVE_POLYBLEP_SAW: case Oscillator::WAVE_POLYBLEP_SAW:
wave->SetWaveShape(WaveShape::kSaw); wave_graphic->SetWaveShape(WaveShape::kSaw);
return; return;
} }
} }
void VCODroplet::AdjustWaveShape(int amount) {
wave = (Oscillator::WAVE_LAST + wave + amount) %
Oscillator::WAVE_LAST;
}
void VCODroplet::SetWaveShape(int ws) {
wave = ws % Oscillator::WAVE_LAST;
last_wave_ctrl = ws;
}

View File

@ -19,8 +19,10 @@ class VCODroplet: public Droplet {
private: private:
Oscillator osc; Oscillator osc;
Parameter freqctrl, wavectrl, ampctrl, finectrl; Parameter freqctrl, wavectrl, ampctrl, finectrl;
size_t wave;
size_t last_wave_ctrl;
const double pi = std::acos(-1); const double pi = std::acos(-1);
Wave* wave = new Wave(WaveShape::kTriangle, 21, GetTitleHeight()); Wave* wave_graphic = new Wave(WaveShape::kTriangle, 21, GetTitleHeight());
/* /*
* Converts oscilator to name of wave shape. * Converts oscilator to name of wave shape.
@ -73,6 +75,20 @@ public:
* Processes information to be shown on the display. * Processes information to be shown on the display.
*/ */
void Draw(); void Draw();
/*
* Changes the wave shape of the VCO.
*
* @param amount wave shape table position adjustment
*/
void AdjustWaveShape(int amount);
/*
* Sets the wave shape of the VCO.
*
* @param ws wave shape
*/
void SetWaveShape(int ws);
}; };
#endif // CASCADE_DROPLETS_VCO_DROPLET_H_ #endif // CASCADE_DROPLETS_VCO_DROPLET_H_

View File

@ -36,7 +36,11 @@ void ProcessControls() {
} }
} }
void ProcessOutputs() {} void ProcessOutputs() {
if(!menu.InMenu()) {
droplet->Control();
}
}
void ProcessOled() { void ProcessOled() {
patch.display.Fill(false); patch.display.Fill(false);
@ -58,7 +62,7 @@ Droplet* GetDroplet() {
switch(menu.GetState()) { switch(menu.GetState()) {
case MenuState::kVCO: case MenuState::kVCO:
return new VCODroplet(&patch, return new VCODroplet(&patch,
DropletState::kRight, DropletState::kFull,
sample_rate); sample_rate);
case MenuState::kNoise: case MenuState::kNoise:
default: default: