aboutsummaryrefslogtreecommitdiff
path: root/keyboards/planck/keymaps/rootiest/keymap.c
diff options
context:
space:
mode:
Diffstat (limited to 'keyboards/planck/keymaps/rootiest/keymap.c')
-rw-r--r--keyboards/planck/keymaps/rootiest/keymap.c1928
1 files changed, 1928 insertions, 0 deletions
diff --git a/keyboards/planck/keymaps/rootiest/keymap.c b/keyboards/planck/keymaps/rootiest/keymap.c
new file mode 100644
index 000000000..634bf2829
--- /dev/null
+++ b/keyboards/planck/keymaps/rootiest/keymap.c
@@ -0,0 +1,1928 @@
1/* Copyright 2021 Chris Laprade
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#include QMK_KEYBOARD_H
18#include "raw_hid.h"
19#include "print.h"
20#include "muse.h"
21
22/*
23 * Define keyboard name to be used by UI.
24 * This allows for using a different name
25 * than the one defined by QMK for your board.
26 */
27#define KEEB_MODEL_NAME "The Rootiest BoogieBoard"
28
29// Give names to the layers so they are easier to reference
30enum custom_layers {
31 _BASE,
32 _QWERTY = _BASE,
33 _COLEMAK,
34 _DVORAK,
35 _SYMBLS,
36 _RAISE = _SYMBLS,
37 _NUMBRS,
38 _LOWER = _NUMBRS,
39 _PLOVER,
40 _FEATURS,
41 _ADJUST = _FEATURS,
42 _NUMPD,
43 _TABULA,
44 _MOUSY,
45};
46
47#define LOWER MO(_NUMBRS)
48#define RAISE MO(_SYMBLS)
49
50// unicode hexes
51#define UC_DEG UC(0x00B0) // °
52#define UC_DEGF UC(0x2109) // ℉
53
54// Time (ms) to wait between frames for the wake rgb animation
55#define WAKE_ANIMATION_TIMER_FREQUENCY 50
56
57// Is a display connected
58// #define USING_OLED_DISPLAY false
59
60// wait DELAY ms before unregistering media keys
61#define TAP_CODE_DELAY 10
62
63// Modifier remover
64#define WITHOUT_MODS(...) \
65 do { \
66 const uint8_t _real_mods = get_mods(); \
67 clear_mods(); \
68 {__VA_ARGS__} set_mods(_real_mods); \
69 } while (0)
70
71// A whole boatload of audio "songs" defined for use by the keyboard
72#ifdef AUDIO_ENABLE
73float planck_song[][2] = SONG(PLANCK_SOUND);
74float hello_song[][2] = SONG(ONE_UP_SOUND2);
75float bye_song[][2] = SONG(GOODBYE_SOUND);
76float num_song[][2] = SONG(DVORAK_SOUND);
77float qwerty_song[][2] = SONG(QWERTY_SOUND);
78float colemak_song[][2] = SONG(COLEMAK_SOUND);
79float dvorak_song[][2] = SONG(DVORAK_SOUND);
80float funk_song[][2] = SONG(COLEMAK_SOUND);
81float workman_song[][2] = SONG(WORKMAN_SOUND);
82float term_song[][2] = SONG(TERMINAL_SOUND);
83float lover_song[][2] = SONG(PLOVER_SOUND);
84float ode_song[][2] = SONG(ODE_TO_JOY);
85float rock_song[][2] = SONG(ROCK_A_BYE_BABY);
86float clue_song[][2] = SONG(CLUEBOARD_SOUND);
87float camp_song[][2] = SONG(CAMPANELLA);
88float imp_march_song[][2] = SONG(IMPERIAL_MARCH);
89float gameover_song[][2] = SONG(MARIO_GAMEOVER);
90float puzzle_song[][2] = SONG(ZELDA_PUZZLE2);
91float caps_on[][2] = SONG(CAPS_LOCK_ON_SOUND);
92float caps_off[][2] = SONG(CAPS_LOCK_OFF_SOUND);
93float slctl_on[][2] = SONG(SCROLL_LOCK_ON_SOUND);
94float slctl_off[][2] = SONG(SCROLL_LOCK_OFF_SOUND);
95float slalt_on[][2] = SONG(NUM_LOCK_ON_SOUND);
96float slalt_off[][2] = SONG(NUM_LOCK_OFF_SOUND);
97float leader_started[][2] = SONG(LEAD_START_SOUND);
98float leader_succeed[][2] = SONG(LEAD_SUCCESS_SOUND);
99float leader_fail[][2] = SONG(LEAD_FAIL_SOUND);
100float plover_song[][2] = SONG(PLOVER_SOUND);
101float plover_gb_song[][2] = SONG(PLOVER_GOODBYE_SOUND);
102#endif
103
104// Declare stored memory config
105typedef union {
106 uint32_t raw;
107 struct {
108 bool do_wakeup_animation : 1;
109 uint8_t rgbcon_tracker : 8;
110 bool do_wakeup_audio : 1;
111 };
112} user_config_t;
113
114user_config_t user_config;
115
116// Initialize variable holding the binary
117// representation of active modifiers.
118uint8_t mod_state = 0;
119
120// Declare custom keycodes
121enum custom_keycodes {
122 MO_BASE = SAFE_RANGE,
123 MO_SYMBLS,
124 MO_NUMBRS,
125 MO_FEATURS,
126 QWERTY,
127 COLEMAK,
128 DVORAK,
129 PLOVER,
130 BACKLIT,
131 MUSIC_ON,
132 MUSIC_OFF,
133 EXT_PLV,
134 MY_RGBCON,
135 MY_DEGREES,
136 ALT_TAB,
137 PRINT_WPM_KEY,
138 IRONY,
139 WAKE_ANI_TOG,
140 WAKE_AUD_TOG,
141 DO_RESET,
142 KC_PRVWD,
143 KC_NXTWD,
144 KC_LSTRT,
145 KC_LEND,
146 KC_DLINE,
147 KC_REDO,
148 KC_SAVE,
149 KC_SLCTALL,
150 KC_ALTF4,
151 KC_KILL,
152 KC_LCUT,
153 KC_LCOPY,
154 KC_NXTAB,
155 KC_PRVTAB,
156};
157
158// Declare unicode map array
159enum unicode_names { BANG, SNEK };
160const uint32_t PROGMEM unicode_map[] = {
161 //[UCD_BANG] = 0x203D, // ‽
162 //[UCD_IRONY] = 0x2E2E, // ⸮
163 [SNEK] = 0x1F40D, // 🐍
164};
165
166enum combo_events { ZC_COPY, XV_PASTE };
167
168const uint16_t PROGMEM copy_combo[] = {KC_Z, KC_C, COMBO_END};
169const uint16_t PROGMEM paste_combo[] = {KC_X, KC_V, COMBO_END};
170
171combo_t key_combos[COMBO_COUNT] = {
172 [ZC_COPY] = COMBO_ACTION(copy_combo),
173 [XV_PASTE] = COMBO_ACTION(paste_combo),
174};
175
176// Tap Dance key declarations
177enum {
178 TD_DEG_DEGF,
179 TD_SMILEY,
180 TD_LSHFT_CAPS,
181 TD_LCTL_STICKY,
182 TD_LALT_STICKY,
183 TD_LOWER,
184 TD_RAISE,
185};
186
187// Declare available Tap-Dance states
188typedef enum {
189 TD_NONE,
190 TD_SINGLE_TAP,
191 TD_DOUBLE_TAP,
192 TD_TRIPLE_TAP,
193 TD_DOUBLE_SINGLE_TAP,
194 TD_SINGLE_HOLD,
195 TD_DOUBLE_HOLD,
196 TD_TRIPLE_HOLD,
197 TD_UNKNOWN,
198} td_state_t;
199
200// Tap-Dance struct
201typedef struct {
202 bool is_press_action;
203 td_state_t state;
204} td_tap_t;
205
206// Whether or not to do the wake animation+sound
207bool do_wake_animation;
208
209// Variable to keep track of the rgb mode assigned by the RGB_CON key
210static uint8_t rgbcon_tracker = 0;
211
212// Used by the on-board WPM tracker
213char wpm_str[12];
214
215// Variables used for the alt-tab key
216bool is_alt_tab_active = false;
217uint16_t alt_tab_timer = 0;
218
219// Variables used by the Irony key
220#define IRONY_HOLD_DELAY 500
221uint16_t irony_pressed_time;
222bool irony_active = false;
223bool irony_shifted = false;
224char irony_str[4] = "⸮";
225char bang_str[4] = "‽";
226
227// Variables used for the rgb wakeup animation
228static uint16_t wake_rgb_timer;
229static uint8_t wake_rgb_count = 0;
230bool waking_up = false;
231bool do_wake_audio = false;
232
233// Muse variables
234bool muse_mode = false;
235bool musical_mode = false;
236uint8_t last_muse_note = 0;
237uint16_t muse_counter = 0;
238uint8_t muse_offset = 70;
239uint16_t muse_tempo = 50;
240
241// Used by Leader key chords
242bool did_leader_succeed;
243LEADER_EXTERNS();
244
245// Tap-Dance stuffs, initializing functions that are coded further below
246td_state_t cur_dance(qk_tap_dance_state_t* state);
247void sml_finished(qk_tap_dance_state_t* state, void* user_data);
248void sml_reset(qk_tap_dance_state_t* state, void* user_data);
249void scap_finished(qk_tap_dance_state_t* state, void* user_data);
250void scap_reset(qk_tap_dance_state_t* state, void* user_data);
251void slctl_finished(qk_tap_dance_state_t* state, void* user_data);
252void slctl_reset(qk_tap_dance_state_t* state, void* user_data);
253void slalt_finished(qk_tap_dance_state_t* state, void* user_data);
254void slalt_reset(qk_tap_dance_state_t* state, void* user_data);
255bool lctl_sticky = false;
256bool lalt_sticky = false;
257
258// This function is called when lock indicators (caps-lock led) are changed/toggled/updated
259bool led_update_user(led_t led_state) {
260 rgblight_set_layer_state(10, led_state.caps_lock);
261#ifdef AUDIO_ENABLE
262 static uint8_t caps_state = 0;
263 if (caps_state != led_state.caps_lock) {
264 // When the caps-lock led state changes play sounds
265 led_state.caps_lock ? PLAY_SONG(caps_on) : PLAY_SONG(caps_off);
266 caps_state = led_state.caps_lock;
267 }
268#endif
269 return true;
270}
271
272// Define key layout/layers
273const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { // Define all the layers
274 [_BASE] = LAYOUT_planck_mit( //
275 KC_GESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC, //
276 LT(_TABULA, KC_TAB), KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT, //
277 TD(TD_LSHFT_CAPS), KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_SFTENT, //
278 TD(TD_LCTL_STICKY), KC_LEAD, KC_LGUI, TD(TD_LALT_STICKY), MO(_SYMBLS), KC_SPC, MO(_NUMBRS), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT),
279 /*
280 Base Layer [0]
281 * ,-----------------------------------------------------------------------------------.
282 * |Gr/ESC| Q | W | E | R | T | Y | U | I | O | P |BckSpc|
283 * |------+------+------+------+------+------+------+------+------+------+------+------|
284 * |Tabula| A | S | D | F | G | H | J | K | L | ; | ' |
285 * |------+------+------+------+------+------+------+------+------+------+------+------|
286 * |SH/CAP| Z | X | C | V | B | N | M | , | . | / |Enter |
287 * |------+------+------+------+------+------+------+------+------+------+------+------|
288 * | LCtrl|Leader| OS | Alt |Symbol| Space |Number| Left | Dwn | Up | Right|
289 * `-----------------------------------------------------------------------------------'
290 */
291
292 [_COLEMAK] = LAYOUT_planck_mit( //
293 KC_GESC, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC, //
294 LT(_TABULA, KC_TAB), KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT, //
295 TD(TD_LSHFT_CAPS), KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_SFTENT, //
296 TD(TD_LCTL_STICKY), KC_LEAD, KC_LGUI, TD(TD_LALT_STICKY), MO(_SYMBLS), KC_SPC, MO(_NUMBRS), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT),
297 /*
298 Colemak Layer [1]
299 * ,-----------------------------------------------------------------------------------.
300 * |Gr/ESC| Q | W | F | P | G | J | L | U | Y | ; | Bksp |
301 * |------+------+------+------+------+------+------+------+------+------+------+------|
302 * |Tabula| A | R | S | T | D | H | N | E | I | O | " |
303 * |------+------+------+------+------+------+------+------+------+------+------+------|
304 * |SH/CAP| Z | X | C | V | B | K | M | , | . | / |Enter |
305 * |------+------+------+------+------+------+------+------+------+------+------+------|
306 * | LCtrl|Leader| OS | Alt |Symbol| Space |Number| Left | Dwn | Up | Right|
307 * `-----------------------------------------------------------------------------------'
308 */
309
310 [_DVORAK] = LAYOUT_planck_mit( //
311 KC_GESC, KC_QUOT, KC_COMM, KC_DOT, KC_P, KC_Y, KC_F, KC_G, KC_C, KC_R, KC_L, KC_BSPC, //
312 LT(_TABULA, KC_TAB), KC_A, KC_O, KC_E, KC_U, KC_I, KC_D, KC_H, KC_T, KC_TRNS, KC_S, KC_SLSH, //
313 TD(TD_LSHFT_CAPS), KC_SCLN, KC_Q, KC_J, KC_K, KC_X, KC_B, KC_M, KC_W, KC_V, KC_Z, KC_SFTENT, //
314 TD(TD_LCTL_STICKY), KC_LEAD, KC_LGUI, TD(TD_LALT_STICKY), MO(_SYMBLS), KC_SPC, MO(_NUMBRS), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT),
315 /* Dvorak Layer [2]
316 * ,-----------------------------------------------------------------------------------.
317 * |Gr/ESC| " | , | . | P | Y | F | G | C | R | L | Bksp |
318 * |------+------+------+------+------+------+------+------+------+------+------+------|
319 * |Tabula| A | O | E | U | I | D | H | T | N | S | / |
320 * |------+------+------+------+------+------+------+------+------+------+------+------|
321 * |SH/CAP| ; | Q | J | K | X | B | M | W | V | Z |Enter |
322 * |------+------+------+------+------+------+------+------+------+------+------+------|
323 * | LCtrl|Leader| OS | Alt |Symbol| Space |Number| Left | Dwn | Up | Right|
324 * `-----------------------------------------------------------------------------------'
325 */
326 [_SYMBLS] = LAYOUT_planck_mit( //
327 KC_MPLY, KC_EXLM, KC_AT, KC_HASH, KC_DLR, KC_PERC, KC_CIRC, KC_AMPR, KC_ASTR, KC_LPRN, KC_RPRN, KC_BSPC, //
328 KC_DEL, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_UNDS, KC_PLUS, KC_LCBR, KC_RCBR, KC_PIPE, //
329 KC_TRNS, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, LSFT(KC_LCTL), LSFT(KC_LCTL), KC_HOME, KC_END, KC_TRNS, //
330 TG(_NUMPD), KC_TRNS, KC_TRNS, KC_TRNS, TO(_BASE), KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY),
331 /*
332 Symbols Layer [3]
333 * ,-----------------------------------------------------------------------------------.
334 * | Play | ! | @ | # | $ | % | ^ | & | * | ( | ) |BckSpc|
335 * |------+------+------+------+------+------+------+------+------+------+------+------|
336 * |Delete| F1 | F2 | F3 | F4 | F5 | F6 | _ | + | { | } | | |
337 * |------+------+------+------+------+------+------+------+------+------+------+------|
338 * | Shift| F7 | F8 | F9 | F10 | F11 | F12 |LShLCt|LShLCt| Home | End |------|
339 * |------+------+------+------+------+------+------+------+------+------+------+------|
340 * | TG(7)|------|------|------| Base | ----- | MO(4)| Next | Vol- | Vol+ | Play |
341 * `-----------------------------------------------------------------------------------'
342 */
343
344 [_NUMBRS] = LAYOUT_planck_mit( //
345 KC_MPLY, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC, //
346 KC_DEL, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS, //
347 KC_TRNS, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, KC_NUHS, KC_NUBS, KC_PGUP, KC_PGDN, KC_TRNS, //
348 TG(_NUMPD), KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, TO(_BASE), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY),
349
350 /*
351 Numbers Layer [4]
352 * ,-----------------------------------------------------------------------------------.
353 * | Play | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 |BckSpc|
354 * |------+------+------+------+------+------+------+------+------+------+------+------|
355 * |Delete| F1 | F2 | F3 | F4 | F5 | F6 | - | = | [ | ] | \ |
356 * |------+------+------+------+------+------+------+------+------+------+------+------|
357 * | Shift| F7 | F8 | F9 | F10 | F11 | F12 | # | / | PgUp | PgDwn|------|
358 * |------+------+------+------+------+------+------+------+------+------+------+------|
359 * | TG(7)|------|------|------| MO(3)| ----- | Base | Next | Vol- | Vol+ | Play |
360 * `-----------------------------------------------------------------------------------'
361 */
362
363 [_PLOVER] = LAYOUT_planck_mit( //
364 KC_1, KC_1, KC_1, KC_1, KC_1, KC_1, KC_1, KC_1, KC_1, KC_1, KC_1, KC_1, //
365 XXXXXXX, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_LBRC, //
366 XXXXXXX, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT, //
367 EXT_PLV, XXXXXXX, XXXXXXX, KC_C, KC_V, XXXXXXX, KC_N, KC_M, XXXXXXX, XXXXXXX, XXXXXXX),
368 /* Plover Layer [5]
369 * ,-----------------------------------------------------------------------------------.
370 * | # | # | # | # | # | # | # | # | # | # | # | # |
371 * |------+------+------+------+------+------+------+------+------+------+------+------|
372 * | | S | T | P | H | * | * | F | P | L | T | D |
373 * |------+------+------+------+------+------+------+------+------+------+------+------|
374 * | | S | K | W | R | * | * | R | B | G | S | Z |
375 * |------+------+------+------+------+------+------+------+------+------+------+------|
376 * | Exit | | | A | O | | E | U | | | |
377 * `-----------------------------------------------------------------------------------'
378 */
379
380 [_FEATURS] = LAYOUT_planck_mit( //
381 LCTL(LALT(KC_DEL)), DO_RESET, DEBUG, RGB_TOG, RGB_MOD, RGB_HUI, RGB_HUD, RGB_SAI, RGB_SAD, TD(TD_DEG_DEGF), TD(TD_SMILEY), KC_DEL, //
382 RGB_VAI, RGB_VAD, MU_MOD, AU_ON, AU_OFF, AG_NORM, AG_SWAP, DF(_BASE), DF(_COLEMAK), DF(_DVORAK), TO(_PLOVER), MY_RGBCON, //
383 KC_TRNS, MUV_DE, MUV_IN, MU_ON, MU_OFF, MI_ON, MI_OFF, TERM_ON, TERM_OFF, CK_ON, CK_OFF, KC_ENTER, //
384 KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, TG(_MOUSY), KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS),
385 /*
386 Special Features Layer [6]
387 * ,-----------------------------------------------------------------------------------.
388 * |C+A+DL| Reset| Debug|RGBTog|RGBMod| Hue+ | Hue- | Sat+ | Sat- |Unicod| Emoji|Delete|
389 * |------+------+------+------+------+------+------+------+------+------+------+------|
390 * |RGBVAI|RGBVAD|MU_MOD| AU_ON|AU_OFF|RALTGU|SALTGU| Base |Colemk|Dvorak|Plover|RGBCON|
391 * |------+------+------+------+------+------+------+------+------+------+------+------|
392 * |------|MUV_DE|MUV_IN| MU_ON|MU_OFF| MI_ON|MI_OFF|TERMON|TRMOFF|CLK-ON|CLKOFF|Enter |
393 * |------+------+------+------+------+------+------+------+------+------+------+------|
394 * |------|------|------|------|------| TG(8) |------|------|------|------|------|
395 * `-----------------------------------------------------------------------------------'
396 */
397
398 [_NUMPD] = LAYOUT_planck_mit( //
399 KC_ESC, KC_HOME, KC_UP, KC_END, KC_PERC, KC_LCBR, KC_RCBR, KC_TAB, KC_P7, KC_P8, KC_P9, KC_BSPC, //
400 KC_TILD, KC_LEFT, KC_DOWN, KC_RGHT, KC_BSLS, KC_LBRC, KC_RBRC, KC_PSLS, KC_P4, KC_P5, KC_P6, KC_PMNS, //
401 KC_LSFT, KC_SLSH, KC_CUT, KC_COPY, KC_PASTE, KC_LT, KC_GT, KC_PAST, KC_P1, KC_P2, KC_P3, KC_PPLS, //
402 TO(_BASE), KC_LEAD, KC_LGUI, KC_LALT, KC_LCPO, KC_SPC, KC_RCPC, KC_HASH, KC_P0, KC_PDOT, KC_PENT),
403 /*
404 Numpad Layer [7]
405 * ,-----------------------------------------------------------------------------------.
406 * | Esc | Home | Up | End | % | { | } | Tab | 7 | 8 | 9 |BckSpc|
407 * |------+------+------+------+------+------+------+------+------+------+------+------|
408 * | ~ | Left | Down | Right| \ | [ | ] | / | 4 | 5 | 6 | - |
409 * |------+------+------+------+------+------+------+------+------+------+------+------|
410 * | Shift| / |Ctrl+X|Ctrl+C|Ctrl+V| < | > | * | 1 | 2 | 3 | + |
411 * |------+------+------+------+------+------+------+------+------+------+------+------|
412 * | Base |Leader| Alt | OS |LCtl/(| Space |)/RCtl| # | 0 | . |Enter |
413 * `-----------------------------------------------------------------------------------'
414 */
415 [_TABULA] = LAYOUT_planck_mit( //
416 KC_ESC, KC_ALTF4, VLK_TOG, PRINT_WPM_KEY, WAKE_ANI_TOG, WAKE_AUD_TOG, KC_REDO, UC_MOD, UC_M_WC, CG_TOGG, AG_TOGG, KC_DLINE, //
417 KC_NXTAB, KC_SLCTALL, KC_SAVE, KC_TRNS, KC_FIND, SH_TG, SH_TG, IRONY, KC_LCUT, KC_LCOPY, KC_TRNS, KC_KILL, //
418 KC_LSFT, KC_UNDO, KC_CUT, KC_COPY, KC_PASTE, KC_PRVWD, KC_NXTWD, TG(_MOUSY), KC_TRNS, KC_HOME, KC_END, KC_SFTENT, //
419 TO(_BASE), KC_LCTL, KC_LGUI, KC_LALT, KC_LSPO, ALT_TAB, KC_RSPC, KC_PRVWD, KC_BRID, KC_BRIU, KC_NXTWD),
420 /* Tabular Layer [8]
421 * ,-----------------------------------------------------------------------------------.
422 * | Esc |Alt+F4|Veloci| WPM |WakANI|WakAUD|Ctrl+Y|UCMode|UCWinC|CtGUTg|AltGTg| DLine|
423 * |------+------+------+------+------+------+------+------+------+------+------+------|
424 * | Tab |Ctrl+A|Ctrl+S|------|Ctrl+F| SWAP | SWAP | ⸮^‽ |CutLin|CpyLin|------|DelLin|
425 * |------+------+------+------+------+------+------+------+------+------+------+------|
426 * | Shift|Ctrl+Z|Ctrl+X|Ctrl+C|Ctrl+V|PrVWin|NxtWin| TG(8)|------| Home | End |Enter |
427 * |------+------+------+------+------+------+------+------+------+------+------+------|
428 * | Base | LCtrl| Alt | OS |LSft/(| Alt+Tab |)/RSft|PrvSel|ScrBr-|ScrBr+|NxtSel|
429 * `-----------------------------------------------------------------------------------'
430 */
431
432 [_MOUSY] = LAYOUT_planck_mit( //
433 KC_ESC, KC_BTN1, KC_MS_U, KC_BTN2, KC_TRNS, KC_TRNS, KC_TRNS, UC_MOD, UC_M_WC, CG_TOGG, AG_TOGG, KC_BSPC, //
434 KC_TAB, KC_MS_L, KC_MS_D, KC_MS_R, KC_TRNS, KC_TRNS, KC_TRNS, IRONY, VLK_TOG, KC_TRNS, KC_TRNS, KC_TRNS, //
435 KC_LSFT, KC_UNDO, KC_CUT, KC_COPY, KC_PASTE, KC_PRVWD, KC_NXTWD, KC_TRNS, KC_HOME, KC_BTN3, KC_END, KC_SFTENT, //
436 TO(_BASE), KC_LCTL, KC_LGUI, KC_LALT, KC_BTN1, ALT_TAB, KC_BTN2, KC_WH_L, KC_WH_D, KC_WH_U, KC_WH_R)};
437/* MousePad Layer [9]
438 * ,-----------------------------------------------------------------------------------.
439 * | Esc |MsBtn1| MsUp |MsBtn2|------|------|------|UCMode|UCWinC|CtGUTg|AltGTg|BckSpc|
440 * |------+------+------+------+------+------+------+------+------+------+------+------|
441 * | ~ |MsLeft|MsDown|MsRigt|------|------|------| ⸮^‽ |Veloci|------|------|------|
442 * |------+------+------+------+------+------+------+------+------+------+------+------|
443 * | Shift|------|Ctrl+X|Ctrl+C|Ctrl+V|------|------|------| Home |MsBtn3| End |Enter |
444 * |------+------+------+------+------+------+------+------+------+------+------+------|
445 * | Base | LCtrl| Alt | OS |MsBtn1| Alt+Tab |MsBtn2|MsWhlL|MsWhlD|MsWhlU|MsWhlR|
446 * `-----------------------------------------------------------------------------------'
447 */
448
449// Define RGB layers | assign leds and their values for each rgb layer
450const rgblight_segment_t PROGMEM my_warning_layer[] = RGBLIGHT_LAYER_SEGMENTS({1, 9, HSV_RED}, {0, 1, HSV_RED});
451const rgblight_segment_t PROGMEM my_allgood_layer[] = RGBLIGHT_LAYER_SEGMENTS({1, 9, HSV_GREEN}, {0, 1, HSV_GREEN});
452const rgblight_segment_t PROGMEM my_capslock_layer[] = RGBLIGHT_LAYER_SEGMENTS({1, 1, HSV_RED}, {8, 1, HSV_RED});
453const rgblight_segment_t PROGMEM my_number_layer[] = RGBLIGHT_LAYER_SEGMENTS({1, 1, HSV_MAGENTA}, {8, 1, HSV_MAGENTA});
454const rgblight_segment_t PROGMEM my_symbol_layer[] = RGBLIGHT_LAYER_SEGMENTS({1, 1, HSV_GREEN}, {8, 1, HSV_GREEN});
455const rgblight_segment_t PROGMEM my_tabula_layer[] = RGBLIGHT_LAYER_SEGMENTS({3, 4, HSV_CORAL}, {1, 1, HSV_CORAL}, {8, 1, HSV_CORAL});
456const rgblight_segment_t PROGMEM my_mousy_layer[] = RGBLIGHT_LAYER_SEGMENTS({3, 4, HSV_TURQUOISE}, {1, 1, HSV_TURQUOISE}, {8, 1, HSV_TURQUOISE}, {7, 1, HSV_MAGENTA});
457const rgblight_segment_t PROGMEM my_numpad_layer[] = RGBLIGHT_LAYER_SEGMENTS({3, 4, HSV_GOLD}, {1, 1, HSV_GOLD}, {8, 1, HSV_GOLD}, {7, 1, HSV_BLUE});
458const rgblight_segment_t PROGMEM my_features_layer[] = RGBLIGHT_LAYER_SEGMENTS({3, 4, HSV_BLUE}, {1, 1, HSV_BLUE}, {8, 1, HSV_BLUE});
459const rgblight_segment_t PROGMEM my_base_layer[] = RGBLIGHT_LAYER_SEGMENTS({0, 0, HSV_BLACK});
460const rgblight_segment_t PROGMEM my_colemak_layer[] = RGBLIGHT_LAYER_SEGMENTS({1, 1, HSV_GREEN});
461const rgblight_segment_t PROGMEM my_dvorak_layer[] = RGBLIGHT_LAYER_SEGMENTS({1, 1, HSV_ORANGE});
462const rgblight_segment_t PROGMEM my_plover_layer[] = RGBLIGHT_LAYER_SEGMENTS({1, 1, HSV_GOLD});
463
464// Define the array of rgb layers. Later layers take precedence
465const rgblight_segment_t* const PROGMEM my_rgb_layers[] = RGBLIGHT_LAYERS_LIST(my_base_layer, // Base Layer
466 my_colemak_layer, // Overrides previous layer
467 my_dvorak_layer, // Overrides previous layers
468 my_symbol_layer, // Overrides previous layers
469 my_number_layer, // ...etc my_features_layer, // Overrides layers
470 my_plover_layer, //
471 my_features_layer, //
472 my_numpad_layer, //
473 my_tabula_layer, //
474 my_mousy_layer, //
475 my_capslock_layer, //
476 my_warning_layer, //
477 my_allgood_layer); // CapsLock Layer);
478
479// Configure encoders
480bool encoder_update_user(uint8_t index, bool clockwise) {
481 if (musical_mode) {
482 if (clockwise) {
483 tap_code16(MU_MOD);
484 } else {
485 tap_code16(MU_MOD);
486 }
487 } else {
488 if (muse_mode) {
489 if (IS_LAYER_ON(_RAISE)) {
490 if (clockwise) {
491 muse_offset++;
492 } else {
493 muse_offset--;
494 }
495 } else {
496 if (clockwise) {
497 muse_tempo += 1;
498 } else {
499 muse_tempo -= 1;
500 }
501 }
502 } else {
503 if (index == 0) { /* First encoder */
504 uint16_t held_keycode_timer = timer_read();
505 switch (biton32(layer_state)) {
506 case 0: // Base Layer
507 if ((get_mods() & MOD_MASK_GUI)) { // GUI-ed
508 if (clockwise) {
509 tap_code(KC_RIGHT);
510
511 } else {
512 tap_code(KC_LEFT);
513 }
514 } else if ((get_mods() & MOD_MASK_ALT)) { // Alt-ed
515 if (clockwise) {
516 tap_code16(LALT(KC_TAB)); // Alt+Tabbing
517 } else {
518 tap_code16(LSA(KC_TAB));
519 }
520 } else if ((get_mods() & MOD_MASK_SHIFT)) { // Shifted
521 const uint8_t _real_mods = get_mods();
522 unregister_code16(KC_LSFT);
523 unregister_code16(KC_RSFT);
524 clear_mods();
525 if (clockwise) {
526 tap_code16(KC_MS_WH_DOWN);
527 } else {
528 tap_code16(KC_MS_WH_UP);
529 }
530 set_mods(_real_mods);
531 } else if ((get_mods() & MOD_MASK_CTRL)) { // Ctrl-ed
532 if (clockwise) {
533 tap_code16(RCTL(KC_TAB)); // Ctrl+Tabbing
534 } else {
535 tap_code16(RCS(KC_TAB));
536 }
537 } else { // Normal or unspecified modifiers
538 if (clockwise) {
539 // Volume control requires extra timer to function correctly
540 register_code(KC_VOLU);
541 while (timer_elapsed(held_keycode_timer) < TAP_CODE_DELAY) {
542 // no-op
543 }
544 unregister_code(KC_VOLD);
545 } else {
546 register_code(KC_VOLD);
547 while (timer_elapsed(held_keycode_timer) < TAP_CODE_DELAY) {
548 // no-op
549 }
550 unregister_code(KC_VOLU);
551 }
552 }
553 return false;
554 break;
555 case 3: // Symbols Layer
556 if (clockwise) {
557 tap_code(KC_WH_D); // Mouse wheeling
558 } else {
559 tap_code(KC_WH_U);
560 }
561 return false;
562 break;
563 case 4: // Numbers Layer
564 if (clockwise) {
565 tap_code(KC_WH_D); // Mouse wheeling
566 } else {
567 tap_code(KC_WH_U);
568 }
569 return false;
570 break;
571 case 6: // Features Layer
572 if (clockwise) {
573 tap_code16(KC_DOWN);
574 } else {
575 tap_code16(KC_UP);
576 }
577 default: // Any other layer
578 if ((get_mods() & MOD_MASK_CSAG)) {
579 if (clockwise) {
580 WITHOUT_MODS({ SEND_STRING(SS_TAP(X_RIGHT)); });
581 } else {
582 WITHOUT_MODS({ SEND_STRING(SS_TAP(X_LEFT)); });
583 }
584 } else {
585 if (clockwise) {
586 tap_code(KC_DOWN); // Simple Up/Down
587 } else {
588 tap_code(KC_UP);
589 }
590 }
591 return false;
592 break;
593 }
594 } else if (index == 1) { /* Second encoder (if we had one) */
595 if (clockwise) {
596 tap_code16(LCTL(KC_LEFT)); // Ctrl+Left/Right
597 } else {
598 tap_code16(LCTL(KC_RIGHT));
599 }
600 }
601 }
602 }
603 return true;
604}
605
606// OLED CONFIGURATION
607/*
608static void render_logo(void) {
609 static const char PROGMEM qmk_logo[] = {0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F, 0x90, 0x91, 0x92, 0x93, 0x94, 0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, 0xA8, 0xA9, 0xAA, 0xAB, 0xAC, 0xAD, 0xAE, 0xAF, 0xB0, 0xB1, 0xB2, 0xB3, 0xB4, 0xC0, 0xC1, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, 0xC8, 0xC9, 0xCA, 0xCB, 0xCC, 0xCD, 0xCE, 0xCF, 0xD0, 0xD1, 0xD2, 0xD3, 0xD4, 0x00};
610
611 oled_write_P(qmk_logo, false);
612}
613*/
614
615// Process Combo events
616void process_combo_event(uint16_t combo_index, bool pressed) {
617 switch (combo_index) {
618 case ZC_COPY:
619 if (pressed) {
620 tap_code16(LCTL(KC_C));
621 }
622 break;
623 case XV_PASTE:
624 if (pressed) {
625 tap_code16(LCTL(KC_V));
626 }
627 break;
628 }
629}
630
631// Runs every time a key is pressed or released
632bool process_record_user(uint16_t keycode, keyrecord_t* record) {
633#ifdef CONSOLE_ENABLE
634 dprintf("KL: kc: 0x%04X, col: %u, row: %u, pressed: %b, time: %u, interrupt: %b, count: %u\n", keycode, record->event.key.col, record->event.key.row, record->event.pressed, record->event.time, record->tap.interrupted, record->tap.count);
635#endif
636 // Store the current modifier state in the variable for later reference
637 mod_state = get_mods();
638 switch (keycode) {
639 case QWERTY:
640 if (record->event.pressed) {
641 set_single_persistent_default_layer(_QWERTY);
642 PLAY_SONG(qwerty_song);
643 }
644 return false;
645 break;
646 case COLEMAK:
647 if (record->event.pressed) {
648 set_single_persistent_default_layer(_COLEMAK);
649 PLAY_SONG(colemak_song);
650 }
651 return false;
652 break;
653 case DVORAK:
654 if (record->event.pressed) {
655 set_single_persistent_default_layer(_DVORAK);
656 PLAY_SONG(dvorak_song);
657 }
658 return false;
659 break;
660 case PLOVER:
661 if (record->event.pressed) {
662#ifdef AUDIO_ENABLE
663 stop_all_notes();
664 PLAY_SONG(plover_song);
665#endif
666 layer_off(_RAISE);
667 layer_off(_LOWER);
668 layer_off(_ADJUST);
669 layer_on(_PLOVER);
670 if (!eeconfig_is_enabled()) {
671 eeconfig_init();
672 }
673 keymap_config.raw = eeconfig_read_keymap();
674 keymap_config.nkro = 1;
675 eeconfig_update_keymap(keymap_config.raw);
676 }
677 return false;
678 break;
679 case EXT_PLV:
680 if (record->event.pressed) {
681#ifdef AUDIO_ENABLE
682 PLAY_SONG(plover_gb_song);
683#endif
684 layer_off(_PLOVER);
685 }
686 return false;
687 break;
688 case MO_SYMBLS:
689 if (record->event.pressed) {
690 layer_on(_SYMBLS);
691 } else {
692 layer_off(_SYMBLS);
693 }
694 return false;
695 case MO_NUMBRS:
696 if (record->event.pressed) {
697 layer_on(_NUMBRS);
698 } else {
699 layer_off(_NUMBRS);
700 }
701 return false;
702 case MO_FEATURS:
703 if (record->event.pressed) {
704 layer_on(_FEATURS);
705 } else {
706 layer_off(_FEATURS);
707 }
708 return false;
709 case MUSIC_ON:
710 if (record->event.pressed) {
711 musical_mode = true;
712 register_code16(MU_ON);
713 } else {
714 unregister_code16(MU_ON);
715 }
716 break;
717 case MUSIC_OFF:
718 if (record->event.pressed) {
719 musical_mode = false;
720 register_code16(MU_OFF);
721 } else {
722 unregister_code16(MU_OFF);
723 }
724 break;
725 case KC_PRVWD: // Control+Left
726 if (record->event.pressed) {
727 if (keymap_config.swap_lctl_lgui) {
728 register_mods(mod_config(MOD_LALT));
729 register_code(KC_LEFT);
730 } else {
731 register_mods(mod_config(MOD_LCTL));
732 register_code(KC_LEFT);
733 }
734 } else {
735 if (keymap_config.swap_lctl_lgui) {
736 unregister_mods(mod_config(MOD_LALT));
737 unregister_code(KC_LEFT);
738 } else {
739 unregister_mods(mod_config(MOD_LCTL));
740 unregister_code(KC_LEFT);
741 }
742 }
743 break;
744 case KC_NXTWD: // Control+Right
745 if (record->event.pressed) {
746 if (keymap_config.swap_lctl_lgui) {
747 register_mods(mod_config(MOD_LALT));
748 register_code(KC_RIGHT);
749 } else {
750 register_mods(mod_config(MOD_LCTL));
751 register_code(KC_RIGHT);
752 }
753 } else {
754 if (keymap_config.swap_lctl_lgui) {
755 unregister_mods(mod_config(MOD_LALT));
756 unregister_code(KC_RIGHT);
757 } else {
758 unregister_mods(mod_config(MOD_LCTL));
759 unregister_code(KC_RIGHT);
760 }
761 }
762 break;
763 case KC_PRVTAB: // Control+Shift+Tab
764 if (record->event.pressed) {
765 register_mods(mod_config(MOD_LCTL));
766 register_mods(mod_config(MOD_LSFT));
767 register_code(KC_TAB);
768 } else {
769 unregister_mods(mod_config(MOD_LCTL));
770 unregister_mods(mod_config(MOD_LSFT));
771 unregister_code(KC_TAB);
772 }
773 break;
774 case KC_NXTAB: // Control+Tab
775 if (record->event.pressed) {
776 if (keymap_config.swap_lctl_lgui) {
777 register_mods(mod_config(MOD_LCTL));
778 register_code(KC_TAB);
779 } else {
780 register_mods(mod_config(MOD_LSFT));
781 register_code(KC_TAB);
782 }
783 } else {
784 if (keymap_config.swap_lctl_lgui) {
785 unregister_mods(mod_config(MOD_LALT));
786 unregister_code(KC_RIGHT);
787 } else {
788 unregister_mods(mod_config(MOD_LCTL));
789 unregister_code(KC_RIGHT);
790 }
791 }
792 break;
793 case KC_LSTRT: // Basically just Home
794 if (record->event.pressed) {
795 if (keymap_config.swap_lctl_lgui) {
796 // CMD-arrow on Mac, but we have CTL and GUI swapped
797 register_mods(mod_config(MOD_LCTL));
798 register_code(KC_LEFT);
799 } else {
800 register_code(KC_HOME);
801 }
802 } else {
803 if (keymap_config.swap_lctl_lgui) {
804 unregister_mods(mod_config(MOD_LCTL));
805 unregister_code(KC_LEFT);
806 } else {
807 unregister_code(KC_HOME);
808 }
809 }
810 break;
811 case KC_LEND: // Basically just End
812 if (record->event.pressed) {
813 if (keymap_config.swap_lctl_lgui) {
814 // CMD-arrow on Mac, but we have CTL and GUI swapped
815 register_mods(mod_config(MOD_LCTL));
816 register_code(KC_RIGHT);
817 } else {
818 register_code(KC_END);
819 }
820 } else {
821 if (keymap_config.swap_lctl_lgui) {
822 unregister_mods(mod_config(MOD_LCTL));
823 unregister_code(KC_RIGHT);
824 } else {
825 unregister_code(KC_END);
826 }
827 }
828 break;
829 case KC_DLINE: // Control+BackSpace
830 if (record->event.pressed) {
831 register_mods(mod_config(MOD_LCTL));
832 register_code(KC_BSPC);
833 } else {
834 unregister_mods(mod_config(MOD_LCTL));
835 unregister_code(KC_BSPC);
836 }
837 break;
838 case KC_COPY: // Copy: Control+C
839 if (record->event.pressed) {
840 register_mods(mod_config(MOD_LCTL));
841 register_code(KC_C);
842 } else {
843 unregister_mods(mod_config(MOD_LCTL));
844 unregister_code(KC_C);
845 }
846 return false;
847 case KC_PASTE: // Paste: Control+V
848 if (record->event.pressed) {
849 register_mods(mod_config(MOD_LCTL));
850 register_code(KC_V);
851 } else {
852 unregister_mods(mod_config(MOD_LCTL));
853 unregister_code(KC_V);
854 }
855 return false;
856 case KC_CUT: // Cut: Control+X
857 if (record->event.pressed) {
858 register_mods(mod_config(MOD_LCTL));
859 register_code(KC_X);
860 } else {
861 unregister_mods(mod_config(MOD_LCTL));
862 unregister_code(KC_X);
863 }
864 return false;
865 break;
866 case KC_UNDO: // Undo: Control+Z
867 if (record->event.pressed) {
868 register_mods(mod_config(MOD_LCTL));
869 register_code(KC_Z);
870 } else {
871 unregister_mods(mod_config(MOD_LCTL));
872 unregister_code(KC_Z);
873 }
874 return false;
875 case KC_REDO: // Redo: Control+Y
876 if (record->event.pressed) {
877 register_mods(mod_config(MOD_LCTL));
878 register_code(KC_Y);
879 } else {
880 unregister_mods(mod_config(MOD_LCTL));
881 unregister_code(KC_Y);
882 }
883 break;
884 case KC_SAVE: // Save: Control+S
885 if (record->event.pressed) {
886 register_mods(mod_config(MOD_LCTL));
887 register_code(KC_S);
888 } else {
889 unregister_mods(mod_config(MOD_LCTL));
890 unregister_code(KC_S);
891 }
892 return false;
893 case KC_FIND: // Find: Control+F
894 if (record->event.pressed) {
895 register_mods(mod_config(MOD_LCTL));
896 register_code(KC_F);
897 } else {
898 unregister_mods(mod_config(MOD_LCTL));
899 unregister_code(KC_F);
900 }
901 return false;
902 case KC_SLCTALL: // Select All: Control+A
903 if (record->event.pressed) {
904 register_mods(mod_config(MOD_LCTL));
905 register_code(KC_A);
906 } else {
907 unregister_mods(mod_config(MOD_LCTL));
908 unregister_code(KC_A);
909 }
910 return false;
911 case KC_KILL: // Kill: Delete Line
912 if (record->event.pressed) {
913 tap_code(KC_HOME);
914 register_mods(mod_config(MOD_LSFT));
915 tap_code(KC_END);
916 unregister_mods(mod_config(MOD_LSFT));
917 tap_code(KC_DELETE);
918 } else {
919 }
920 return false;
921 case KC_LCUT: // Cut Line
922 if (record->event.pressed) {
923 tap_code(KC_HOME);
924 register_mods(mod_config(MOD_LSFT));
925 tap_code(KC_END);
926 unregister_mods(mod_config(MOD_LSFT));
927 register_mods(mod_config(MOD_LCTL));
928 tap_code(KC_X);
929 unregister_mods(mod_config(MOD_LCTL));
930 } else {
931 }
932 return false;
933 case KC_LCOPY: // Copy Line
934 if (record->event.pressed) {
935 tap_code(KC_HOME);
936 register_mods(mod_config(MOD_LSFT));
937 tap_code(KC_END);
938 unregister_mods(mod_config(MOD_LSFT));
939 register_mods(mod_config(MOD_LCTL));
940 tap_code(KC_C);
941 unregister_mods(mod_config(MOD_LCTL));
942 tap_code(KC_END);
943 } else {
944 }
945 return false;
946 case KC_ALTF4: // Close Window: Alt+F4
947 if (record->event.pressed) {
948 register_mods(mod_config(MOD_LALT));
949 register_code(KC_F4);
950 } else {
951 unregister_mods(mod_config(MOD_LALT));
952 unregister_code(KC_F4);
953 }
954 return false;
955 case ALT_TAB: // Change Window: Super ⭍ Alt+Tab
956 if (record->event.pressed) {
957 if (!is_alt_tab_active) {
958 is_alt_tab_active = true;
959 register_code(KC_LALT);
960 }
961 alt_tab_timer = timer_read();
962 register_code(KC_TAB);
963#ifdef CONSOLE_ENABLE
964 dprint("I've tabbed to another window!\n");
965#endif
966 } else {
967 unregister_code(KC_TAB);
968 }
969 break;
970 case KC_BSPC: {
971 // Initialize a boolean variable that keeps track
972 // of the delete key status: registered or not?
973 static bool delkey_registered;
974 if (record->event.pressed) {
975 // Detect the activation of either shift keys
976 if (mod_state & MOD_MASK_SHIFT) {
977 // First temporarily canceling both shifts so that
978 // shift isn't applied to the KC_DEL keycode
979 del_mods(MOD_MASK_SHIFT);
980 register_code(KC_DEL);
981 // Update the boolean variable to reflect the status of KC_DEL
982 delkey_registered = true;
983 // Reapplying modifier state so that the held shift key(s)
984 // still work even after having tapped the Backspace/Delete key.
985 set_mods(mod_state);
986 return false;
987 }
988 } else { // on release of KC_BSPC
989 // In case KC_DEL is still being sent even after the release of KC_BSPC
990 if (delkey_registered) {
991 unregister_code(KC_DEL);
992 delkey_registered = false;
993 return false;
994 }
995 }
996 }
997 // Let QMK process the KC_BSPC keycode as usual outside of shift
998 return true;
999
1000 case DO_RESET: // Reset button with LED indication
1001 if (record->event.pressed) {
1002 rgblight_set_effect_range(0, 9);
1003 rgblight_sethsv_noeeprom(HSV_RED);
1004 rgblight_mode_noeeprom(RGBLIGHT_MODE_STATIC_LIGHT);
1005 rgblight_blink_layer(11, 5000);
1006 reset_keyboard();
1007 }
1008 break;
1009 case WAKE_ANI_TOG: // Toggle the Wakeup RGB animation
1010 if (record->event.pressed) {
1011 user_config.do_wakeup_animation ^= 1; // Toggles the status
1012 eeconfig_update_user(user_config.raw); // Writes the new status to EEPROM
1013 if (user_config.do_wakeup_animation) {
1014 print("Wake animation enabled.\n");
1015 PLAY_SONG(slctl_on);
1016
1017 } else {
1018 print("Wake animation disabled.\n");
1019 PLAY_SONG(slctl_off);
1020 }
1021 }
1022 break;
1023 case WAKE_AUD_TOG: // Toggle the wake-up music
1024 if (record->event.pressed) {
1025 user_config.do_wakeup_audio ^= 1; // Toggles the status
1026 eeconfig_update_user(user_config.raw); // Writes the new status to EEPROM
1027 if (user_config.do_wakeup_audio) {
1028 print("Wake music enabled.\n");
1029 PLAY_SONG(slctl_on);
1030
1031 } else {
1032 print("Wake music disabled.\n");
1033 PLAY_SONG(slctl_off);
1034 }
1035 }
1036 break;
1037 case IRONY: // Outputs Irony/Interrobang symbols
1038 if ((get_mods() & MOD_MASK_SHIFT)) {
1039 irony_shifted = true;
1040 } else {
1041 irony_shifted = false;
1042 }
1043 if (record->event.pressed) {
1044 if (irony_shifted) {
1045 send_unicode_string(bang_str);
1046 } else {
1047 send_unicode_string(irony_str);
1048 }
1049 irony_active = true;
1050 irony_pressed_time = timer_read();
1051 } else {
1052 irony_active = false;
1053 irony_pressed_time = 0;
1054 irony_shifted = false;
1055 }
1056 return false;
1057 case TG(_NUMPD): // Toggle the NumPad layer
1058 if (record->event.pressed) {
1059#ifdef AUDIO_ENABLE
1060 PLAY_SONG(hello_song);
1061#endif
1062 print("I've activated the NumPad!\n");
1063 } else {
1064 }
1065 break;
1066 case TG(_TABULA): // Toggle the Tabula layer
1067 if (record->event.pressed) {
1068#ifdef AUDIO_ENABLE
1069 PLAY_SONG(lover_song);
1070#endif
1071 print("I've activated Tabular!\n");
1072 } else {
1073 }
1074 break;
1075 case TG(_MOUSY): // Toggle the MouseyPad layer
1076 if (record->event.pressed) {
1077#ifdef AUDIO_ENABLE
1078 PLAY_SONG(funk_song);
1079#endif
1080 print("I've activated the MousePad!\n");
1081 } else {
1082 }
1083 break;
1084 case TO(_BASE): // Return to the base layer
1085 if (record->event.pressed) {
1086#ifdef AUDIO_ENABLE
1087 PLAY_SONG(planck_song);
1088#endif
1089 print("I've returned to the Base Layer!\n");
1090 } else {
1091 }
1092 break;
1093 case PRINT_WPM_KEY: // Prints the current average words-per-minute to the console
1094 sprintf(wpm_str, "Current WPM: %hu", get_current_wpm());
1095 printf("%s\n", wpm_str);
1096 break;
1097
1098 case MY_RGBCON: // Cycles through custom RGB animation presets
1099 if (record->event.pressed) {
1100 // when keycode RGB-CON is pressed
1101 user_config.rgbcon_tracker = rgbcon_tracker + 1; // Toggles the status
1102 eeconfig_update_user(user_config.raw);
1103 switch (rgbcon_tracker) {
1104 case 0:
1105 rgblight_set_effect_range(0, 9);
1106 rgblight_sethsv(HSV_BLACK);
1107 rgblight_mode(RGBLIGHT_MODE_STATIC_LIGHT);
1108 print("Changed RGB mode to: Disabled RGB\n");
1109 rgbcon_tracker++;
1110 break;
1111 case 1:
1112 rgblight_set_effect_range(0, 9);
1113 rgblight_sethsv(HSV_WHITE);
1114 rgblight_mode(RGBLIGHT_MODE_STATIC_LIGHT);
1115 print("Changed RGB mode to: Static White\n");
1116 rgbcon_tracker++;
1117 break;
1118 case 2:
1119 rgblight_set_effect_range(0, 9);
1120 rgblight_sethsv(HSV_CYAN);
1121 rgblight_mode(RGBLIGHT_MODE_STATIC_LIGHT);
1122 print("Changed RGB mode to: Static Cyan\n");
1123 rgbcon_tracker++;
1124 break;
1125 case 3:
1126 rgblight_set_effect_range(0, 9);
1127 rgblight_sethsv(HSV_WHITE);
1128 rgblight_mode(RGBLIGHT_MODE_BREATHING);
1129 print("Changed RGB mode to: Breathing Lights\n");
1130#ifdef AUDIO_ENABLE
1131 print("Played Marching song!\n");
1132 PLAY_SONG(imp_march_song);
1133#endif
1134 rgbcon_tracker++;
1135 break;
1136 case 4:
1137 rgblight_set_effect_range(0, 9);
1138 rgblight_sethsv(HSV_RED);
1139 rgblight_mode(RGBLIGHT_MODE_RAINBOW_SWIRL);
1140 print("Changed RGB mode to: Rainbow Swirl\n");
1141 rgbcon_tracker++;
1142 break;
1143 case 5:
1144 rgblight_set_effect_range(0, 9);
1145 rgblight_sethsv(HSV_CYAN);
1146 rgblight_mode(RGBLIGHT_MODE_RAINBOW_MOOD);
1147 print("Changed RGB mode to: Rainbow Mood\n");
1148#ifdef AUDIO_ENABLE
1149 print("Played Game Over song!\n");
1150 PLAY_SONG(gameover_song);
1151#endif
1152 rgbcon_tracker = 0;
1153 break;
1154 case 6:
1155 rgblight_set_effect_range(0, 9);
1156 rgblight_sethsv(HSV_BLACK);
1157 rgblight_mode(RGBLIGHT_MODE_STATIC_LIGHT);
1158 print("Changed RGB mode to: Disabled RGB\n");
1159 rgbcon_tracker = 1;
1160 break;
1161 }
1162 } else {
1163 }
1164 break;
1165 }
1166 return true;
1167};
1168
1169// Runs *after* a key is pressed
1170void post_process_record_user(uint16_t keycode, keyrecord_t* record) {
1171 switch (keycode) {
1172 case DEBUG:
1173 // Blink the warning layer when the debug key is pressed
1174 rgblight_blink_layer_repeat(debug_enable ? 11 : 12, 1500, 3);
1175
1176 // Update the console with the debug mode status
1177 if (debug_enable) {
1178 print("Debug mode enabled.\n");
1179 PLAY_SONG(slctl_on);
1180
1181 } else {
1182 print("Debug mode disabled.\n");
1183 PLAY_SONG(slctl_off);
1184 }
1185 break;
1186 }
1187}
1188
1189// RGB Default Layer assignments
1190layer_state_t default_layer_state_set_user(layer_state_t state) {
1191 state = update_tri_layer_state(state, _SYMBLS, _NUMBRS, _FEATURS);
1192
1193 // Sets the default RGB layer states
1194 rgblight_set_layer_state(0, layer_state_cmp(state, _BASE));
1195 rgblight_set_layer_state(1, layer_state_cmp(state, _COLEMAK));
1196 rgblight_set_layer_state(2, layer_state_cmp(state, _DVORAK));
1197 return state;
1198}
1199
1200// RGB Layer assignments
1201layer_state_t layer_state_set_user(layer_state_t state) {
1202 state = update_tri_layer_state(state, _SYMBLS, _NUMBRS, _FEATURS);
1203
1204 // Sets the RGB layer states
1205 rgblight_set_layer_state(5, layer_state_cmp(state, _PLOVER));
1206 rgblight_set_layer_state(6, layer_state_cmp(state, _FEATURS));
1207 rgblight_set_layer_state(3, layer_state_cmp(state, _SYMBLS));
1208 rgblight_set_layer_state(4, layer_state_cmp(state, _NUMBRS));
1209 rgblight_set_layer_state(7, layer_state_cmp(state, _NUMPD));
1210 rgblight_set_layer_state(8, layer_state_cmp(state, _TABULA));
1211 rgblight_set_layer_state(9, layer_state_cmp(state, _MOUSY));
1212 return state;
1213}
1214
1215// Runs the wakeup rgb animation + music
1216void rgb_wakeup_sequence(void) {
1217 if (waking_up) {
1218 if ((timer_elapsed(wake_rgb_timer) > WAKE_ANIMATION_TIMER_FREQUENCY)) {
1219 if (wake_rgb_count < 1) {
1220 rgblight_sethsv_noeeprom(HSV_OFF);
1221 rgblight_set_effect_range(0, 9);
1222 } else if (wake_rgb_count < 2 && wake_rgb_count > 0) {
1223 rgblight_sethsv_noeeprom(HSV_BLACK);
1224 rgblight_set_effect_range(0, 2);
1225 rgblight_sethsv_noeeprom(HSV_WHITE);
1226 rgblight_set_effect_range(2, 9);
1227 } else if (wake_rgb_count < 3 && wake_rgb_count > 1) {
1228 rgblight_sethsv_noeeprom(HSV_BLACK);
1229 rgblight_set_effect_range(0, 2);
1230 rgblight_sethsv_noeeprom(HSV_WHITE);
1231 rgblight_set_effect_range(2, 9);
1232 } else if (wake_rgb_count < 4 && wake_rgb_count > 2) {
1233 rgblight_sethsv_noeeprom(HSV_BLACK);
1234 rgblight_set_effect_range(0, 3);
1235 rgblight_sethsv_noeeprom(HSV_WHITE);
1236 rgblight_set_effect_range(3, 9);
1237 } else if (wake_rgb_count < 5 && wake_rgb_count > 3) {
1238 rgblight_sethsv_noeeprom(HSV_BLACK);
1239 rgblight_set_effect_range(0, 4);
1240 rgblight_sethsv_noeeprom(HSV_WHITE);
1241 rgblight_set_effect_range(4, 9);
1242 } else if (wake_rgb_count < 6 && wake_rgb_count > 4) {
1243 rgblight_sethsv_noeeprom(HSV_BLACK);
1244 rgblight_set_effect_range(0, 5);
1245 rgblight_sethsv_noeeprom(HSV_WHITE);
1246 rgblight_set_effect_range(5, 9);
1247 } else if (wake_rgb_count < 7 && wake_rgb_count > 5) {
1248 rgblight_sethsv_noeeprom(HSV_BLACK);
1249 rgblight_set_effect_range(0, 6);
1250 rgblight_sethsv_noeeprom(HSV_WHITE);
1251 rgblight_set_effect_range(6, 9);
1252 } else if (wake_rgb_count < 8 && wake_rgb_count > 6) {
1253 rgblight_sethsv_noeeprom(HSV_BLACK);
1254 rgblight_set_effect_range(0, 7);
1255 rgblight_sethsv_noeeprom(HSV_WHITE);
1256 rgblight_set_effect_range(7, 9);
1257 } else if (wake_rgb_count < 9 && wake_rgb_count > 7) {
1258 rgblight_sethsv_noeeprom(HSV_BLACK);
1259 rgblight_set_effect_range(0, 8);
1260 rgblight_sethsv_noeeprom(HSV_WHITE);
1261 rgblight_set_effect_range(8, 9);
1262 } else if (wake_rgb_count < 10 && wake_rgb_count > 8) {
1263 rgblight_sethsv_noeeprom(HSV_BLACK);
1264 rgblight_set_effect_range(0, 0);
1265 rgblight_sethsv_noeeprom(HSV_WHITE);
1266 rgblight_set_effect_range(0, 9);
1267 } else if (wake_rgb_count < 11 && wake_rgb_count > 9) {
1268 rgblight_sethsv_noeeprom(HSV_BLACK);
1269 rgblight_set_effect_range(0, 8);
1270 rgblight_sethsv_noeeprom(HSV_WHITE);
1271 rgblight_set_effect_range(8, 9);
1272 } else if (wake_rgb_count < 12 && wake_rgb_count > 10) {
1273 rgblight_sethsv_noeeprom(HSV_BLACK);
1274 rgblight_set_effect_range(0, 7);
1275 rgblight_sethsv_noeeprom(HSV_WHITE);
1276 rgblight_set_effect_range(7, 9);
1277 } else if (wake_rgb_count < 13 && wake_rgb_count > 11) {
1278 rgblight_sethsv_noeeprom(HSV_BLACK);
1279 rgblight_set_effect_range(0, 6);
1280 rgblight_sethsv_noeeprom(HSV_WHITE);
1281 rgblight_set_effect_range(6, 9);
1282 } else if (wake_rgb_count < 14 && wake_rgb_count > 12) {
1283 rgblight_sethsv_noeeprom(HSV_BLACK);
1284 rgblight_set_effect_range(0, 5);
1285 rgblight_sethsv_noeeprom(HSV_WHITE);
1286 rgblight_set_effect_range(5, 9);
1287 } else if (wake_rgb_count < 15 && wake_rgb_count > 13) {
1288 rgblight_sethsv_noeeprom(HSV_BLACK);
1289 rgblight_set_effect_range(0, 4);
1290 rgblight_sethsv_noeeprom(HSV_WHITE);
1291 rgblight_set_effect_range(4, 9);
1292 } else if (wake_rgb_count < 16 && wake_rgb_count > 14) {
1293 rgblight_sethsv_noeeprom(HSV_BLACK);
1294 rgblight_set_effect_range(0, 3);
1295 rgblight_sethsv_noeeprom(HSV_WHITE);
1296 rgblight_set_effect_range(3, 9);
1297 } else if (wake_rgb_count < 17 && wake_rgb_count > 15) {
1298 rgblight_sethsv_noeeprom(HSV_BLACK);
1299 rgblight_set_effect_range(0, 2);
1300 rgblight_sethsv_noeeprom(HSV_WHITE);
1301 rgblight_set_effect_range(2, 9);
1302 } else if (wake_rgb_count < 18 && wake_rgb_count > 16) {
1303 rgblight_sethsv_noeeprom(HSV_BLACK);
1304 rgblight_set_effect_range(0, 1);
1305 rgblight_sethsv_noeeprom(HSV_WHITE);
1306 rgblight_set_effect_range(1, 9);
1307 } else if (wake_rgb_count > 17) {
1308 // Final frame of wake-up rgb animation
1309 rgblight_sethsv_noeeprom(HSV_BLACK);
1310 rgblight_set_effect_range(0, 9);
1311 waking_up = false;
1312 print("I have awoken!\n");
1313#ifdef AUDIO_ENABLE
1314 // Play the wake-up sound *after* we finish the animation
1315 if (do_wake_audio) {
1316 PLAY_SONG(puzzle_song);
1317 }
1318#endif
1319 }
1320 rgblight_mode_noeeprom(RGBLIGHT_MODE_STATIC_LIGHT);
1321 wake_rgb_count++;
1322 wake_rgb_timer = timer_read();
1323 }
1324 }
1325}
1326
1327// Spits out some unicode special characters in response to a tap-dance
1328void send_degree_symbol(qk_tap_dance_state_t* state, void* user_data) {
1329 switch (state->count) {
1330 case 4:
1331 // ℃
1332 unicode_input_start();
1333 register_hex(0x2103);
1334 unicode_input_finish();
1335 print("You pressed the Degrees key 4 times!\n");
1336 reset_tap_dance(state);
1337 break;
1338 case 3:
1339 //℉
1340 unicode_input_start();
1341 register_hex(0x2109);
1342 unicode_input_finish();
1343 print("You pressed the Degrees key 3 times!\n");
1344 reset_tap_dance(state);
1345 break;
1346 case 2:
1347 // €
1348 unicode_input_start();
1349 register_hex(0x20AC);
1350 unicode_input_finish();
1351 print("You pressed the Degrees key 2 times!\n");
1352 reset_tap_dance(state);
1353 break;
1354 case 1:
1355 // °
1356 unicode_input_start();
1357 register_hex(0x00B0);
1358 unicode_input_finish();
1359 print("You pressed the Degrees key 1 time!\n");
1360 reset_tap_dance(state);
1361 break;
1362 }
1363}
1364
1365// Handles per-key configuration of Retro-Tapping
1366bool get_retro_tapping(uint16_t keycode, keyrecord_t* record) {
1367 switch (keycode) {
1368 default:
1369 return false;
1370 }
1371}
1372// Handles per-key configuration of Mod-Tap-Interrupt
1373bool get_ignore_mod_tap_interrupt(uint16_t keycode, keyrecord_t* record) {
1374 switch (keycode) {
1375 default:
1376 return false;
1377 }
1378}
1379// Handles per-key configuration of Tapping Force-Hold
1380bool get_tapping_force_hold(uint16_t keycode, keyrecord_t* record) {
1381 switch (keycode) {
1382 default:
1383 return false;
1384 }
1385}
1386// Handles per-key configuration of Permissive-Hold
1387bool get_permissive_hold(uint16_t keycode, keyrecord_t* record) {
1388 switch (keycode) {
1389 default:
1390 return false;
1391 }
1392}
1393/*
1394 * The following two functions make leader keys "musical"
1395 * by playing sound at different stages of the leader chord
1396 */
1397// Called when you tap the Leader key
1398void leader_start(void) {
1399#ifdef AUDIO_ENABLE
1400 PLAY_SONG(leader_started);
1401#endif
1402}
1403// Called when either the leader sequence is completed, or the leader timeout is hit
1404void leader_end(void) {
1405 if (did_leader_succeed) {
1406#ifdef AUDIO_ENABLE
1407 PLAY_SONG(leader_succeed);
1408#endif
1409 } else {
1410#ifdef AUDIO_ENABLE
1411 PLAY_SONG(leader_fail);
1412#endif
1413 }
1414}
1415
1416// Monitors and labels the current state of any tap-dances
1417td_state_t cur_dance(qk_tap_dance_state_t* state) {
1418 if (state->count == 1) {
1419 if (state->interrupted || !state->pressed) return TD_SINGLE_TAP;
1420 // Key has not been interrupted, but the key is still held. Means you want to send a 'HOLD'.
1421 else
1422 return TD_SINGLE_HOLD;
1423 } else if (state->count == 2) {
1424 if (state->interrupted)
1425 return TD_DOUBLE_SINGLE_TAP;
1426 else if (state->pressed)
1427 return TD_DOUBLE_HOLD;
1428 else
1429 return TD_DOUBLE_TAP;
1430 }
1431 if (state->count == 3) {
1432 if (state->interrupted || !state->pressed)
1433 return TD_TRIPLE_TAP;
1434 else
1435 return TD_TRIPLE_HOLD;
1436 } else
1437 return TD_UNKNOWN;
1438}
1439
1440// Create an instance of 'td_tap_t' for each tap dance.
1441static td_tap_t sml_state = {.is_press_action = true, .state = TD_NONE};
1442static td_tap_t scap_state = {.is_press_action = true, .state = TD_NONE};
1443static td_tap_t slctl_state = {.is_press_action = true, .state = TD_NONE};
1444static td_tap_t slalt_state = {.is_press_action = true, .state = TD_NONE};
1445
1446// Left-Shift->Sticky-Caps tap-dance finished
1447void scap_finished(qk_tap_dance_state_t* state, void* user_data) {
1448 scap_state.state = cur_dance(state);
1449 switch (scap_state.state) {
1450 case TD_SINGLE_HOLD:
1451 register_code(KC_LSFT);
1452 break;
1453 default:
1454 if (host_keyboard_leds() & (1 << USB_LED_CAPS_LOCK)) {
1455 tap_code(KC_CAPS);
1456 reset_tap_dance(state);
1457 break;
1458 } else {
1459 if ((state->count) >= TAPPING_TOGGLE) {
1460 tap_code(KC_CAPS);
1461 reset_tap_dance(state);
1462 break;
1463 } else {
1464 register_code(KC_LSFT);
1465 break;
1466 }
1467 }
1468 }
1469}
1470
1471// Left-Shift->Sticky-Caps tap-dance reset
1472void scap_reset(qk_tap_dance_state_t* state, void* user_data) {
1473 unregister_code(KC_LSHIFT);
1474 scap_state.state = TD_NONE;
1475}
1476
1477// Sticky-Left-Control tap-dance finished
1478void slctl_finished(qk_tap_dance_state_t* state, void* user_data) {
1479 slctl_state.state = cur_dance(state);
1480 switch (slctl_state.state) {
1481 case TD_SINGLE_HOLD:
1482 register_code(KC_LCTL);
1483 break;
1484 default:
1485 if (lctl_sticky) {
1486 unregister_code(KC_LCTL);
1487 lctl_sticky = false;
1488 PLAY_SONG(slctl_off);
1489 reset_tap_dance(state);
1490 break;
1491 } else {
1492 if ((state->count) >= TAPPING_TOGGLE) {
1493 register_code(KC_LCTL);
1494 lctl_sticky = true;
1495 PLAY_SONG(slctl_on);
1496 reset_tap_dance(state);
1497 break;
1498 } else {
1499 register_code(KC_LCTL);
1500 reset_tap_dance(state);
1501 break;
1502 }
1503 }
1504 }
1505}
1506
1507// Sticky-Left-Control tap-dance reset
1508void slctl_reset(qk_tap_dance_state_t* state, void* user_data) {
1509 if (!lctl_sticky) {
1510 unregister_code(KC_LCTL);
1511 slctl_state.state = TD_NONE;
1512 } else {
1513 slctl_state.state = TD_NONE;
1514 }
1515}
1516
1517// Sticky-Left-Alt tap-dance finished
1518void slalt_finished(qk_tap_dance_state_t* state, void* user_data) {
1519 slalt_state.state = cur_dance(state);
1520 switch (slalt_state.state) {
1521 case TD_SINGLE_HOLD:
1522 register_code(KC_LALT);
1523 break;
1524 default:
1525 if (lalt_sticky) {
1526 unregister_code(KC_LALT);
1527 lalt_sticky = false;
1528 PLAY_SONG(slalt_off);
1529 reset_tap_dance(state);
1530 break;
1531 } else {
1532 if ((state->count) >= TAPPING_TOGGLE) {
1533 register_code(KC_LALT);
1534 lalt_sticky = true;
1535 PLAY_SONG(slalt_on);
1536 reset_tap_dance(state);
1537 break;
1538 } else {
1539 register_code(KC_LALT);
1540 reset_tap_dance(state);
1541 break;
1542 }
1543 }
1544 }
1545}
1546
1547// Sticky-Left-Alt tap-dance reset
1548void slalt_reset(qk_tap_dance_state_t* state, void* user_data) {
1549 if (!lalt_sticky) {
1550 unregister_code(KC_LALT);
1551 slalt_state.state = TD_NONE;
1552 } else {
1553 slalt_state.state = TD_NONE;
1554 }
1555}
1556
1557// Smiley key tap-dance finished
1558void sml_finished(qk_tap_dance_state_t* state, void* user_data) {
1559 sml_state.state = cur_dance(state);
1560 switch (sml_state.state) {
1561 default:
1562 switch (state->count) {
1563 default:
1564 // 👍
1565 send_unicode_string("👍");
1566 print("You pressed the Emoji key at least 11 times!\n");
1567 reset_tap_dance(state);
1568 break;
1569 case 10:
1570 // 👎
1571 send_unicode_string("👎");
1572 print("You pressed the Emoji key 10 times!\n");
1573 reset_tap_dance(state);
1574 break;
1575 case 9:
1576 //🍌
1577 send_unicode_string("🍌");
1578 print("You pressed the Emoji key 9 times!\n");
1579 reset_tap_dance(state);
1580 break;
1581 case 8:
1582 // 🍑
1583 send_unicode_string("🍑");
1584 print("You pressed the Emoji key 8 times!\n");
1585 reset_tap_dance(state);
1586 break;
1587 case 7:
1588 // 🐕
1589 send_unicode_string("🐕");
1590 print("You pressed the Emoji key 7 times!\n");
1591 reset_tap_dance(state);
1592 break;
1593 case 6:
1594 // 🐈
1595 send_unicode_string("🐈");
1596 print("You pressed the Emoji key 6 times!\n");
1597 reset_tap_dance(state);
1598 break;
1599 case 5:
1600 // 🐍
1601 send_unicode_string("🐍");
1602 print("You pressed the Emoji key 5 times!\n");
1603 reset_tap_dance(state);
1604 break;
1605 case 4:
1606 //🐒
1607 send_unicode_string("🐒");
1608 print("You pressed the Emoji key 4 times!\n");
1609 reset_tap_dance(state);
1610 break;
1611 case 3:
1612 // 💩
1613 send_unicode_string("💩");
1614 print("You pressed the Emoji key 3 times!\n");
1615 reset_tap_dance(state);
1616 break;
1617 case 2:
1618 // 🙁
1619 send_unicode_string("🙁");
1620 print("You pressed the Emoji key 2 times!\n");
1621 reset_tap_dance(state);
1622 break;
1623 case 1:
1624 // 🙂
1625 send_unicode_string("🙂");
1626 print("You pressed the Emoji key 1 time!\n");
1627 reset_tap_dance(state);
1628 break;
1629 }
1630 break;
1631 case TD_SINGLE_HOLD:
1632 // 👍
1633 send_unicode_string("👍");
1634 print("You single-held the Emoji key!\n");
1635 reset_tap_dance(state);
1636 break;
1637 case TD_DOUBLE_HOLD:
1638 // 👎
1639 send_unicode_string("👎");
1640 print("You double-held the Emoji key!\n");
1641 reset_tap_dance(state);
1642 break;
1643 case TD_TRIPLE_HOLD:
1644 //🤯
1645 send_unicode_string("🤯");
1646 print("You triple-held the Emoji key!\n");
1647 reset_tap_dance(state);
1648 break;
1649 case TD_NONE:
1650 reset_tap_dance(state);
1651 break;
1652 }
1653}
1654void sml_reset(qk_tap_dance_state_t* state, void* user_data) { sml_state.state = TD_NONE; }
1655
1656// Tap Dance definitions
1657qk_tap_dance_action_t tap_dance_actions[] = {
1658 // Tap once for °, twice for ℉, thrice for ℃
1659 [TD_DEG_DEGF] = ACTION_TAP_DANCE_FN(send_degree_symbol), //
1660 [TD_LSHFT_CAPS] = ACTION_TAP_DANCE_FN_ADVANCED_TIME(NULL, scap_finished, scap_reset, 200), //
1661 [TD_LCTL_STICKY] = ACTION_TAP_DANCE_FN_ADVANCED_TIME(NULL, slctl_finished, slctl_reset, 200), //
1662 [TD_LALT_STICKY] = ACTION_TAP_DANCE_FN_ADVANCED_TIME(NULL, slalt_finished, slalt_reset, 200), //
1663 [TD_SMILEY] = ACTION_TAP_DANCE_FN_ADVANCED_TIME(NULL, sml_finished, sml_reset, 500),
1664};
1665
1666// Dip-Switch controls
1667void dip_switch_update_user(uint8_t index, bool active) {
1668 switch (index) {
1669 case 0: {
1670#ifdef AUDIO_ENABLE
1671 static bool play_sound = false;
1672#endif
1673 if (active) {
1674#ifdef AUDIO_ENABLE
1675 if (play_sound) {
1676 PLAY_SONG(plover_song);
1677 }
1678#endif
1679 layer_on(_ADJUST);
1680 } else {
1681#ifdef AUDIO_ENABLE
1682 if (play_sound) {
1683 PLAY_SONG(plover_gb_song);
1684 }
1685#endif
1686 layer_off(_ADJUST);
1687 }
1688#ifdef AUDIO_ENABLE
1689 play_sound = true;
1690#endif
1691 break;
1692 }
1693 case 1:
1694 if (active) {
1695 muse_mode = true;
1696 } else {
1697 muse_mode = false;
1698 }
1699 }
1700}
1701
1702// Runs at every complete matrix scan
1703void matrix_scan_user(void) {
1704 // Some code for controlling MIDI output
1705#ifdef AUDIO_ENABLE
1706 if (muse_mode) {
1707 if (muse_counter == 0) {
1708 uint8_t muse_note = muse_offset + SCALE[muse_clock_pulse()];
1709 if (muse_note != last_muse_note) {
1710 stop_note(compute_freq_for_midi_note(last_muse_note));
1711 play_note(compute_freq_for_midi_note(muse_note), 0xF);
1712 last_muse_note = muse_note;
1713 }
1714 }
1715 muse_counter = (muse_counter + 1) % muse_tempo;
1716 } else {
1717 if (muse_counter) {
1718 stop_all_notes();
1719 muse_counter = 0;
1720 }
1721 }
1722#endif
1723 // Check the shift-state and hold-time for the Irony key
1724 if (irony_active) {
1725 if ((get_mods() & MOD_MASK_SHIFT)) {
1726 irony_shifted = true;
1727 } else {
1728 irony_shifted = false;
1729 }
1730 if (timer_elapsed(irony_pressed_time) >= IRONY_HOLD_DELAY) {
1731 if (irony_shifted) {
1732 send_unicode_string(bang_str);
1733 } else {
1734 send_unicode_string(irony_str);
1735 }
1736 }
1737 }
1738
1739 // Monitor and respond to the current Alt+Tab state
1740 if (is_alt_tab_active) {
1741 if (timer_elapsed(alt_tab_timer) > 1000) {
1742 unregister_code(KC_LALT);
1743 is_alt_tab_active = false;
1744 }
1745 }
1746 // Monitor and perform leader-key chords
1747 LEADER_DICTIONARY() {
1748 did_leader_succeed = leading = false;
1749
1750 SEQ_ONE_KEY(KC_E) {
1751 SEND_STRING(SS_LCTL(SS_LSFT("t")));
1752 did_leader_succeed = true;
1753 }
1754 SEQ_ONE_KEY(KC_C) {
1755 SEND_STRING(SS_LGUI("r") SS_DELAY(250) "calc\n");
1756 did_leader_succeed = true;
1757 }
1758 else SEQ_ONE_KEY(KC_V) {
1759 SEND_STRING(SS_LCTL("v"));
1760 did_leader_succeed = true;
1761 }
1762 else SEQ_TWO_KEYS(KC_E, KC_D) {
1763 SEND_STRING(SS_LGUI("r") "cmd\n" SS_LCTL("c"));
1764 did_leader_succeed = true;
1765 }
1766 else SEQ_TWO_KEYS(KC_A, KC_C) {
1767 SEND_STRING(SS_LCTL("a") SS_LCTL("c"));
1768 did_leader_succeed = true;
1769 }
1770 else SEQ_THREE_KEYS(KC_C, KC_A, KC_T) {
1771 send_unicode_string("😸");
1772 did_leader_succeed = true;
1773 }
1774 else SEQ_THREE_KEYS(KC_B, KC_A, KC_T) {
1775 send_unicode_string("🦇");
1776 did_leader_succeed = true;
1777 }
1778 else SEQ_THREE_KEYS(KC_D, KC_O, KC_G) {
1779 send_unicode_string("🐶");
1780 did_leader_succeed = true;
1781 }
1782 else SEQ_FIVE_KEYS(KC_S, KC_M, KC_I, KC_L, KC_E) {
1783 send_unicode_string("🙂");
1784 did_leader_succeed = true;
1785 }
1786 else SEQ_FOUR_KEYS(KC_H, KC_A, KC_P, KC_Y) {
1787 send_unicode_string("🙂");
1788 did_leader_succeed = true;
1789 }
1790 else SEQ_FIVE_KEYS(KC_H, KC_A, KC_P, KC_P, KC_Y) {
1791 send_unicode_string("🙂");
1792 did_leader_succeed = true;
1793 }
1794 else SEQ_THREE_KEYS(KC_S, KC_A, KC_D) {
1795 send_unicode_string("🙁");
1796 did_leader_succeed = true;
1797 }
1798 else SEQ_THREE_KEYS(KC_Y, KC_E, KC_S) {
1799 send_unicode_string("👍");
1800 did_leader_succeed = true;
1801 }
1802 else SEQ_TWO_KEYS(KC_N, KC_O) {
1803 send_unicode_string("👎");
1804 did_leader_succeed = true;
1805 }
1806 else SEQ_THREE_KEYS(KC_W, KC_O, KC_W) {
1807 send_unicode_string("🤯");
1808 did_leader_succeed = true;
1809 }
1810 else SEQ_THREE_KEYS(KC_P, KC_O, KC_O) {
1811 send_unicode_string("💩");
1812 did_leader_succeed = true;
1813 }
1814 else SEQ_FOUR_KEYS(KC_P, KC_O, KC_O, KC_P) {
1815 send_unicode_string("💩");
1816 did_leader_succeed = true;
1817 }
1818 else SEQ_FOUR_KEYS(KC_B, KC_O, KC_A, KC_T) {
1819 send_unicode_string("⛵");
1820 did_leader_succeed = true;
1821 }
1822 leader_end();
1823 }
1824 // Run the wake-up RGB animation if performing wake-up
1825 if (do_wake_animation) {
1826 rgb_wakeup_sequence();
1827 }
1828}
1829
1830// Music mask controls
1831
1832bool music_mask_user(uint16_t keycode) {
1833 switch (keycode) {
1834 case RAISE:
1835 case LOWER:
1836 return false;
1837 default:
1838 return true;
1839 }
1840}
1841
1842void suspend_power_down_user(void) {
1843 // Runs during start of system suspend
1844 print("Going to sleep.");
1845}
1846
1847void suspend_wakeup_init_user(void) {
1848 // Runs during wake from system suspend
1849}
1850
1851void keyboard_post_init_user(void) {
1852 // Print welcome message to console
1853 printf("Welcome to %s!\n", KEEB_MODEL_NAME);
1854 // Read the user config from EEPROM
1855 user_config.raw = eeconfig_read_user();
1856 do_wake_animation = user_config.do_wakeup_animation;
1857 do_wake_audio = user_config.do_wakeup_audio;
1858 rgbcon_tracker = user_config.rgbcon_tracker;
1859
1860 // Tell the console the status of saved config
1861 if (user_config.do_wakeup_animation) {
1862 print("Wake animation enabled.\n");
1863 } else {
1864 print("Wake animation disabled.\n");
1865 }
1866 if (user_config.do_wakeup_audio) {
1867 print("Wake music enabled.\n");
1868 } else {
1869 print("Wake music disabled.\n");
1870 }
1871 switch (user_config.rgbcon_tracker) {
1872 case 2:
1873 print("RGB mode: Static White\n");
1874 break;
1875 case 3:
1876 print("RGB mode: Static Cyan\n");
1877 break;
1878 case 4:
1879 print("RGB mode: Breathing Lights\n");
1880 break;
1881 case 5:
1882 print("RGB mode: Rainbow Swirl\n");
1883 break;
1884 case 6:
1885 print("RGB mode: Rainbow Mood\n");
1886 break;
1887 default:
1888 print("RGB mode: Disabled RGB\n");
1889 break;
1890 }
1891
1892 // Enable the LED layers
1893 rgblight_enable_noeeprom(); // Enables RGB, without saving settings
1894 rgblight_layers = my_rgb_layers;
1895
1896 /*
1897 * Initialize the LED crawl wake animation here
1898 * To perform it on just the first wake
1899 */
1900 wake_rgb_timer = timer_read();
1901 waking_up = true;
1902
1903 // Initialize OLED display
1904 /*
1905 if (USING_OLED_DISPLAY) {
1906 print("Initializing display!\n");
1907 render_logo();
1908 }
1909 */
1910}
1911
1912// EEPROM is getting reset!
1913void eeconfig_init_user(void) {
1914 user_config.raw = 0;
1915 eeconfig_update_user(user_config.raw); // Write default value to EEPROM now
1916}
1917
1918// Communicate 2-way with host via HID_RAW
1919#ifdef RAW_ENABLE
1920void raw_hid_receive(uint8_t* data, uint8_t length) {
1921 // Sample code below simply echoes back to the console any data received by the raw_hid process
1922
1923# ifdef CONSOLE_ENABLE
1924 dprint("Received USB data from host system:\n");
1925 dprintf("%s\n", data);
1926# endif
1927}
1928#endif