diff options
| author | unknown <itsaferbie@gmail.com> | 2017-08-26 13:54:17 -0400 |
|---|---|---|
| committer | Jack Humbert <jack.humb@gmail.com> | 2017-08-26 23:31:47 -0400 |
| commit | 78ab926cc8e2cda53f177eba586053b42797d341 (patch) | |
| tree | 7f3d6161180d2959e999094c1093c959c29cfc67 /keyboards/deltasplit75/matrix.c | |
| parent | b28982e329c790d42369d0669b55128eb89a62f4 (diff) | |
| download | qmk_firmware-78ab926cc8e2cda53f177eba586053b42797d341.tar.gz qmk_firmware-78ab926cc8e2cda53f177eba586053b42797d341.zip | |
Updated my files and added debouncing
Diffstat (limited to 'keyboards/deltasplit75/matrix.c')
| -rw-r--r-- | keyboards/deltasplit75/matrix.c | 244 |
1 files changed, 195 insertions, 49 deletions
diff --git a/keyboards/deltasplit75/matrix.c b/keyboards/deltasplit75/matrix.c index 138969004..4def27239 100644 --- a/keyboards/deltasplit75/matrix.c +++ b/keyboards/deltasplit75/matrix.c | |||
| @@ -21,9 +21,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
| 21 | #include <stdint.h> | 21 | #include <stdint.h> |
| 22 | #include <stdbool.h> | 22 | #include <stdbool.h> |
| 23 | #include <avr/io.h> | 23 | #include <avr/io.h> |
| 24 | #include <avr/wdt.h> | 24 | #include "wait.h" |
| 25 | #include <avr/interrupt.h> | ||
| 26 | #include <util/delay.h> | ||
| 27 | #include "print.h" | 25 | #include "print.h" |
| 28 | #include "debug.h" | 26 | #include "debug.h" |
| 29 | #include "util.h" | 27 | #include "util.h" |
| @@ -31,6 +29,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
| 31 | #include "split_util.h" | 29 | #include "split_util.h" |
| 32 | #include "pro_micro.h" | 30 | #include "pro_micro.h" |
| 33 | #include "config.h" | 31 | #include "config.h" |
| 32 | #include "timer.h" | ||
| 34 | 33 | ||
| 35 | #ifdef USE_I2C | 34 | #ifdef USE_I2C |
| 36 | # include "i2c.h" | 35 | # include "i2c.h" |
| @@ -38,14 +37,29 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. | |||
| 38 | # include "serial.h" | 37 | # include "serial.h" |
| 39 | #endif | 38 | #endif |
| 40 | 39 | ||
| 41 | #ifndef DEBOUNCE | 40 | #ifndef DEBOUNCING_DELAY |
| 42 | # define DEBOUNCE 5 | 41 | # define DEBOUNCING_DELAY 5 |
| 43 | #endif | 42 | #endif |
| 44 | 43 | ||
| 44 | #if (DEBOUNCING_DELAY > 0) | ||
| 45 | static uint16_t debouncing_time; | ||
| 46 | static bool debouncing = false; | ||
| 47 | #endif | ||
| 48 | |||
| 49 | #if (MATRIX_COLS <= 8) | ||
| 50 | # define print_matrix_header() print("\nr/c 01234567\n") | ||
| 51 | # define print_matrix_row(row) print_bin_reverse8(matrix_get_row(row)) | ||
| 52 | # define matrix_bitpop(i) bitpop(matrix[i]) | ||
| 53 | # define ROW_SHIFTER ((uint8_t)1) | ||
| 54 | #else | ||
| 55 | # error "Currently only supports 8 COLS" | ||
| 56 | #endif | ||
| 57 | static matrix_row_t matrix_debouncing[MATRIX_ROWS]; | ||
| 58 | |||
| 45 | #define ERROR_DISCONNECT_COUNT 5 | 59 | #define ERROR_DISCONNECT_COUNT 5 |
| 46 | 60 | ||
| 47 | static uint8_t debouncing = DEBOUNCE; | 61 | #define ROWS_PER_HAND (MATRIX_ROWS/2) |
| 48 | static const int ROWS_PER_HAND = MATRIX_ROWS/2; | 62 | |
| 49 | static uint8_t error_count = 0; | 63 | static uint8_t error_count = 0; |
| 50 | 64 | ||
| 51 | static const uint8_t row_pins[MATRIX_ROWS] = MATRIX_ROW_PINS; | 65 | static const uint8_t row_pins[MATRIX_ROWS] = MATRIX_ROW_PINS; |
| @@ -55,11 +69,19 @@ static const uint8_t col_pins[MATRIX_COLS] = MATRIX_COL_PINS; | |||
| 55 | static matrix_row_t matrix[MATRIX_ROWS]; | 69 | static matrix_row_t matrix[MATRIX_ROWS]; |
| 56 | static matrix_row_t matrix_debouncing[MATRIX_ROWS]; | 70 | static matrix_row_t matrix_debouncing[MATRIX_ROWS]; |
| 57 | 71 | ||
| 58 | static matrix_row_t read_cols(void); | 72 | #if (DIODE_DIRECTION == COL2ROW) |
| 59 | static void init_cols(void); | 73 | static void init_cols(void); |
| 60 | static void unselect_rows(void); | 74 | static bool read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row); |
| 61 | static void select_row(uint8_t row); | 75 | static void unselect_rows(void); |
| 62 | 76 | static void select_row(uint8_t row); | |
| 77 | static void unselect_row(uint8_t row); | ||
| 78 | #elif (DIODE_DIRECTION == ROW2COL) | ||
| 79 | static void init_rows(void); | ||
| 80 | static bool read_rows_on_col(matrix_row_t current_matrix[], uint8_t current_col); | ||
| 81 | static void unselect_cols(void); | ||
| 82 | static void unselect_col(uint8_t col); | ||
| 83 | static void select_col(uint8_t col); | ||
| 84 | #endif | ||
| 63 | __attribute__ ((weak)) | 85 | __attribute__ ((weak)) |
| 64 | void matrix_init_quantum(void) { | 86 | void matrix_init_quantum(void) { |
| 65 | matrix_init_kb(); | 87 | matrix_init_kb(); |
| @@ -118,33 +140,54 @@ void matrix_init(void) | |||
| 118 | } | 140 | } |
| 119 | 141 | ||
| 120 | matrix_init_quantum(); | 142 | matrix_init_quantum(); |
| 143 | |||
| 121 | } | 144 | } |
| 122 | 145 | ||
| 123 | uint8_t _matrix_scan(void) | 146 | uint8_t _matrix_scan(void) |
| 124 | { | 147 | { |
| 125 | // Right hand is stored after the left in the matirx so, we need to offset it | ||
| 126 | int offset = isLeftHand ? 0 : (ROWS_PER_HAND); | 148 | int offset = isLeftHand ? 0 : (ROWS_PER_HAND); |
| 149 | #if (DIODE_DIRECTION == COL2ROW) | ||
| 150 | // Set row, read cols | ||
| 151 | for (uint8_t current_row = 0; current_row < ROWS_PER_HAND; current_row++) { | ||
| 152 | # if (DEBOUNCING_DELAY > 0) | ||
| 153 | bool matrix_changed = read_cols_on_row(matrix_debouncing+offset, current_row); | ||
| 154 | |||
| 155 | if (matrix_changed) { | ||
| 156 | debouncing = true; | ||
| 157 | debouncing_time = timer_read(); | ||
| 158 | PORTD ^= (1 << 2); | ||
| 159 | } | ||
| 160 | |||
| 161 | # else | ||
| 162 | read_cols_on_row(matrix+offset, current_row); | ||
| 163 | # endif | ||
| 164 | |||
| 165 | } | ||
| 166 | |||
| 167 | #elif (DIODE_DIRECTION == ROW2COL) | ||
| 168 | // Set col, read rows | ||
| 169 | for (uint8_t current_col = 0; current_col < MATRIX_COLS; current_col++) { | ||
| 170 | # if (DEBOUNCING_DELAY > 0) | ||
| 171 | bool matrix_changed = read_rows_on_col(matrix_debouncing+offset, current_col); | ||
| 172 | if (matrix_changed) { | ||
| 173 | debouncing = true; | ||
| 174 | debouncing_time = timer_read(); | ||
| 175 | } | ||
| 176 | # else | ||
| 177 | read_rows_on_col(matrix+offset, current_col); | ||
| 178 | # endif | ||
| 127 | 179 | ||
| 128 | for (uint8_t i = 0; i < ROWS_PER_HAND; i++) { | ||
| 129 | select_row(i); | ||
| 130 | _delay_us(30); // without this wait read unstable value. | ||
| 131 | matrix_row_t cols = read_cols(); | ||
| 132 | if (matrix_debouncing[i+offset] != cols) { | ||
| 133 | matrix_debouncing[i+offset] = cols; | ||
| 134 | debouncing = DEBOUNCE; | ||
| 135 | } | ||
| 136 | unselect_rows(); | ||
| 137 | } | 180 | } |
| 181 | #endif | ||
| 138 | 182 | ||
| 139 | if (debouncing) { | 183 | # if (DEBOUNCING_DELAY > 0) |
| 140 | if (--debouncing) { | 184 | if (debouncing && (timer_elapsed(debouncing_time) > DEBOUNCING_DELAY)) { |
| 141 | _delay_ms(1); | ||
| 142 | } else { | ||
| 143 | for (uint8_t i = 0; i < ROWS_PER_HAND; i++) { | 185 | for (uint8_t i = 0; i < ROWS_PER_HAND; i++) { |
| 144 | matrix[i+offset] = matrix_debouncing[i+offset]; | 186 | matrix[i+offset] = matrix_debouncing[i+offset]; |
| 145 | } | 187 | } |
| 188 | debouncing = false; | ||
| 146 | } | 189 | } |
| 147 | } | 190 | # endif |
| 148 | 191 | ||
| 149 | return 1; | 192 | return 1; |
| 150 | } | 193 | } |
| @@ -200,9 +243,7 @@ int serial_transaction(void) { | |||
| 200 | 243 | ||
| 201 | uint8_t matrix_scan(void) | 244 | uint8_t matrix_scan(void) |
| 202 | { | 245 | { |
| 203 | int ret = _matrix_scan(); | 246 | uint8_t ret = _matrix_scan(); |
| 204 | |||
| 205 | |||
| 206 | 247 | ||
| 207 | #ifdef USE_I2C | 248 | #ifdef USE_I2C |
| 208 | if( i2c_transaction() ) { | 249 | if( i2c_transaction() ) { |
| @@ -226,20 +267,17 @@ uint8_t matrix_scan(void) | |||
| 226 | TXLED0; | 267 | TXLED0; |
| 227 | error_count = 0; | 268 | error_count = 0; |
| 228 | } | 269 | } |
| 229 | |||
| 230 | matrix_scan_quantum(); | 270 | matrix_scan_quantum(); |
| 231 | |||
| 232 | return ret; | 271 | return ret; |
| 233 | } | 272 | } |
| 234 | 273 | ||
| 235 | void matrix_slave_scan(void) { | 274 | void matrix_slave_scan(void) { |
| 236 | _matrix_scan(); | 275 | _matrix_scan(); |
| 237 | 276 | ||
| 238 | int offset = (isLeftHand) ? 0 : (MATRIX_ROWS / 2); | 277 | int offset = (isLeftHand) ? 0 : ROWS_PER_HAND; |
| 239 | 278 | ||
| 240 | #ifdef USE_I2C | 279 | #ifdef USE_I2C |
| 241 | for (int i = 0; i < ROWS_PER_HAND; ++i) { | 280 | for (int i = 0; i < ROWS_PER_HAND; ++i) { |
| 242 | /* i2c_slave_buffer[i] = matrix[offset+i]; */ | ||
| 243 | i2c_slave_buffer[i] = matrix[offset+i]; | 281 | i2c_slave_buffer[i] = matrix[offset+i]; |
| 244 | } | 282 | } |
| 245 | #else // USE_SERIAL | 283 | #else // USE_SERIAL |
| @@ -286,33 +324,141 @@ uint8_t matrix_key_count(void) | |||
| 286 | return count; | 324 | return count; |
| 287 | } | 325 | } |
| 288 | 326 | ||
| 289 | static void init_cols(void) | 327 | #if (DIODE_DIRECTION == COL2ROW) |
| 328 | |||
| 329 | static void init_cols(void) | ||
| 290 | { | 330 | { |
| 291 | for(int x = 0; x < MATRIX_COLS; x++) { | 331 | for(uint8_t x = 0; x < MATRIX_COLS; x++) { |
| 292 | _SFR_IO8((col_pins[x] >> 4) + 1) &= ~_BV(col_pins[x] & 0xF); | 332 | uint8_t pin = col_pins[x]; |
| 293 | _SFR_IO8((col_pins[x] >> 4) + 2) |= _BV(col_pins[x] & 0xF); | 333 | _SFR_IO8((pin >> 4) + 1) &= ~_BV(pin & 0xF); // IN |
| 334 | _SFR_IO8((pin >> 4) + 2) |= _BV(pin & 0xF); // HI | ||
| 294 | } | 335 | } |
| 295 | } | 336 | } |
| 296 | 337 | ||
| 297 | static matrix_row_t read_cols(void) | 338 | static bool read_cols_on_row(matrix_row_t current_matrix[], uint8_t current_row) |
| 298 | { | 339 | { |
| 299 | matrix_row_t result = 0; | 340 | // Store last value of row prior to reading |
| 300 | for(int x = 0; x < MATRIX_COLS; x++) { | 341 | matrix_row_t last_row_value = current_matrix[current_row]; |
| 301 | result |= (_SFR_IO8(col_pins[x] >> 4) & _BV(col_pins[x] & 0xF)) ? 0 : (1 << x); | 342 | |
| 343 | // Clear data in matrix row | ||
| 344 | current_matrix[current_row] = 0; | ||
| 345 | |||
| 346 | // Select row and wait for row selecton to stabilize | ||
| 347 | select_row(current_row); | ||
| 348 | wait_us(30); | ||
| 349 | |||
| 350 | // For each col... | ||
| 351 | for(uint8_t col_index = 0; col_index < MATRIX_COLS; col_index++) { | ||
| 352 | |||
| 353 | // Select the col pin to read (active low) | ||
| 354 | uint8_t pin = col_pins[col_index]; | ||
| 355 | uint8_t pin_state = (_SFR_IO8(pin >> 4) & _BV(pin & 0xF)); | ||
| 356 | |||
| 357 | // Populate the matrix row with the state of the col pin | ||
| 358 | current_matrix[current_row] |= pin_state ? 0 : (ROW_SHIFTER << col_index); | ||
| 302 | } | 359 | } |
| 303 | return result; | 360 | |
| 361 | // Unselect row | ||
| 362 | unselect_row(current_row); | ||
| 363 | |||
| 364 | return (last_row_value != current_matrix[current_row]); | ||
| 365 | } | ||
| 366 | |||
| 367 | static void select_row(uint8_t row) | ||
| 368 | { | ||
| 369 | uint8_t pin = row_pins[row]; | ||
| 370 | _SFR_IO8((pin >> 4) + 1) |= _BV(pin & 0xF); // OUT | ||
| 371 | _SFR_IO8((pin >> 4) + 2) &= ~_BV(pin & 0xF); // LOW | ||
| 372 | } | ||
| 373 | |||
| 374 | static void unselect_row(uint8_t row) | ||
| 375 | { | ||
| 376 | uint8_t pin = row_pins[row]; | ||
| 377 | _SFR_IO8((pin >> 4) + 1) &= ~_BV(pin & 0xF); // IN | ||
| 378 | _SFR_IO8((pin >> 4) + 2) |= _BV(pin & 0xF); // HI | ||
| 304 | } | 379 | } |
| 305 | 380 | ||
| 306 | static void unselect_rows(void) | 381 | static void unselect_rows(void) |
| 307 | { | 382 | { |
| 308 | for(int x = 0; x < ROWS_PER_HAND; x++) { | 383 | for(uint8_t x = 0; x < ROWS_PER_HAND; x++) { |
| 309 | _SFR_IO8((row_pins[x] >> 4) + 1) &= ~_BV(row_pins[x] & 0xF); | 384 | uint8_t pin = row_pins[x]; |
| 310 | _SFR_IO8((row_pins[x] >> 4) + 2) |= _BV(row_pins[x] & 0xF); | 385 | _SFR_IO8((pin >> 4) + 1) &= ~_BV(pin & 0xF); // IN |
| 386 | _SFR_IO8((pin >> 4) + 2) |= _BV(pin & 0xF); // HI | ||
| 311 | } | 387 | } |
| 312 | } | 388 | } |
| 313 | 389 | ||
| 314 | static void select_row(uint8_t row) | 390 | #elif (DIODE_DIRECTION == ROW2COL) |
| 391 | |||
| 392 | static void init_rows(void) | ||
| 315 | { | 393 | { |
| 316 | _SFR_IO8((row_pins[row] >> 4) + 1) |= _BV(row_pins[row] & 0xF); | 394 | for(uint8_t x = 0; x < ROWS_PER_HAND; x++) { |
| 317 | _SFR_IO8((row_pins[row] >> 4) + 2) &= ~_BV(row_pins[row] & 0xF); | 395 | uint8_t pin = row_pins[x]; |
| 396 | _SFR_IO8((pin >> 4) + 1) &= ~_BV(pin & 0xF); // IN | ||
| 397 | _SFR_IO8((pin >> 4) + 2) |= _BV(pin & 0xF); // HI | ||
| 398 | } | ||
| 318 | } | 399 | } |
| 400 | |||
| 401 | static bool read_rows_on_col(matrix_row_t current_matrix[], uint8_t current_col) | ||
| 402 | { | ||
| 403 | bool matrix_changed = false; | ||
| 404 | |||
| 405 | // Select col and wait for col selecton to stabilize | ||
| 406 | select_col(current_col); | ||
| 407 | wait_us(30); | ||
| 408 | |||
| 409 | // For each row... | ||
| 410 | for(uint8_t row_index = 0; row_index < ROWS_PER_HAND; row_index++) | ||
| 411 | { | ||
| 412 | |||
| 413 | // Store last value of row prior to reading | ||
| 414 | matrix_row_t last_row_value = current_matrix[row_index]; | ||
| 415 | |||
| 416 | // Check row pin state | ||
| 417 | if ((_SFR_IO8(row_pins[row_index] >> 4) & _BV(row_pins[row_index] & 0xF)) == 0) | ||
| 418 | { | ||
| 419 | // Pin LO, set col bit | ||
| 420 | current_matrix[row_index] |= (ROW_SHIFTER << current_col); | ||
| 421 | } | ||
| 422 | else | ||
| 423 | { | ||
| 424 | // Pin HI, clear col bit | ||
| 425 | current_matrix[row_index] &= ~(ROW_SHIFTER << current_col); | ||
| 426 | } | ||
| 427 | |||
| 428 | // Determine if the matrix changed state | ||
| 429 | if ((last_row_value != current_matrix[row_index]) && !(matrix_changed)) | ||
| 430 | { | ||
| 431 | matrix_changed = true; | ||
| 432 | } | ||
| 433 | } | ||
| 434 | |||
| 435 | // Unselect col | ||
| 436 | unselect_col(current_col); | ||
| 437 | |||
| 438 | return matrix_changed; | ||
| 439 | } | ||
| 440 | |||
| 441 | static void select_col(uint8_t col) | ||
| 442 | { | ||
| 443 | uint8_t pin = col_pins[col]; | ||
| 444 | _SFR_IO8((pin >> 4) + 1) |= _BV(pin & 0xF); // OUT | ||
| 445 | _SFR_IO8((pin >> 4) + 2) &= ~_BV(pin & 0xF); // LOW | ||
| 446 | } | ||
| 447 | |||
| 448 | static void unselect_col(uint8_t col) | ||
| 449 | { | ||
| 450 | uint8_t pin = col_pins[col]; | ||
| 451 | _SFR_IO8((pin >> 4) + 1) &= ~_BV(pin & 0xF); // IN | ||
| 452 | _SFR_IO8((pin >> 4) + 2) |= _BV(pin & 0xF); // HI | ||
| 453 | } | ||
| 454 | |||
| 455 | static void unselect_cols(void) | ||
| 456 | { | ||
| 457 | for(uint8_t x = 0; x < MATRIX_COLS; x++) { | ||
| 458 | uint8_t pin = col_pins[x]; | ||
| 459 | _SFR_IO8((pin >> 4) + 1) &= ~_BV(pin & 0xF); // IN | ||
| 460 | _SFR_IO8((pin >> 4) + 2) |= _BV(pin & 0xF); // HI | ||
| 461 | } | ||
| 462 | } | ||
| 463 | |||
| 464 | #endif | ||
