aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--docs/config_options.md3
-rw-r--r--docs/custom_quantum_functions.md8
-rw-r--r--keyboards/anavi/macropad8/keymaps/default/config.h19
-rw-r--r--keyboards/handwired/frankie_macropad/keymaps/default/config.h19
-rw-r--r--keyboards/kbdfans/kbd67/rev1/keymaps/default/config.h2
-rw-r--r--keyboards/mt84/keymaps/default/config.h19
-rw-r--r--quantum/matrix.c71
-rw-r--r--quantum/split_common/matrix.c69
8 files changed, 131 insertions, 79 deletions
diff --git a/docs/config_options.md b/docs/config_options.md
index d0f0b316e..26fe8cea5 100644
--- a/docs/config_options.md
+++ b/docs/config_options.md
@@ -51,8 +51,10 @@ This is a C header file that is one of the first things included, and will persi
51 * the number of columns in your keyboard's matrix 51 * the number of columns in your keyboard's matrix
52* `#define MATRIX_ROW_PINS { D0, D5, B5, B6 }` 52* `#define MATRIX_ROW_PINS { D0, D5, B5, B6 }`
53 * pins of the rows, from top to bottom 53 * pins of the rows, from top to bottom
54 * may be omitted by the keyboard designer if matrix reads are handled in an alternate manner. See [low-level matrix overrides](custom_quantum_functions.md?id=low-level-matrix-overrides) for more information.
54* `#define MATRIX_COL_PINS { F1, F0, B0, C7, F4, F5, F6, F7, D4, D6, B4, D7 }` 55* `#define MATRIX_COL_PINS { F1, F0, B0, C7, F4, F5, F6, F7, D4, D6, B4, D7 }`
55 * pins of the columns, from left to right 56 * pins of the columns, from left to right
57 * may be omitted by the keyboard designer if matrix reads are handled in an alternate manner. See [low-level matrix overrides](custom_quantum_functions.md?id=low-level-matrix-overrides) for more information.
56* `#define MATRIX_IO_DELAY 30` 58* `#define MATRIX_IO_DELAY 30`
57 * the delay in microseconds when between changing matrix pin state and reading values 59 * the delay in microseconds when between changing matrix pin state and reading values
58* `#define UNUSED_PINS { D1, D2, D3, B1, B2, B3 }` 60* `#define UNUSED_PINS { D1, D2, D3, B1, B2, B3 }`
@@ -280,6 +282,7 @@ There are a few different ways to set handedness for split keyboards (listed in
280* `#define MATRIX_ROW_PINS_RIGHT { <row pins> }` 282* `#define MATRIX_ROW_PINS_RIGHT { <row pins> }`
281* `#define MATRIX_COL_PINS_RIGHT { <col pins> }` 283* `#define MATRIX_COL_PINS_RIGHT { <col pins> }`
282 * If you want to specify a different pinout for the right half than the left half, you can define `MATRIX_ROW_PINS_RIGHT`/`MATRIX_COL_PINS_RIGHT`. Currently, the size of `MATRIX_ROW_PINS` must be the same as `MATRIX_ROW_PINS_RIGHT` and likewise for the definition of columns. 284 * If you want to specify a different pinout for the right half than the left half, you can define `MATRIX_ROW_PINS_RIGHT`/`MATRIX_COL_PINS_RIGHT`. Currently, the size of `MATRIX_ROW_PINS` must be the same as `MATRIX_ROW_PINS_RIGHT` and likewise for the definition of columns.
285 * may be omitted by the keyboard designer if matrix reads are handled in an alternate manner. See [low-level matrix overrides](custom_quantum_functions.md?id=low-level-matrix-overrides) for more information.
283 286
284* `#define DIRECT_PINS_RIGHT { { F1, F0, B0, C7 }, { F4, F5, F6, F7 } }` 287* `#define DIRECT_PINS_RIGHT { { F1, F0, B0, C7 }, { F4, F5, F6, F7 } }`
285 * If you want to specify a different direct pinout for the right half than the left half, you can define `DIRECT_PINS_RIGHT`. Currently, the size of `DIRECT_PINS` must be the same as `DIRECT_PINS_RIGHT`. 288 * If you want to specify a different direct pinout for the right half than the left half, you can define `DIRECT_PINS_RIGHT`. Currently, the size of `DIRECT_PINS` must be the same as `DIRECT_PINS_RIGHT`.
diff --git a/docs/custom_quantum_functions.md b/docs/custom_quantum_functions.md
index 694b421e7..30c637bb4 100644
--- a/docs/custom_quantum_functions.md
+++ b/docs/custom_quantum_functions.md
@@ -144,6 +144,14 @@ This is useful for setting up stuff that you may need elsewhere, but isn't hardw
144* Keyboard/Revision: `void matrix_init_kb(void)` 144* Keyboard/Revision: `void matrix_init_kb(void)`
145* Keymap: `void matrix_init_user(void)` 145* Keymap: `void matrix_init_user(void)`
146 146
147### Low-level Matrix Overrides Function Documentation :id=low-level-matrix-overrides
148
149* GPIO pin initialisation: `void matrix_init_pins(void)`
150 * This needs to perform the low-level initialisation of all row and column pins. By default this will initialise the input/output state of each of the GPIO pins listed in `MATRIX_ROW_PINS` and `MATRIX_COL_PINS`, based on whether or not the keyboard is set up for `ROW2COL`, `COL2ROW`, or `DIRECT_PINS`. Should the keyboard designer override this function, no initialisation of pin state will occur within QMK itself, instead deferring to the keyboard's override.
151* `COL2ROW`-based row reads: `void matrix_read_rows_on_col(matrix_row_t current_matrix[], uint8_t current_col)`
152* `ROW2COL`-based column reads: `void matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row)`
153* `DIRECT_PINS`-based reads: `void matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row)`
154 * These three functions need to perform the low-level retrieval of matrix state of relevant input pins, based on the matrix type. Only one of the functions should be implemented, if needed. By default this will iterate through `MATRIX_ROW_PINS` and `MATRIX_COL_PINS`, configuring the inputs and outputs based on whether or not the keyboard is set up for `ROW2COL`, `COL2ROW`, or `DIRECT_PINS`. Should the keyboard designer override this function, no manipulation of matrix GPIO pin state will occur within QMK itself, instead deferring to the keyboard's override.
147 155
148## Keyboard Post Initialization code 156## Keyboard Post Initialization code
149 157
diff --git a/keyboards/anavi/macropad8/keymaps/default/config.h b/keyboards/anavi/macropad8/keymaps/default/config.h
new file mode 100644
index 000000000..dd687cad5
--- /dev/null
+++ b/keyboards/anavi/macropad8/keymaps/default/config.h
@@ -0,0 +1,19 @@
1/* Copyright 2021 QMK
2 *
3 * This program is free software: you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation, either version 2 of the License, or
6 * (at your option) any later version.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 */
16
17#pragma once
18
19#define LAYER_STATE_8BIT
diff --git a/keyboards/handwired/frankie_macropad/keymaps/default/config.h b/keyboards/handwired/frankie_macropad/keymaps/default/config.h
new file mode 100644
index 000000000..dd687cad5
--- /dev/null
+++ b/keyboards/handwired/frankie_macropad/keymaps/default/config.h
@@ -0,0 +1,19 @@
1/* Copyright 2021 QMK
2 *
3 * This program is free software: you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation, either version 2 of the License, or
6 * (at your option) any later version.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 */
16
17#pragma once
18
19#define LAYER_STATE_8BIT
diff --git a/keyboards/kbdfans/kbd67/rev1/keymaps/default/config.h b/keyboards/kbdfans/kbd67/rev1/keymaps/default/config.h
index a3ed4f762..90fb10ebb 100644
--- a/keyboards/kbdfans/kbd67/rev1/keymaps/default/config.h
+++ b/keyboards/kbdfans/kbd67/rev1/keymaps/default/config.h
@@ -16,4 +16,4 @@
16 16
17#pragma once 17#pragma once
18 18
19// place overrides here 19#define LAYER_STATE_8BIT
diff --git a/keyboards/mt84/keymaps/default/config.h b/keyboards/mt84/keymaps/default/config.h
new file mode 100644
index 000000000..dd687cad5
--- /dev/null
+++ b/keyboards/mt84/keymaps/default/config.h
@@ -0,0 +1,19 @@
1/* Copyright 2021 QMK
2 *
3 * This program is free software: you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation, either version 2 of the License, or
6 * (at your option) any later version.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 */
16
17#pragma once
18
19#define LAYER_STATE_8BIT
diff --git a/quantum/matrix.c b/quantum/matrix.c
index 9298661ad..71ef27089 100644
--- a/quantum/matrix.c
+++ b/quantum/matrix.c
@@ -16,6 +16,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
16*/ 16*/
17#include <stdint.h> 17#include <stdint.h>
18#include <stdbool.h> 18#include <stdbool.h>
19#include <string.h>
19#include "util.h" 20#include "util.h"
20#include "matrix.h" 21#include "matrix.h"
21#include "debounce.h" 22#include "debounce.h"
@@ -24,14 +25,23 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
24#ifdef DIRECT_PINS 25#ifdef DIRECT_PINS
25static pin_t direct_pins[MATRIX_ROWS][MATRIX_COLS] = DIRECT_PINS; 26static pin_t direct_pins[MATRIX_ROWS][MATRIX_COLS] = DIRECT_PINS;
26#elif (DIODE_DIRECTION == ROW2COL) || (DIODE_DIRECTION == COL2ROW) 27#elif (DIODE_DIRECTION == ROW2COL) || (DIODE_DIRECTION == COL2ROW)
28# ifdef MATRIX_ROW_PINS
27static const pin_t row_pins[MATRIX_ROWS] = MATRIX_ROW_PINS; 29static const pin_t row_pins[MATRIX_ROWS] = MATRIX_ROW_PINS;
30# endif // MATRIX_ROW_PINS
31# ifdef MATRIX_COL_PINS
28static const pin_t col_pins[MATRIX_COLS] = MATRIX_COL_PINS; 32static const pin_t col_pins[MATRIX_COLS] = MATRIX_COL_PINS;
33# endif // MATRIX_COL_PINS
29#endif 34#endif
30 35
31/* matrix state(1:on, 0:off) */ 36/* matrix state(1:on, 0:off) */
32extern matrix_row_t raw_matrix[MATRIX_ROWS]; // raw values 37extern matrix_row_t raw_matrix[MATRIX_ROWS]; // raw values
33extern matrix_row_t matrix[MATRIX_ROWS]; // debounced values 38extern matrix_row_t matrix[MATRIX_ROWS]; // debounced values
34 39
40// user-defined overridable functions
41__attribute__((weak)) void matrix_init_pins(void);
42__attribute__((weak)) void matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row);
43__attribute__((weak)) void matrix_read_rows_on_col(matrix_row_t current_matrix[], uint8_t current_col);
44
35static inline void setPinOutput_writeLow(pin_t pin) { 45static inline void setPinOutput_writeLow(pin_t pin) {
36 ATOMIC_BLOCK_FORCEON { 46 ATOMIC_BLOCK_FORCEON {
37 setPinOutput(pin); 47 setPinOutput(pin);
@@ -58,7 +68,7 @@ __attribute__((weak)) void matrix_init_pins(void) {
58 } 68 }
59} 69}
60 70
61__attribute__((weak)) bool matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row) { 71__attribute__((weak)) void matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row) {
62 // Start with a clear matrix row 72 // Start with a clear matrix row
63 matrix_row_t current_row_value = 0; 73 matrix_row_t current_row_value = 0;
64 74
@@ -69,16 +79,13 @@ __attribute__((weak)) bool matrix_read_cols_on_row(matrix_row_t current_matrix[]
69 } 79 }
70 } 80 }
71 81
72 // If the row has changed, store the row and return the changed flag. 82 // Update the matrix
73 if (current_matrix[current_row] != current_row_value) { 83 current_matrix[current_row] = current_row_value;
74 current_matrix[current_row] = current_row_value;
75 return true;
76 }
77 return false;
78} 84}
79 85
80#elif defined(DIODE_DIRECTION) 86#elif defined(DIODE_DIRECTION)
81# if (DIODE_DIRECTION == COL2ROW) 87# if defined(MATRIX_ROW_PINS) && defined(MATRIX_COL_PINS)
88# if (DIODE_DIRECTION == COL2ROW)
82 89
83static void select_row(uint8_t row) { setPinOutput_writeLow(row_pins[row]); } 90static void select_row(uint8_t row) { setPinOutput_writeLow(row_pins[row]); }
84 91
@@ -97,7 +104,7 @@ __attribute__((weak)) void matrix_init_pins(void) {
97 } 104 }
98} 105}
99 106
100__attribute__((weak)) bool matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row) { 107__attribute__((weak)) void matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row) {
101 // Start with a clear matrix row 108 // Start with a clear matrix row
102 matrix_row_t current_row_value = 0; 109 matrix_row_t current_row_value = 0;
103 110
@@ -118,15 +125,11 @@ __attribute__((weak)) bool matrix_read_cols_on_row(matrix_row_t current_matrix[]
118 unselect_row(current_row); 125 unselect_row(current_row);
119 matrix_output_unselect_delay(); // wait for all Col signals to go HIGH 126 matrix_output_unselect_delay(); // wait for all Col signals to go HIGH
120 127
121 // If the row has changed, store the row and return the changed flag. 128 // Update the matrix
122 if (current_matrix[current_row] != current_row_value) { 129 current_matrix[current_row] = current_row_value;
123 current_matrix[current_row] = current_row_value;
124 return true;
125 }
126 return false;
127} 130}
128 131
129# elif (DIODE_DIRECTION == ROW2COL) 132# elif (DIODE_DIRECTION == ROW2COL)
130 133
131static void select_col(uint8_t col) { setPinOutput_writeLow(col_pins[col]); } 134static void select_col(uint8_t col) { setPinOutput_writeLow(col_pins[col]); }
132 135
@@ -145,45 +148,32 @@ __attribute__((weak)) void matrix_init_pins(void) {
145 } 148 }
146} 149}
147 150
148__attribute__((weak)) bool matrix_read_rows_on_col(matrix_row_t current_matrix[], uint8_t current_col) { 151__attribute__((weak)) void matrix_read_rows_on_col(matrix_row_t current_matrix[], uint8_t current_col) {
149 bool matrix_changed = false;
150
151 // Select col 152 // Select col
152 select_col(current_col); 153 select_col(current_col);
153 matrix_output_select_delay(); 154 matrix_output_select_delay();
154 155
155 // For each row... 156 // For each row...
156 for (uint8_t row_index = 0; row_index < MATRIX_ROWS; row_index++) { 157 for (uint8_t row_index = 0; row_index < MATRIX_ROWS; row_index++) {
157 // Store last value of row prior to reading
158 matrix_row_t last_row_value = current_matrix[row_index];
159 matrix_row_t current_row_value = last_row_value;
160
161 // Check row pin state 158 // Check row pin state
162 if (readPin(row_pins[row_index]) == 0) { 159 if (readPin(row_pins[row_index]) == 0) {
163 // Pin LO, set col bit 160 // Pin LO, set col bit
164 current_row_value |= (MATRIX_ROW_SHIFTER << current_col); 161 current_matrix[row_index] |= (MATRIX_ROW_SHIFTER << current_col);
165 } else { 162 } else {
166 // Pin HI, clear col bit 163 // Pin HI, clear col bit
167 current_row_value &= ~(MATRIX_ROW_SHIFTER << current_col); 164 current_matrix[row_index] &= ~(MATRIX_ROW_SHIFTER << current_col);
168 }
169
170 // Determine if the matrix changed state
171 if ((last_row_value != current_row_value)) {
172 matrix_changed |= true;
173 current_matrix[row_index] = current_row_value;
174 } 165 }
175 } 166 }
176 167
177 // Unselect col 168 // Unselect col
178 unselect_col(current_col); 169 unselect_col(current_col);
179 matrix_output_unselect_delay(); // wait for all Row signals to go HIGH 170 matrix_output_unselect_delay(); // wait for all Row signals to go HIGH
180
181 return matrix_changed;
182} 171}
183 172
184# else 173# else
185# error DIODE_DIRECTION must be one of COL2ROW or ROW2COL! 174# error DIODE_DIRECTION must be one of COL2ROW or ROW2COL!
186# endif 175# endif
176# endif // defined(MATRIX_ROW_PINS) && defined(MATRIX_COL_PINS)
187#else 177#else
188# error DIODE_DIRECTION is not defined! 178# error DIODE_DIRECTION is not defined!
189#endif 179#endif
@@ -204,20 +194,23 @@ void matrix_init(void) {
204} 194}
205 195
206uint8_t matrix_scan(void) { 196uint8_t matrix_scan(void) {
207 bool changed = false; 197 matrix_row_t curr_matrix[MATRIX_ROWS] = {0};
208 198
209#if defined(DIRECT_PINS) || (DIODE_DIRECTION == COL2ROW) 199#if defined(DIRECT_PINS) || (DIODE_DIRECTION == COL2ROW)
210 // Set row, read cols 200 // Set row, read cols
211 for (uint8_t current_row = 0; current_row < MATRIX_ROWS; current_row++) { 201 for (uint8_t current_row = 0; current_row < MATRIX_ROWS; current_row++) {
212 changed |= matrix_read_cols_on_row(raw_matrix, current_row); 202 matrix_read_cols_on_row(curr_matrix, current_row);
213 } 203 }
214#elif (DIODE_DIRECTION == ROW2COL) 204#elif (DIODE_DIRECTION == ROW2COL)
215 // Set col, read rows 205 // Set col, read rows
216 for (uint8_t current_col = 0; current_col < MATRIX_COLS; current_col++) { 206 for (uint8_t current_col = 0; current_col < MATRIX_COLS; current_col++) {
217 changed |= matrix_read_rows_on_col(raw_matrix, current_col); 207 matrix_read_rows_on_col(curr_matrix, current_col);
218 } 208 }
219#endif 209#endif
220 210
211 bool changed = memcmp(raw_matrix, curr_matrix, sizeof(curr_matrix)) != 0;
212 if (changed) memcpy(raw_matrix, curr_matrix, sizeof(curr_matrix));
213
221 debounce(raw_matrix, matrix, MATRIX_ROWS, changed); 214 debounce(raw_matrix, matrix, MATRIX_ROWS, changed);
222 215
223 matrix_scan_quantum(); 216 matrix_scan_quantum();
diff --git a/quantum/split_common/matrix.c b/quantum/split_common/matrix.c
index a54ea90b3..2cf7b7058 100644
--- a/quantum/split_common/matrix.c
+++ b/quantum/split_common/matrix.c
@@ -16,6 +16,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
16*/ 16*/
17#include <stdint.h> 17#include <stdint.h>
18#include <stdbool.h> 18#include <stdbool.h>
19#include <string.h>
19#include "util.h" 20#include "util.h"
20#include "matrix.h" 21#include "matrix.h"
21#include "debounce.h" 22#include "debounce.h"
@@ -31,8 +32,12 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
31#ifdef DIRECT_PINS 32#ifdef DIRECT_PINS
32static pin_t direct_pins[MATRIX_ROWS][MATRIX_COLS] = DIRECT_PINS; 33static pin_t direct_pins[MATRIX_ROWS][MATRIX_COLS] = DIRECT_PINS;
33#elif (DIODE_DIRECTION == ROW2COL) || (DIODE_DIRECTION == COL2ROW) 34#elif (DIODE_DIRECTION == ROW2COL) || (DIODE_DIRECTION == COL2ROW)
35# ifdef MATRIX_ROW_PINS
34static pin_t row_pins[MATRIX_ROWS] = MATRIX_ROW_PINS; 36static pin_t row_pins[MATRIX_ROWS] = MATRIX_ROW_PINS;
37# endif // MATRIX_ROW_PINS
38# ifdef MATRIX_COL_PINS
35static pin_t col_pins[MATRIX_COLS] = MATRIX_COL_PINS; 39static pin_t col_pins[MATRIX_COLS] = MATRIX_COL_PINS;
40# endif // MATRIX_COL_PINS
36#endif 41#endif
37 42
38/* matrix state(1:on, 0:off) */ 43/* matrix state(1:on, 0:off) */
@@ -45,6 +50,9 @@ uint8_t thisHand, thatHand;
45// user-defined overridable functions 50// user-defined overridable functions
46__attribute__((weak)) void matrix_slave_scan_kb(void) { matrix_slave_scan_user(); } 51__attribute__((weak)) void matrix_slave_scan_kb(void) { matrix_slave_scan_user(); }
47__attribute__((weak)) void matrix_slave_scan_user(void) {} 52__attribute__((weak)) void matrix_slave_scan_user(void) {}
53__attribute__((weak)) void matrix_init_pins(void);
54__attribute__((weak)) void matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row);
55__attribute__((weak)) void matrix_read_rows_on_col(matrix_row_t current_matrix[], uint8_t current_col);
48 56
49static inline void setPinOutput_writeLow(pin_t pin) { 57static inline void setPinOutput_writeLow(pin_t pin) {
50 ATOMIC_BLOCK_FORCEON { 58 ATOMIC_BLOCK_FORCEON {
@@ -72,7 +80,7 @@ __attribute__((weak)) void matrix_init_pins(void) {
72 } 80 }
73} 81}
74 82
75__attribute__((weak)) bool matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row) { 83__attribute__((weak)) void matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row) {
76 // Start with a clear matrix row 84 // Start with a clear matrix row
77 matrix_row_t current_row_value = 0; 85 matrix_row_t current_row_value = 0;
78 86
@@ -83,16 +91,13 @@ __attribute__((weak)) bool matrix_read_cols_on_row(matrix_row_t current_matrix[]
83 } 91 }
84 } 92 }
85 93
86 // If the row has changed, store the row and return the changed flag. 94 // Update the matrix
87 if (current_matrix[current_row] != current_row_value) { 95 current_matrix[current_row] = current_row_value;
88 current_matrix[current_row] = current_row_value;
89 return true;
90 }
91 return false;
92} 96}
93 97
94#elif defined(DIODE_DIRECTION) 98#elif defined(DIODE_DIRECTION)
95# if (DIODE_DIRECTION == COL2ROW) 99# if defined(MATRIX_ROW_PINS) && defined(MATRIX_COL_PINS)
100# if (DIODE_DIRECTION == COL2ROW)
96 101
97static void select_row(uint8_t row) { setPinOutput_writeLow(row_pins[row]); } 102static void select_row(uint8_t row) { setPinOutput_writeLow(row_pins[row]); }
98 103
@@ -111,7 +116,7 @@ __attribute__((weak)) void matrix_init_pins(void) {
111 } 116 }
112} 117}
113 118
114__attribute__((weak)) bool matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row) { 119__attribute__((weak)) void matrix_read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row) {
115 // Start with a clear matrix row 120 // Start with a clear matrix row
116 matrix_row_t current_row_value = 0; 121 matrix_row_t current_row_value = 0;
117 122
@@ -132,15 +137,11 @@ __attribute__((weak)) bool matrix_read_cols_on_row(matrix_row_t current_matrix[]
132 unselect_row(current_row); 137 unselect_row(current_row);
133 matrix_output_unselect_delay(); // wait for all Col signals to go HIGH 138 matrix_output_unselect_delay(); // wait for all Col signals to go HIGH
134 139
135 // If the row has changed, store the row and return the changed flag. 140 // Update the matrix
136 if (current_matrix[current_row] != current_row_value) { 141 current_matrix[current_row] = current_row_value;
137 current_matrix[current_row] = current_row_value;
138 return true;
139 }
140 return false;
141} 142}
142 143
143# elif (DIODE_DIRECTION == ROW2COL) 144# elif (DIODE_DIRECTION == ROW2COL)
144 145
145static void select_col(uint8_t col) { setPinOutput_writeLow(col_pins[col]); } 146static void select_col(uint8_t col) { setPinOutput_writeLow(col_pins[col]); }
146 147
@@ -159,45 +160,32 @@ __attribute__((weak)) void matrix_init_pins(void) {
159 } 160 }
160} 161}
161 162
162__attribute__((weak)) bool matrix_read_rows_on_col(matrix_row_t current_matrix[], uint8_t current_col) { 163__attribute__((weak)) void matrix_read_rows_on_col(matrix_row_t current_matrix[], uint8_t current_col) {
163 bool matrix_changed = false;
164
165 // Select col 164 // Select col
166 select_col(current_col); 165 select_col(current_col);
167 matrix_output_select_delay(); 166 matrix_output_select_delay();
168 167
169 // For each row... 168 // For each row...
170 for (uint8_t row_index = 0; row_index < ROWS_PER_HAND; row_index++) { 169 for (uint8_t row_index = 0; row_index < ROWS_PER_HAND; row_index++) {
171 // Store last value of row prior to reading
172 matrix_row_t last_row_value = current_matrix[row_index];
173 matrix_row_t current_row_value = last_row_value;
174
175 // Check row pin state 170 // Check row pin state
176 if (readPin(row_pins[row_index]) == 0) { 171 if (readPin(row_pins[row_index]) == 0) {
177 // Pin LO, set col bit 172 // Pin LO, set col bit
178 current_row_value |= (MATRIX_ROW_SHIFTER << current_col); 173 current_matrix[row_index] |= (MATRIX_ROW_SHIFTER << current_col);
179 } else { 174 } else {
180 // Pin HI, clear col bit 175 // Pin HI, clear col bit
181 current_row_value &= ~(MATRIX_ROW_SHIFTER << current_col); 176 current_matrix[row_index] &= ~(MATRIX_ROW_SHIFTER << current_col);
182 }
183
184 // Determine if the matrix changed state
185 if ((last_row_value != current_row_value)) {
186 matrix_changed |= true;
187 current_matrix[row_index] = current_row_value;
188 } 177 }
189 } 178 }
190 179
191 // Unselect col 180 // Unselect col
192 unselect_col(current_col); 181 unselect_col(current_col);
193 matrix_output_unselect_delay(); // wait for all Row signals to go HIGH 182 matrix_output_unselect_delay(); // wait for all Row signals to go HIGH
194
195 return matrix_changed;
196} 183}
197 184
198# else 185# else
199# error DIODE_DIRECTION must be one of COL2ROW or ROW2COL! 186# error DIODE_DIRECTION must be one of COL2ROW or ROW2COL!
200# endif 187# endif
188# endif // defined(MATRIX_ROW_PINS) && defined(MATRIX_COL_PINS)
201#else 189#else
202# error DIODE_DIRECTION is not defined! 190# error DIODE_DIRECTION is not defined!
203#endif 191#endif
@@ -288,20 +276,23 @@ bool matrix_post_scan(void) {
288} 276}
289 277
290uint8_t matrix_scan(void) { 278uint8_t matrix_scan(void) {
291 bool local_changed = false; 279 matrix_row_t curr_matrix[MATRIX_ROWS] = {0};
292 280
293#if defined(DIRECT_PINS) || (DIODE_DIRECTION == COL2ROW) 281#if defined(DIRECT_PINS) || (DIODE_DIRECTION == COL2ROW)
294 // Set row, read cols 282 // Set row, read cols
295 for (uint8_t current_row = 0; current_row < ROWS_PER_HAND; current_row++) { 283 for (uint8_t current_row = 0; current_row < ROWS_PER_HAND; current_row++) {
296 local_changed |= matrix_read_cols_on_row(raw_matrix, current_row); 284 matrix_read_cols_on_row(curr_matrix, current_row);
297 } 285 }
298#elif (DIODE_DIRECTION == ROW2COL) 286#elif (DIODE_DIRECTION == ROW2COL)
299 // Set col, read rows 287 // Set col, read rows
300 for (uint8_t current_col = 0; current_col < MATRIX_COLS; current_col++) { 288 for (uint8_t current_col = 0; current_col < MATRIX_COLS; current_col++) {
301 local_changed |= matrix_read_rows_on_col(raw_matrix, current_col); 289 matrix_read_rows_on_col(curr_matrix, current_col);
302 } 290 }
303#endif 291#endif
304 292
293 bool local_changed = memcmp(raw_matrix, curr_matrix, sizeof(curr_matrix)) != 0;
294 if (local_changed) memcpy(raw_matrix, curr_matrix, sizeof(curr_matrix));
295
305 debounce(raw_matrix, matrix + thisHand, ROWS_PER_HAND, local_changed); 296 debounce(raw_matrix, matrix + thisHand, ROWS_PER_HAND, local_changed);
306 297
307 bool remote_changed = matrix_post_scan(); 298 bool remote_changed = matrix_post_scan();