Added ICM, knob CCs
This commit is contained in:
parent
e757ebc885
commit
00cdfc08e0
7 changed files with 125 additions and 46 deletions
|
@ -104,6 +104,9 @@ struct instrument_state_t {
|
|||
byte leverVal = 0; // keep track and make sure we send CC with 0 value when off threshold
|
||||
int pitchBend = 8192;
|
||||
int pbSend = 8192; // Pitch bend actually sent, modified by vibrato, etc
|
||||
byte knobVals[4];
|
||||
byte rollCCVal = 0;
|
||||
byte tiltCCVal = 0;
|
||||
|
||||
// Key states
|
||||
byte quarterToneTrigger;
|
||||
|
|
|
@ -44,6 +44,7 @@ void initHardware() {
|
|||
breathFilter.setFilter(LOWPASS, FILTER_FREQ, 0.0); // create a one pole (RC) lowpass filter
|
||||
breathAltFilter.setFilter(LOWPASS, FILTER_FREQ, 0.0); // create a one pole (RC) lowpass filter
|
||||
spikeFilter.setFilter(HIGHPASS, 200, 0.0); // create a one pole (RC) lowpass filter
|
||||
icmSensor.begin_I2C(ICM20948_I2CADDR_DEFAULT, &MainI2CBus);
|
||||
|
||||
ledStrip.begin();
|
||||
|
||||
|
@ -168,4 +169,17 @@ int readPressure() {
|
|||
|
||||
int readAltPressure() {
|
||||
return breathAltFilter.input(pressureSensorAlt.readPressure()) * PRESSURE_SENS_MULTIPLIER;
|
||||
}
|
||||
|
||||
icm_result_t readICM() {
|
||||
sensors_event_t accel;
|
||||
sensors_event_t gyro;
|
||||
sensors_event_t mag;
|
||||
sensors_event_t temp;
|
||||
icmSensor.getEvent(&accel, &gyro, &temp, &mag);
|
||||
|
||||
return {
|
||||
mag.magnetic.y,
|
||||
mag.magnetic.x,
|
||||
};
|
||||
}
|
|
@ -16,6 +16,11 @@ extern WS2812Serial ledStrip;
|
|||
extern Adafruit_Sensor *accelSensor;
|
||||
extern Adafruit_ICM20948 icmSensor;
|
||||
|
||||
struct icm_result_t {
|
||||
float tilt;
|
||||
float roll;
|
||||
};
|
||||
|
||||
void initHardware();
|
||||
void updateFilters(preset_t &preset);
|
||||
bool checkButtonState(uint8_t mask); // return true if the given buttons are pressed
|
||||
|
@ -28,6 +33,7 @@ uint16_t utilTouched();
|
|||
int readPressure();
|
||||
int readAltPressure();
|
||||
int readSpikePressure();
|
||||
icm_result_t readICM();
|
||||
|
||||
// xEVI hardware setup
|
||||
|
||||
|
|
|
@ -778,9 +778,7 @@ private:
|
|||
|
||||
class StatusMenu : public MenuScreen {
|
||||
public:
|
||||
StatusMenu(MenuScreen& mainMenu) : _mainMenu(mainMenu) {
|
||||
Serial.println("init statusmenu");
|
||||
}
|
||||
StatusMenu(MenuScreen& mainMenu) : _mainMenu(mainMenu) { }
|
||||
void update(state_t& state, InputState& input, bool redraw) {
|
||||
InputState nullinput;
|
||||
if (input.changed && input.btnMenu) {
|
||||
|
@ -1005,13 +1003,14 @@ ChoiceMenu<4, PortamentoMode> portMenu("GLIDE MOD", &preset_t::portamentoMode, {
|
|||
});
|
||||
PresetValueMenu<0, uint8_t> portLimitMenu("GLIDE LMT", &preset_t::portamentoLimit, 1, 127, true);
|
||||
PresetValueMenu<0, uint8_t> pitchBendMenu("PITCHBEND", &preset_t::PBdepth, 0, 12, true);
|
||||
ChoiceMenu<4, ExtraControl> extraCtlMenu("EXT CTL", &preset_t::extraControl, { {OFF, VIBRATO, GLIDE, CC} }, {
|
||||
"OFF",
|
||||
"VIBRATO",
|
||||
"GLIDE",
|
||||
"CC"
|
||||
});
|
||||
ChoiceMenu<4, ExtraControl> extraCtlMenu("EXT CTL", &preset_t::extraControl, { {OFF, VIBRATO, GLIDE, CC} }, { "OFF", "VIBRATO", "GLIDE", "CC" });
|
||||
PresetValueMenu<128, uint8_t> extraCCMenu("EXT CC", &preset_t::extraCC, 0, 127, true, CC_NAMES);
|
||||
ChoiceMenu<4, ExtraControl> tiltModeMenu("TILT MODE", &preset_t::icmTiltMode, { {OFF, VIBRATO, GLIDE, CC} }, { "OFF", "VIBRATO", "GLIDE", "CC" });
|
||||
PresetValueMenu<128, uint8_t> tiltCCMenu("TILT CC", &preset_t::icmTiltCC, 0, 127, true, CC_NAMES);
|
||||
ChoiceMenu<4, ExtraControl> rollModeMenu("ROLL MODE", &preset_t::icmRollMode, { {OFF, VIBRATO, GLIDE, CC} }, { "OFF", "VIBRATO", "GLIDE", "CC" });
|
||||
PresetValueMenu<128, uint8_t> rollCCMenu("ROLL CC", &preset_t::icmRollCC, 0, 127, true, CC_NAMES);
|
||||
ChoiceMenu<4, ExtraControl> accelModeMenu("ACCEL MODE", &preset_t::icmAccelMode, { {OFF, VIBRATO, GLIDE, CC} }, { "OFF", "VIBRATO", "GLIDE", "CC" });
|
||||
PresetValueMenu<128, uint8_t> accelCCMenu("ACCEL CC", &preset_t::icmAccelCC, 0, 127, true, CC_NAMES);
|
||||
PresetValueMenu<1, uint8_t> deglitchMenu("DEGLITCH", &preset_t::deglitch, 0, 70, true, { "OFF" }, "ms");
|
||||
PresetValueMenu<29, uint8_t> pinkyMenu("PINKY KEY", &preset_t::pinkySetting, 0, 29, true, {
|
||||
"-12", "-11", "-10", "-9", "-8", "-7", "-6", "-5", "-4", "-3", "-2", "-1",
|
||||
|
@ -1065,7 +1064,7 @@ std::array<MenuScreen *const, 11> breathMenuEntries = {
|
|||
};
|
||||
SubMenu<11> breathMenu("BR SETUP", breathMenuEntries);
|
||||
|
||||
const std::array<MenuScreen *const, 13> controlMenuEntries = {
|
||||
const std::array<MenuScreen *const, 19> controlMenuEntries = {
|
||||
&fingeringMenu,
|
||||
&rollerMenu,
|
||||
&biteCtlMenu,
|
||||
|
@ -1078,9 +1077,15 @@ const std::array<MenuScreen *const, 13> controlMenuEntries = {
|
|||
&portLimitMenu,
|
||||
°litchMenu,
|
||||
&pinkyMenu,
|
||||
&pitchBendMenu
|
||||
&pitchBendMenu,
|
||||
&tiltModeMenu,
|
||||
&tiltCCMenu,
|
||||
&rollModeMenu,
|
||||
&rollCCMenu,
|
||||
&accelModeMenu,
|
||||
&accelCCMenu,
|
||||
};
|
||||
SubMenu<13> controlMenu("CTL SETUP", controlMenuEntries);
|
||||
SubMenu<19> controlMenu("CTL SETUP", controlMenuEntries);
|
||||
|
||||
const std::array<MenuScreen *const, 5> vibratoMenuEntries = {
|
||||
&vibDepthMenu,
|
||||
|
@ -1225,6 +1230,10 @@ void initDisplay() {
|
|||
currentMenu = &statusMenu;
|
||||
}
|
||||
|
||||
bool inMenu() {
|
||||
return currentMenu != &statusMenu;
|
||||
}
|
||||
|
||||
void handleMenu(state_t& state, bool draw) {
|
||||
unsigned long timeNow = millis();
|
||||
bool wakeUp = false;
|
||||
|
|
|
@ -38,6 +38,7 @@ class MenuScreen {
|
|||
};
|
||||
|
||||
void initDisplay();
|
||||
bool inMenu();
|
||||
void displayOff(state_t &state);
|
||||
void showVersion();
|
||||
void displayError(const char *error);
|
||||
|
|
|
@ -83,12 +83,12 @@ struct preset_t {
|
|||
uint8_t knob3CC = 73;
|
||||
uint8_t knob4CC = 74;
|
||||
|
||||
uint8_t icmAccelMode;
|
||||
uint8_t icmAccelCC;
|
||||
uint8_t icmTiltMode;
|
||||
uint8_t icmTiltCC;
|
||||
uint8_t icmRotationMode;
|
||||
uint8_t icmRotationCC;
|
||||
ExtraControl icmAccelMode = ExtraControl::CC;
|
||||
uint8_t icmAccelCC = 75;
|
||||
ExtraControl icmTiltMode = ExtraControl::CC;
|
||||
uint8_t icmTiltCC = 76;
|
||||
ExtraControl icmRollMode = ExtraControl::CC;
|
||||
uint8_t icmRollCC = 77;
|
||||
|
||||
uint8_t breathFilterFreq = 20;
|
||||
uint8_t spikeFilterFreq = 20;
|
||||
|
|
|
@ -231,17 +231,17 @@ int breath() {
|
|||
// send midi cc
|
||||
midiSendControlChange(state.currentPreset->breathCC, breathCCval);
|
||||
}
|
||||
if (state.currentPreset->breathMode == BreathMode::BREATH_AT
|
||||
|| state.currentPreset->breathMode == BreathMode::BREATH_LSB_AT
|
||||
|| state.currentPreset->breathMode == BreathMode::BREATH_ACC_AT) {
|
||||
if (state.currentPreset->breathMode == BreathMode::BREATH_AT
|
||||
|| state.currentPreset->breathMode == BreathMode::BREATH_LSB_AT
|
||||
|| state.currentPreset->breathMode == BreathMode::BREATH_ACC_AT) {
|
||||
// send aftertouch
|
||||
midiSendAfterTouch(breathCCval);
|
||||
}
|
||||
oldbreath = breathCCval;
|
||||
}
|
||||
|
||||
if (breathCCvalHires != oldbreathhires
|
||||
&& (state.currentPreset->breathMode == BreathMode::BREATH_LSB || state.currentPreset->breathMode == BreathMode::BREATH_LSB_AT)) {
|
||||
if (breathCCvalHires != oldbreathhires
|
||||
&& (state.currentPreset->breathMode == BreathMode::BREATH_LSB || state.currentPreset->breathMode == BreathMode::BREATH_LSB_AT)) {
|
||||
midiSendControlChange(state.currentPreset->breathCC + 32, breathCCvalFine);
|
||||
}
|
||||
|
||||
|
@ -299,13 +299,13 @@ void pitch_bend() {
|
|||
if (ExtraControl::VIBRATO == state.currentPreset->leverControl) { // lever vibrato
|
||||
vibRead = instrument.leverSignal;
|
||||
if (vibRead > instrument.vibThr) {
|
||||
instrument.vibSignal = (instrument.vibSignal +
|
||||
mapConstrain(vibRead, (instrument.vibZero - vibMax), instrument.vibThr, calculatedDepth, 0)
|
||||
) / 2;
|
||||
instrument.vibSignal = (instrument.vibSignal +
|
||||
mapConstrain(vibRead, (instrument.vibZero - vibMax), instrument.vibThr, calculatedDepth, 0)
|
||||
) / 2;
|
||||
} else if (vibRead < instrument.vibThrLo) {
|
||||
instrument.vibSignal = (instrument.vibSignal +
|
||||
mapConstrain(vibRead, (instrument.vibZero + vibMax), instrument.vibThr, calculatedDepth, 0)
|
||||
) / 2;
|
||||
instrument.vibSignal = (instrument.vibSignal +
|
||||
mapConstrain(vibRead, (instrument.vibZero + vibMax), instrument.vibThr, calculatedDepth, 0)
|
||||
) / 2;
|
||||
} else {
|
||||
instrument.vibSignal = instrument.vibSignal / 2;
|
||||
}
|
||||
|
@ -425,6 +425,52 @@ void sendCC() {
|
|||
}
|
||||
instrument.extraVal = extraVal;
|
||||
}
|
||||
|
||||
if (!inMenu()) {
|
||||
for (int i = 0; i < 4; i++) {
|
||||
byte val = constrain((int)state.instrument->knobVals[i] + readKnob(i), 0, 127);
|
||||
if (state.instrument->knobVals[i] != val) {
|
||||
switch (i) {
|
||||
case 0:
|
||||
midiSendControlChange(state.currentPreset->knob1CC, val);
|
||||
break;
|
||||
case 1:
|
||||
midiSendControlChange(state.currentPreset->knob2CC, val);
|
||||
break;
|
||||
case 2:
|
||||
midiSendControlChange(state.currentPreset->knob3CC, val);
|
||||
break;
|
||||
case 3:
|
||||
midiSendControlChange(state.currentPreset->knob4CC, val);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
state.instrument->knobVals[i] = val;
|
||||
}
|
||||
}
|
||||
|
||||
icm_result_t icmSignal = readICM();
|
||||
Serial.print(">roll: ");
|
||||
Serial.println(icmSignal.roll);
|
||||
Serial.print(">tilt: ");
|
||||
Serial.println(icmSignal.tilt);
|
||||
if (ExtraControl::CC == state.currentPreset->icmRollMode) {
|
||||
byte roll = mapConstrain(abs(icmSignal.roll), 0, 40, 127, 0);
|
||||
if (roll != state.instrument->rollCCVal) {
|
||||
midiSendControlChange(state.currentPreset->icmRollCC, roll);
|
||||
state.instrument->rollCCVal = roll;
|
||||
}
|
||||
}
|
||||
|
||||
if (ExtraControl::CC == state.currentPreset->icmTiltMode) {
|
||||
byte tilt = mapConstrain(abs(icmSignal.tilt), -20, 40, 0, 127);
|
||||
if (tilt != state.instrument->tiltCCVal) {
|
||||
midiSendControlChange(state.currentPreset->icmTiltCC, tilt);
|
||||
state.instrument->tiltCCVal = tilt;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// Re-zero floating calibration values
|
||||
|
@ -444,7 +490,7 @@ void autoCal() {
|
|||
instrument.vibZero = instrument.vibZeroBite = 0;
|
||||
long int bZero = 0;
|
||||
long int bAltZero = 0;
|
||||
for(int i = 1 ; i <= CALIBRATE_SAMPLE_COUNT; ++i) {
|
||||
for (int i = 1; i <= CALIBRATE_SAMPLE_COUNT; ++i) {
|
||||
bZero += readPressure();
|
||||
bAltZero += readAltPressure();
|
||||
instrument.vibZero += readTouchUtil(leverPin);
|
||||
|
@ -464,9 +510,9 @@ void fullAutoCal() {
|
|||
int calReadNext;
|
||||
|
||||
calibration.breathAltThrValOffset = 5;
|
||||
calibration.breathAltMaxValOffset = 1500 ;
|
||||
calibration.breathAltMaxValOffset = 1500;
|
||||
calibration.breathThrValOffset = 5;
|
||||
calibration.breathMaxValOffset = 1500 ;
|
||||
calibration.breathMaxValOffset = 1500;
|
||||
autoCal();
|
||||
|
||||
// Lever
|
||||
|
@ -841,7 +887,7 @@ void setup() {
|
|||
Serial.begin(9600); // debug
|
||||
Serial.println("Debug Startup");
|
||||
if (CrashReport) {
|
||||
while (!Serial) ; // wait for serial monitor open
|
||||
while (!Serial); // wait for serial monitor open
|
||||
Serial.print(CrashReport);
|
||||
}
|
||||
|
||||
|
@ -912,7 +958,7 @@ void loop() {
|
|||
int16_t spikeSignal = constrain(readSpikePressure(), -SPIKE_HI_LIMIT, SPIKE_HI_LIMIT);
|
||||
|
||||
|
||||
if (state.currentPreset->breathMode == BREATH_ACC || state.currentPreset-> breathMode == BREATH_ACC_AT) {
|
||||
if (state.currentPreset->breathMode == BREATH_ACC || state.currentPreset->breathMode == BREATH_ACC_AT) {
|
||||
int delta = breathSignal - instrument.breathZero;
|
||||
if (abs(delta) > state.calibration->breathAltThrValOffset) {
|
||||
instrument.breathSignal = constrain(instrument.breathSignal + delta / 10, instrument.breathZero, instrument.breathMaxVal);
|
||||
|
@ -922,18 +968,18 @@ void loop() {
|
|||
}
|
||||
instrument.breathAltSignal = constrain(readAltPressure(), BREATH_LO_LIMIT, BREATH_HI_LIMIT); // Get the filtered pressure sensor reading from analog pin A0, input from sensor MP3V5004GP
|
||||
|
||||
/*
|
||||
Serial.print(">breathThr:");
|
||||
Serial.println(instrument.breathThrVal);
|
||||
Serial.print(">note:");
|
||||
Serial.println(state.mainState);
|
||||
Serial.print(">spike:");
|
||||
Serial.println(spikeSignal);
|
||||
Serial.print(">breath:");
|
||||
Serial.println(breathSignal);
|
||||
Serial.print(">combo:");
|
||||
Serial.println(instrument.breathSignal);
|
||||
*/
|
||||
/*
|
||||
Serial.print(">breathThr:");
|
||||
Serial.println(instrument.breathThrVal);
|
||||
Serial.print(">note:");
|
||||
Serial.println(state.mainState);
|
||||
Serial.print(">spike:");
|
||||
Serial.println(spikeSignal);
|
||||
Serial.print(">breath:");
|
||||
Serial.println(breathSignal);
|
||||
Serial.print(">combo:");
|
||||
Serial.println(instrument.breathSignal);
|
||||
*/
|
||||
|
||||
runStateMachine();
|
||||
sendCCs();
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue