I'm trying to create a code for a simple 2 footswitch midi controller to scroll through presets 0-7 (on a guitar pedal) using two momentary switches and an arduino nano.
All is going well until i wanted to add a feature where pressing both switches at the same time recalled preset 127 as this is manual mode on the guitar pedal. It seems to mostly work however now to scroll through 0-7 I have to hold the opposite button down whilst pressing the other. Can anyone help with why this might be?
Thanks
#include <MIDI.h>
MIDI_CREATE_DEFAULT_INSTANCE();
int progNo = 0;
int upLastTime, downLastTime, upNow, downNow;
int last_progNo;
int LED1 = 15;
int LED2 = 14;
int LED3 = 16;
int LED4 = 10;
int LED5 = 9;
int LED6 = 8;
int LED7 = 7;
int LED8 = 6;
void setup() {
Serial.begin(9600);
MIDI.begin();
MIDI.setInputChannel(1);
pinMode(2, INPUT);
pinMode(3, INPUT);
pinMode(LED1, OUTPUT);
pinMode(LED2, OUTPUT);
pinMode(LED3, OUTPUT);
pinMode(LED4, OUTPUT);
pinMode(LED5, OUTPUT);
pinMode(LED6, OUTPUT);
pinMode(LED7, OUTPUT);
pinMode(LED8, OUTPUT);
digitalWrite(2, HIGH); // enable pull up
digitalWrite(3, HIGH); // enable pull up
upLastTime = digitalRead(2);
downLastTime = digitalRead(3);
}
void loop() {
upNow = digitalRead(2);
downNow = digitalRead(3);
// Check if both up and down buttons are pressed
if (upNow == HIGH && downNow == HIGH) {
progNo = 127; // Set to preset 127
MIDI.sendProgramChange(byte(progNo), 1);
delay(20); // Debounce delay
} else {
// Check individual button presses
if (upNow == HIGH && upLastTime == LOW) {
progNo++; // Increment program change
if (progNo > 7) progNo = 0; // Wrap around to 0
MIDI.sendProgramChange(byte(progNo), 1);
delay(20); // Debounce delay
}
if (downNow == HIGH && downLastTime == LOW) {
progNo--; // Decrement program change
if (progNo < 0) progNo = 7; // Wrap around to 7
MIDI.sendProgramChange(byte(progNo), 1);
delay(20); // Debounce delay
}
}
// Check if both up and down buttons are pressed
if (upNow == HIGH && downNow == HIGH) {
progNo = 127; // Set to preset 127
MIDI.sendProgramChange(byte(progNo), 1);
delay(20); // Debounce delay
} else {
Since you've set INPUT_PULLUP and if one assumes the switches are normally open, won't this test always be true? Are the switches NO or NC?
// Check individual button presses
if (upNow == HIGH && upLastTime == LOW) {`
I can't see any place where upLastTime is updated. Same for downLastTime.
pinMode(2, INPUT);
pinMode(3, INPUT);
The code will be easier to read and maintain if you give the input pins descriptive names - like was done for the LEDs.
Sorry, viewed your reply quickly last night and missed it!
Just tried your sketch and it seems to work better however, when looking on the serial monitor - the progNo always defaults to 127 if nothing is pressed and because of this when i try to scroll down through presets it will start at 127 - 126 - 125 etc.
#include <MIDI.h>
MIDI_CREATE_DEFAULT_INSTANCE();
const byte LEDs[] = { 15, 14, 16, 10, 9, 8, 7, 6};
void setup() {
Serial.begin(9600);
MIDI.begin();
MIDI.setInputChannel(1);
pinMode(2, INPUT_PULLUP);// enable pull up
pinMode(3, INPUT_PULLUP);
for (byte i = 0; i < 8; i++)pinMode(LEDs[i], OUTPUT);
}
void loop() {
static byte progNo = 0;
static bool upNow, downNow = false;
upNow = digitalRead(2) == HIGH; //Switches are NC
downNow = digitalRead(3) == HIGH;
// Check if both up and down buttons are pressed
if (upNow && downNow ) {
progNo = 127; // Set to preset 127
MIDI.sendProgramChange(byte(progNo), 1);
delay(1000); // not a Debounce delay
} else {
// Check individual button presses
if (upNow ) {
if (progNo < 7)progNo++; // Increment program change
else progNo = 0; // Wrap around to 0
MIDI.sendProgramChange(byte(progNo), 1);
delay(50);
}
if (downNow ) {
if (progNo > 0)progNo--; // Decrement program change
else progNo = 7; // Wrap around to 7
MIDI.sendProgramChange(byte(progNo), 1);
delay(50);
}
}
for (byte i = 0; i < 8; i++)if (progNo != i)digitalWrite(LEDs[i], LOW); else digitalWrite(LEDs[i], HIGH);
Serial.println(progNo); // Print only if the program number is different
}
DIY or load a button library (there are several in the IDE libraries) which offers a long press/short press feature. A regular (short) press will cycle through the 0-7 options. Let's arbitrarily choose the right switch to activate the manual mode on a long press and deactivate manual mode on a left switch long press - and return to the 0-7 mode. If desired, one could even remember which 0-7 preset was active and restore it when exiting manual mode.