Last active
June 6, 2018 06:01
-
-
Save johannespetzold/d80fce91a2cf7665aefa1f502f29e561 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include "Keyboard.h" | |
// columns are outputs, rows are inputs | |
uint8_t colPins[] = { 15, 14, 16, 10, 3, 4 }; | |
uint8_t rowPins[] = { 5, 6, 7, 8, 9 }; | |
#define NUMCOLS sizeof(colPins) | |
#define NUMROWS sizeof(rowPins) | |
#define NUMKEYS (NUMCOLS * NUMROWS) | |
uint8_t keymap[][NUMKEYS] = { | |
{ | |
KEY_ESC, 'q', 'w', 'e', 'r', 't', | |
KEY_TAB, 'a', 's', 'd', 'f', 'g', | |
0, 'z', 'x', 'c', 'v', 'b', | |
KEY_LEFT_GUI, ' ', KEY_DOWN_ARROW, KEY_UP_ARROW, 1, KEY_LEFT_SHIFT, | |
KEY_LEFT_ALT, KEY_LEFT_CTRL | |
}, | |
{ | |
KEY_ESC, KEY_F1, KEY_F2, KEY_F3, KEY_F4, KEY_F5, | |
KEY_TAB, '1', '2', '3', '4', '5', | |
0, 'z', 'x', 'c', 'v', 'b', | |
KEY_LEFT_GUI, ' ', KEY_PAGE_DOWN, KEY_PAGE_UP, 1, KEY_LEFT_SHIFT, | |
KEY_LEFT_ALT, KEY_LEFT_CTRL | |
}, | |
}; | |
#define NUMLAYERS (sizeof(keymap) / sizeof(keymap[0])) | |
void setup() { | |
Keyboard.begin(); | |
Serial.begin(2000000); | |
// pinMode(17, OUTPUT); | |
for (uint8_t i = 0; i < NUMCOLS; i++) { | |
uint8_t pin = colPins[i]; | |
pinMode(pin, OUTPUT); | |
digitalWrite(pin, HIGH); | |
} | |
for (uint8_t i = 0; i < NUMROWS; i++) { | |
uint8_t pin = rowPins[i]; | |
pinMode(pin, INPUT_PULLUP); | |
} | |
} | |
uint8_t keyState[NUMKEYS]; | |
uint8_t activeLayer; | |
bool keyStateValid[NUMKEYS]; | |
uint8_t debounceTimers[NUMKEYS]; | |
#define DEBOUNCE_TIMER_DELAY_MICROS 2000 | |
#define DEBOUNCE_TIMER_RESOLUTION_MICROS 16 | |
#define DEBOUNCE_TIMER_DELAY (DEBOUNCE_TIMER_DELAY_MICROS / DEBOUNCE_TIMER_RESOLUTION_MICROS) | |
void pressKey(uint8_t keyCode) { | |
if (keyCode < NUMLAYERS) { | |
activeLayer = keyCode; | |
} else { | |
Keyboard.press(keyCode); | |
} | |
} | |
void releaseKey(uint8_t keyCode) { | |
if (keyCode < NUMLAYERS) { | |
activeLayer = 0; | |
} else { | |
Keyboard.release(keyCode); | |
} | |
} | |
void onKeyStateChanged(uint8_t key) { | |
uint8_t code = keymap[activeLayer][key]; | |
if (keyState[key] == LOW) { | |
pressKey(code); | |
} else { | |
releaseKey(code); | |
} | |
} | |
void setKeyState(uint8_t key, uint8_t state) { | |
uint8_t now = micros() / DEBOUNCE_TIMER_RESOLUTION_MICROS; | |
uint8_t expired = now - DEBOUNCE_TIMER_DELAY; | |
if (!keyStateValid[key]) { | |
keyState[key] = state; | |
debounceTimers[key] = expired; | |
keyStateValid[key] = true; | |
return; | |
} | |
if (int8_t(debounceTimers[key] - expired) > 0) { | |
return; | |
} | |
if (state == keyState[key]) { | |
debounceTimers[key] = expired; | |
return; | |
} | |
keyState[key] = state; | |
debounceTimers[key] = now; | |
onKeyStateChanged(key); | |
} | |
void scanColumn(uint8_t col) { | |
uint8_t colPin = colPins[col]; | |
digitalWrite(colPin, LOW); | |
for (uint8_t row = 0, key = col; row < NUMROWS; row++, key += NUMCOLS) { | |
uint8_t rowPin = rowPins[row]; | |
uint8_t keyState = digitalRead(rowPin); | |
setKeyState(key, keyState); | |
} | |
digitalWrite(colPin, HIGH); | |
} | |
void loop() { | |
for (uint8_t col = 0; col < NUMCOLS; col++) { | |
scanColumn(col); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment