keymap.c (3497B)
- /* Copyright 2023 Tom Parker-Shemilt <palfrey@tevp.net>
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, version 3 of the License.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see <http://www.gnu.org/licenses/>.
- */
- #include <stdlib.h>
- #include QMK_KEYBOARD_H
- // clang-format off
- // Exact keymap is irrelevant as we're using rows/cols
- // but we need _something_ set so we're using no-ops
- const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
- [0] = LAYOUT(
- KC_NO, KC_NO, KC_NO, KC_NO, KC_NO,
- KC_NO, KC_NO, KC_NO, KC_NO, KC_NO,
- KC_NO, KC_NO, KC_NO, KC_NO, KC_NO,
- KC_NO, KC_NO, KC_NO, KC_NO, KC_NO,
- KC_NO, KC_NO, KC_NO, KC_NO, KC_NO
- )};
- bool tiles[5][5] = {
- {false, false, false, false, false},
- {false, false, false, false, false},
- {false, false, false, false, false},
- {false, false, false, false, false},
- {false, false, false, false, false},
- };
- /* Because snake pattern of leds */
- const uint8_t remap[25] = {
- 20,21,22,23,24,
- 19,6,7,8,9,
- 18,5,0,1,10,
- 17,4,3,2,11,
- 16,15,14,13,12,
- };
- // clang-format on
- bool is_blank(void) {
- for (uint8_t y = 0; y < 5; y++) {
- for (uint8_t x = 0; x < 5; x++) {
- if (tiles[x][y]) {
- return false;
- }
- }
- }
- return true;
- }
- void do_move(uint8_t x, uint8_t y) {
- tiles[x][y] ^= true;
- if (x > 0) {
- tiles[x - 1][y] ^= true;
- }
- if (y > 0) {
- tiles[x][y - 1] ^= true;
- }
- if (x < 4) {
- tiles[x + 1][y] ^= true;
- }
- if (y < 4) {
- tiles[x][y + 1] ^= true;
- }
- }
- void refresh_leds(void) {
- for (uint8_t y = 0; y < 5; y++) {
- for (uint8_t x = 0; x < 5; x++) {
- uint8_t tile = tiles[x][y];
- uint8_t index = (y * 5) + x;
- if (tile) {
- rgblight_setrgb_at(RGB_RED, remap[index]);
- } else {
- rgblight_setrgb_at(RGB_WHITE, remap[index]);
- }
- }
- }
- rgblight_set();
- }
- uint8_t initial_moves = 1;
- void start_game(void) {
- rgblight_mode(RGBLIGHT_MODE_STATIC_LIGHT);
- srand(timer_read32());
- while (true) {
- for (uint8_t i = 0; i < initial_moves; i++) {
- do_move(rand() % 5, rand() % 5);
- }
- if (!is_blank()) {
- // Catch the "we picked the same location 2*N times" case
- break;
- }
- }
- refresh_leds();
- }
- void keyboard_post_init_user(void) {
- rgblight_enable_noeeprom();
- start_game();
- }
- bool won = false;
- bool process_record_user(uint16_t keycode, keyrecord_t *record) {
- if (record->event.pressed) {
- if (won) {
- initial_moves++;
- won = false;
- start_game();
- } else {
- uint8_t x = record->event.key.col;
- uint8_t y = record->event.key.row;
- do_move(x, y);
- if (is_blank()) {
- rgblight_mode(RGBLIGHT_MODE_RAINBOW_SWIRL);
- won = true;
- }
- }
- }
- refresh_leds();
- return true;
- }