5 #include <util/delay.h>
9 // matrix is active low. (key on: 0/key off: 1)
10 // row: Hi-Z(unselected)/low output(selected)
11 // PD0, PC7, PD7, PF6, PD6, PD1, PD2, PC6, PF7
12 // col: input w/pullup
15 // matrix state buffer
18 static uint8_t _matrix0[MATRIX_ROWS];
19 static uint8_t _matrix1[MATRIX_ROWS];
21 static uint8_t read_col(void);
22 static void unselect_rows(void);
23 static void select_row(uint8_t row);
26 // this must be called once before matrix_scan.
27 void matrix_init(void)
29 // initialize row and col
34 // initialize matrix state: all keys off
35 for (int i=0; i < MATRIX_ROWS; i++) _matrix0[i] = 0xFF;
36 for (int i=0; i < MATRIX_ROWS; i++) _matrix1[i] = 0xFF;
38 matrix_prev = _matrix1;
41 uint8_t matrix_scan(void)
50 for (row = 0; row < MATRIX_ROWS; row++) {
52 _delay_us(30); // without this wait read unstable value.
61 bool matrix_is_modified(void) {
62 for (int i=0; i <MATRIX_ROWS; i++) {
63 if (matrix[i] != matrix_prev[i])
69 bool matrix_has_ghost(void) {
70 for (int i=0; i <MATRIX_ROWS; i++) {
71 if (matrix_has_ghost_in_row(i))
77 bool matrix_has_ghost_in_row(uint8_t row) {
78 uint8_t state = ~matrix[row];
79 // no ghost exists in case less than 2 keys on
80 if (((state - 1) & state) == 0)
83 // ghost exists in case same state as other row
84 for (int i=0; i < MATRIX_ROWS; i++) {
85 if (i == row) continue;
86 if ((~matrix[i] & state) == state) return true;
91 static uint8_t read_col(void)
96 static void unselect_rows(void) {
105 static void select_row(uint8_t row)