Hi guys and gals, I am programming far beyond my understanding through copying and adapting existing code.
But I'm stuck, and any help is greatly appreciated!
I got a code for reading a 7x8 keyboard matrix which was read using a shift register. That code worked fine although one column did not generate notes.
Now I'm using the same code but slightly modified to accomodate a 4x4 keyboard matrix.
I find that turning bitmask lines on and off in the code makes the difference between midi notes being played or not. However, I can get only three rows to play, and this moment only two. My hardware setup:
Arduino Uno
button matrix of 16 buttons, 4 rows, 4 columns, with diodes galore. This matrix is tested with a led and functions properly.
row pins of the button matrix are 9,10,11,12 the wires leading from the rows are also grounded though 10k Ohm resistors
shift register used 74HC595
the columns of the button matrix are attached to the shift register pins 2, 3, 4 and 15
5 volt and ground are connected to the correct pins of the shift register
a midi port is connected to the Arduino. This is the code:
#include <MIDI.h>
// Keyboard matrix
const int NUM_ROWS = 4;
const int NUM_COLS = 4;
// Row input pins
const int rowPins[NUM_ROWS] = {9,10,11,12};
// 74HC595 pins
const int dataPin = 4;
const int latchPin = 3;
const int clockPin = 2;
// bitmasks for scanning columns
const byte bits[] = {
//B10000000,//this line turned off two columns give midi notes
//B01000000,//this line turned off three columns give midi notes
B00100000, //als deze aan staat transponeren alle note 4 halve omhoog
B00010000,//column one sound
B00001000,//column two sound
B00000100,//column three sound
B00000010,
B00000001,
};
int prevKeyStates[NUM_ROWS][NUM_COLS];
MIDI_CREATE_DEFAULT_INSTANCE();
void setup() {
// Set pin modes
pinMode(dataPin, OUTPUT);
pinMode(clockPin, OUTPUT);
pinMode(latchPin, OUTPUT);
for (int i = 0; i < NUM_ROWS; ++i) {
pinMode(rowPins[i], INPUT_PULLUP);
}
Serial.begin(9600);
MIDI.begin(1); // MIDI channel 1
}
void loop() {
// Scan columns
for (int colCtr = 0; colCtr < NUM_COLS; ++colCtr) {
// Activate column
scanColumn(colCtr);
// Read row values
for (int rowCtr = 0; rowCtr < NUM_ROWS; ++rowCtr) {
int keyState = digitalRead(rowPins[rowCtr]);
// Check if key is pressed and was not pressed before
if (keyState == HIGH && prevKeyStates[rowCtr][colCtr] == LOW) {
// Calculate key number
int keyNum = colCtr * NUM_ROWS + rowCtr + 1;
// Calculate MIDI note number
int noteNum = keyNum + 50;
// Send MIDI note on command
MIDI.sendNoteOn(noteNum, 127, 1);
}
// Check if key was released and was pressed before
else if (keyState == LOW && prevKeyStates[rowCtr][colCtr] == HIGH) {
// Calculate key number
int keyNum = colCtr * NUM_ROWS + rowCtr + 1;
// Calculate MIDI note number
int noteNum = keyNum + 50;
// Send MIDI note off command
MIDI.sendNoteOff(noteNum, 0, 1);
}
prevKeyStates[rowCtr][colCtr] = keyState;
}
}
}
void scanColumn(int colNum) {
digitalWrite(latchPin, LOW);
if (0 <= colNum && colNum <= 4) {
shiftOut(dataPin, clockPin, MSBFIRST, B00000000); // Right shift register
shiftOut(dataPin, clockPin, MSBFIRST, bits[colNum]); // Left shift register
} else {
shiftOut(dataPin, clockPin, MSBFIRST, bits[colNum - 4]); // Right shift register
shiftOut(dataPin, clockPin, MSBFIRST, B00000000); // Left shift register
}
digitalWrite(latchPin, HIGH);
}