Files
WS-1.0-Firmwares/InputsTest/InputsTest.ino
2025-10-04 23:19:54 +03:00

133 lines
3.7 KiB
C++

//Hardware Definitions
#define Knob1 A6 //Intensity
#define Knob2 A4 //Modulation Frequency
#define Knob3 A2 //Harmonics
#define Knob4 A0
#define KnobA A5
#define KnobDR A3
#define KnobS A1
#define CVIn A7
#define GateIn 10
#define EnvSwitch 11
#define DroneSwitch 12
#define LED 5
// smoothing for intensity to remove clicks on transitions
float smoothness = 0.95f;
Smooth <long> aSmoothIntensity(smoothness);
int carrierFreq = 440;
int mod_ratio = 5; // brightness (harmonics)
long fm_intensity; // carries control info from updateControl to updateAudio
void MIDINoteOn(byte channel, byte note, byte velocity) {
carrierFreq = mtof((int) note);
envelope.noteOn();
MIDINotePlaying = true;
digitalWrite(LED, LOW);
}
void MIDINoteOff(byte channel, byte note, byte velocity) {
envelope.noteOff();
//MIDINotePlaying = false;
digitalWrite(LED, HIGH);
}
void setup(){
//pinMode(LED_BUILTIN_TX,INPUT); //switch rx and tx leds of, so they don't blink on midi
//pinMode(LED_BUILTIN_RX,INPUT);
pinMode(LED, OUTPUT);
pinMode(GateIn, INPUT_PULLUP);
pinMode(EnvSwitch, INPUT_PULLUP);
pinMode(DroneSwitch, INPUT_PULLUP);
MIDI.setHandleNoteOn(MIDINoteOn);
MIDI.setHandleNoteOff(MIDINoteOff);
MIDI.begin(MIDI_CHANNEL);
startMozzi();
digitalWrite(LED, HIGH);
}
void updateControl(){
//Get Control Values
int CVInVal = mozziAnalogRead(CVIn);
int knob1Val = mozziAnalogRead(Knob1);
int knob2Val = mozziAnalogRead(Knob2);
int knob3Val = mozziAnalogRead(Knob3);
int knob4Val = mozziAnalogRead(Knob4);
int knobAVal = mozziAnalogRead(KnobA);
int knobDRVal = mozziAnalogRead(KnobDR);
int knobSVal = mozziAnalogRead(KnobS);
bool droneSwitchVal = digitalRead(DroneSwitch);
bool envSwitchVal = digitalRead(EnvSwitch);
bool gateInVal = !digitalRead(GateIn);
//Remap the Values
if (!MIDINotePlaying) {
carrierFreq = kMapCarrierFreq(CVInVal); //Pitch
if (gateInVal && !gateIsHigh) {
gateIsHigh = true;
envelope.noteOn();
} else if (!gateInVal && gateIsHigh) {
gateIsHigh = false;
envelope.noteOff();
}
} else if (MIDINotePlaying && !envelope.playing()) { //
MIDINotePlaying = false;
}
int intensity = kMapIntensity(knob1Val);
float modSpeed = (float)kMapModSpeed(knob2Val)/1000; //float for lower frequencies
int harmonics = kMapHarmonics(knob3Val);
int knob4Map = 1;//mapThisToo(knob4Val);
//Update Envelope Settings
int attackTime = kMapAttack(knobAVal);
int decayReleaseTime = kMapDecayRelease(knobDRVal);
int sustainLevel = kMapSustain(knobSVal);
envelope.setDecayLevel(sustainLevel); //Should be enough
//envelope.setSustainLevel(sustainLevel); //but with this, just in case
envelope.setTimes(attackTime, decayReleaseTime, 30000, decayReleaseTime); //30000 is so the note will sustain 30 seconds unless a noteOff comes
//envelope.setDecayLevel(100);
//envelope.setSustainLevel(100);
//envelope.setTimes(150, 300, 10000, 300); //10000 is so the note will sustain 10 seconds unless a noteOff comes
//calculate the modulation frequency to stay in ratio
int modFreq = carrierFreq * mod_ratio * harmonics;
// set the FM oscillator frequencies
aCarrier.setFreq(carrierFreq);
aModulator.setFreq(modFreq);
// calculate the fm_intensity
fm_intensity = ((long)intensity * knob4Map * (kIntensityMod.next()+128))>>8; // shift back to range after 8 bit multiply
kIntensityMod.setFreq(modSpeed);
MIDI.read();
digitalWrite(LED, !gateInVal);
envelope.update();
if(!droneSwitchVal) {
gain = envelope.next();
} else {
gain = 255;
}
}
AudioOutput updateAudio(){
long modulation = aSmoothIntensity.next(fm_intensity) * aModulator.next();
return MonoOutput::from16Bit((int) gain * aCarrier.phMod(modulation));
}
void loop(){
audioHook();
}