summaryrefslogtreecommitdiff
path: root/users
diff options
context:
space:
mode:
Diffstat (limited to 'users')
-rw-r--r--users/333fred/333fred.h10
-rw-r--r--users/333fred/333fred_config.h1
-rw-r--r--users/arkag/arkag.c528
-rw-r--r--users/arkag/arkag.h152
-rw-r--r--users/arkag/config.h6
-rw-r--r--users/arkag/mechmini2.jpgbin0 -> 3548191 bytes
-rw-r--r--users/arkag/readme.md42
-rw-r--r--users/arkag/rules.mk1
-rw-r--r--users/bocaj/bocaj.c189
-rw-r--r--users/bocaj/bocaj.h85
-rw-r--r--users/bocaj/config.h33
-rw-r--r--users/bocaj/process_records.c149
-rw-r--r--users/bocaj/process_records.h52
-rw-r--r--users/bocaj/readme.md102
-rw-r--r--users/bocaj/rules.mk33
-rw-r--r--users/bocaj/send_unicode.c106
-rw-r--r--users/bocaj/send_unicode.h (renamed from users/drashna/drashna_unicode.h)10
-rw-r--r--users/bocaj/tap_dances.c64
-rw-r--r--users/bocaj/tap_dances.h19
-rw-r--r--users/bocaj/wrappers.h37
-rw-r--r--users/doogle999/doogle999.c460
-rw-r--r--users/doogle999/doogle999.h99
-rw-r--r--users/doogle999/readme.md41
-rw-r--r--users/doogle999/rules.mk14
-rw-r--r--users/drashna/.gitlab-ci.yml78
-rw-r--r--users/drashna/config.h41
-rw-r--r--users/drashna/drashna.c383
-rw-r--r--users/drashna/drashna.h319
-rw-r--r--users/drashna/process_records.c178
-rw-r--r--users/drashna/process_records.h101
-rw-r--r--users/drashna/readme.md97
-rw-r--r--users/drashna/rgb_stuff.c129
-rw-r--r--users/drashna/rgb_stuff.h9
-rw-r--r--users/drashna/rules.mk11
-rw-r--r--users/drashna/send_unicode.h71
-rw-r--r--users/drashna/tap_dances.c11
-rw-r--r--users/drashna/tap_dances.h12
-rw-r--r--users/drashna/template.c102
-rw-r--r--users/drashna/template.h8
-rw-r--r--users/drashna/wrappers.h171
-rw-r--r--users/edvorakjp/edvorakjp.c222
-rw-r--r--users/edvorakjp/edvorakjp.h37
-rw-r--r--users/edvorakjp/edvorakjp_process_record.c214
-rw-r--r--users/edvorakjp/edvorakjp_status.c75
-rw-r--r--users/edvorakjp/edvorakjp_tap_dance.c71
-rw-r--r--users/edvorakjp/readme.md12
-rw-r--r--users/edvorakjp/rules.mk8
-rwxr-xr-xusers/ishtob/config.h75
-rw-r--r--users/ishtob/ishtob.c69
-rw-r--r--users/ishtob/ishtob.h240
-rw-r--r--users/ishtob/readme.md87
-rwxr-xr-xusers/ishtob/rules.mk7
-rw-r--r--users/jarred/config.h50
-rw-r--r--users/jarred/jarred.c15
-rw-r--r--users/jarred/jarred.h8
-rw-r--r--users/jarred/rules.mk15
-rw-r--r--users/kageurufu/config.h4
-rw-r--r--users/kageurufu/custom_rgb.c18
-rw-r--r--users/kageurufu/custom_rgb.h3
-rw-r--r--users/kageurufu/kageurufu.c12
-rw-r--r--users/kageurufu/kageurufu.h5
-rw-r--r--users/kageurufu/layouts.h58
-rw-r--r--users/kageurufu/process_records.c44
-rw-r--r--users/kageurufu/process_records.h27
-rw-r--r--users/kageurufu/readme.md14
-rw-r--r--users/kageurufu/rules.mk15
-rw-r--r--users/kuatsure/kuatsure.h2
-rw-r--r--users/kuatsure/rules.mk2
-rw-r--r--users/mechmerlin/changelog.md14
-rw-r--r--users/mechmerlin/config.h5
-rw-r--r--users/mechmerlin/mechmerlin.c20
-rw-r--r--users/mechmerlin/mechmerlin.h17
-rw-r--r--users/mechmerlin/readme.md40
-rw-r--r--users/mechmerlin/rules.mk1
-rw-r--r--users/mtdjr/mtdjr.c2
-rw-r--r--users/mtdjr/mtdjr.h2
-rw-r--r--users/replicaJunction/config.h66
-rw-r--r--users/replicaJunction/readme.md14
-rw-r--r--users/replicaJunction/replicaJunction.c149
-rw-r--r--users/replicaJunction/replicaJunction.h115
-rw-r--r--users/replicaJunction/rules.mk1
-rw-r--r--users/romus/README.md45
-rw-r--r--users/romus/config.h8
-rw-r--r--users/romus/romus.c557
-rw-r--r--users/romus/romus.h272
-rw-r--r--users/romus/rules.mk24
-rw-r--r--users/sigma/config.h21
-rw-r--r--users/sigma/rules.mk3
-rw-r--r--users/sigma/sigma.c276
-rw-r--r--users/sigma/sigma.h58
-rw-r--r--users/spacebarracecar/config.h0
-rw-r--r--users/spacebarracecar/readme.md111
-rw-r--r--users/spacebarracecar/rules.mk5
-rw-r--r--users/spacebarracecar/spacebarracecar.c342
-rw-r--r--users/spacebarracecar/spacebarracecar.h241
-rw-r--r--users/talljoe/config.h7
-rw-r--r--users/talljoe/rules.mk2
-rw-r--r--users/talljoe/talljoe.c85
-rw-r--r--users/talljoe/talljoe.h76
-rw-r--r--users/talljoe/tapdance.c148
-rw-r--r--users/turbomech/backupturbomech.c1
-rw-r--r--users/wanleg/config.h44
-rw-r--r--users/wanleg/readme.md14
-rw-r--r--users/wanleg/rules.mk39
-rw-r--r--users/wanleg/tapdances.c264
-rw-r--r--users/wanleg/wanleg.c139
-rw-r--r--users/wanleg/wanleg.h309
-rw-r--r--users/xtonhasvim/fancylighting.c172
-rw-r--r--users/xtonhasvim/fancylighting.h36
-rw-r--r--users/xtonhasvim/rules.mk1
-rw-r--r--users/xtonhasvim/xtonhasvim.c72
-rw-r--r--users/xtonhasvim/xtonhasvim.h13
-rw-r--r--users/zer09/config.h6
-rw-r--r--users/zer09/tap_dance.c27
-rw-r--r--users/zer09/zer09.h10
115 files changed, 8135 insertions, 1102 deletions
diff --git a/users/333fred/333fred.h b/users/333fred/333fred.h
index 8599198a57..443930a6b1 100644
--- a/users/333fred/333fred.h
+++ b/users/333fred/333fred.h
@@ -4,10 +4,12 @@
#define BASE 0
#define CODE 1 // code layer
-#define SYMB 2
-#define MDIA 3 // media keys
-#define VIM 4
-#define GAME 5
+#define CODEFLOW 2
+#define SYMB 3
+#define MDIA 4 // media keys
+#define VIM 5
+#define GAME 6
+#define GAME_ARROW 7
// Tap dance config shared between my keyboards
enum tap_dance_declarations {
diff --git a/users/333fred/333fred_config.h b/users/333fred/333fred_config.h
index 7c637d8d36..b158e2d5a2 100644
--- a/users/333fred/333fred_config.h
+++ b/users/333fred/333fred_config.h
@@ -1,4 +1,3 @@
#pragma once
-#define PREVENT_STUCK_MODIFIERS
#define PERMISSIVE_HOLD
diff --git a/users/arkag/arkag.c b/users/arkag/arkag.c
new file mode 100644
index 0000000000..212d06de67
--- /dev/null
+++ b/users/arkag/arkag.c
@@ -0,0 +1,528 @@
+#include "arkag.h"
+
+/*
+ Current Layout and Keeb:
+ https://github.com/arkag/qmk_firmware/blob/master/keyboards/mechmini/v2/keymaps/arkag/keymap.c
+*/
+
+// Start: Written by konstantin: vomindoraan
+#include <ctype.h>
+#include <stdlib.h>
+#include <string.h>
+
+void send_unicode_hex_string(const char *str) {
+ if (!str) { return; } // Saftey net
+ while (*str) {
+ // Find the next code point (token) in the string
+ for (; *str == ' '; str++);
+ size_t n = strcspn(str, " "); // Length of the current token
+ char code_point[n+1];
+ strncpy(code_point, str, n);
+ code_point[n] = '\0'; // Make sure it's null-terminated
+
+ // Normalize the code point: make all hex digits lowercase
+ for (char *p = code_point; *p; p++) {
+ *p = tolower(*p);
+ }
+
+ // Send the code point as a Unicode input string
+ unicode_input_start();
+ send_string(code_point);
+ unicode_input_finish();
+ str += n; // Move to the first ' ' (or '\0') after the current token
+ }
+}
+// End: Written by konstantin: vomindoraan
+
+// Start: Written by Chris Lewis
+#ifndef MIN
+#define MIN(a,b) (((a)<(b))?(a):(b))
+#endif
+#ifndef MAX
+#define MAX(a,b) (((a)>(b))?(a):(b))
+#endif
+
+#define TYPING_SPEED_MAX_VALUE 200
+uint8_t typing_speed = 0;
+
+void velocikey_accelerate() {
+ if (typing_speed < TYPING_SPEED_MAX_VALUE) typing_speed += (TYPING_SPEED_MAX_VALUE / 50);
+}
+
+void velocikey_decelerate() {
+ static uint16_t decay_timer = 0;
+
+ if (timer_elapsed(decay_timer) > 500 || decay_timer == 0) {
+ if (typing_speed > 0) typing_speed -= 1;
+ //Decay a little faster at half of max speed
+ if (typing_speed > TYPING_SPEED_MAX_VALUE / 2) typing_speed -= 1;
+ //Decay even faster at 3/4 of max speed
+ if (typing_speed > TYPING_SPEED_MAX_VALUE / 4 * 3) typing_speed -= 3;
+ decay_timer = timer_read();
+ }
+}
+
+uint8_t velocikey_match_speed(uint8_t minValue, uint8_t maxValue) {
+ return MAX(minValue, maxValue - (maxValue - minValue) * ((float)typing_speed / TYPING_SPEED_MAX_VALUE));
+}
+// End: Written by Chris Lewis
+
+uint8_t current_os,
+ mod_primary_mask,
+ fade_interval,
+ num_extra_flashes_off = 0;
+Color underglow,
+ flash_color,
+ saved_color,
+ hsv_none = {0,0,0};
+flashState flash_state = no_flash;
+fadeState fade_state = add_fade;
+activityState state = boot;
+
+void set_color (Color new, bool update) {
+ rgblight_sethsv_eeprom_helper(new.h, new.s, new.v, update);
+}
+
+void save_color(Color to_save) {
+ saved_color = to_save;
+}
+
+void reset_color(void) {
+ underglow = saved_color;
+}
+
+Color mod_color(Color current_color, bool should_add, uint8_t change_amount) {
+ save_color(underglow);
+ int addlim = 359 - change_amount;
+ int sublim = change_amount;
+ int leftovers;
+ if (should_add) {
+ if (current_color.h <= addlim) {
+ current_color.h += change_amount;
+ } else {
+ leftovers = (359 + change_amount) % 359;
+ current_color.h = 0 + leftovers;
+ }
+ } else {
+ if (current_color.h >= sublim) {
+ current_color.h -= change_amount;
+ } else {
+ leftovers = change_amount - current_color.h;
+ current_color.h = 359 - leftovers;
+ }
+ }
+ return current_color;
+}
+
+void check_state (void) {
+ static uint16_t active_timer;
+ if (!active_timer) {active_timer = timer_read();}
+ static bool activated, deactivated, slept;
+ switch (state) {
+ case active:
+ if (!activated) {
+ if (slept) {rgblight_mode_noeeprom(1);}
+ activated = true;
+ deactivated = false;
+ slept = false;
+ }
+ fade_interval = velocikey_match_speed(1, 25);
+ if (timer_elapsed(active_timer) < INACTIVE_DELAY) {return;}
+ active_timer = timer_read();
+ state = inactive;
+ return;
+
+ case inactive:
+ if (!deactivated) {
+ deactivated = true;
+ activated = false;
+ slept = false;
+ }
+ velocikey_decelerate();
+ fade_interval = velocikey_match_speed(1, 25);
+ if (timer_elapsed(active_timer) < SLEEP_DELAY) {return;}
+ state = sleeping;
+ return;
+
+ case sleeping:
+ if (!slept) {
+ rgblight_mode_noeeprom(4);
+ slept = true;
+ activated = false;
+ deactivated = false;
+ }
+ return;
+
+ case boot:
+ return;
+ }
+}
+
+void fade_rgb (void) {
+ static uint16_t fade_timer;
+ if (state == boot) {return;}
+ if (!fade_timer) {fade_timer = timer_read();}
+ if (timer_elapsed(fade_timer) < fade_interval) {return;}
+ switch (fade_state) {
+ case add_fade:
+ if (underglow.h == 359) {
+ fade_state = sub_fade;
+ return;
+ }
+ underglow.h = underglow.h + 1;
+ break;
+
+ case sub_fade:
+ if (underglow.h == 0) {
+ fade_state = add_fade;
+ return;
+ }
+ underglow.h = underglow.h - 1;
+ break;
+ }
+ fade_timer = timer_read();
+ if (flash_state == no_flash) {
+ set_color(underglow, false);
+ }
+}
+
+void flash_rgb (void) {
+ static uint16_t flash_timer;
+ switch(flash_state) {
+ case no_flash:
+ return;
+
+ case flash_off:
+ if (!flash_timer) {flash_timer = timer_read();}
+ if (timer_elapsed(flash_timer) >= LED_FLASH_DELAY) {
+ set_color(hsv_none, false);
+ flash_timer = timer_read();
+ flash_state = flash_on;
+ }
+ return;
+
+ case flash_on:
+ if (timer_elapsed(flash_timer) >= LED_FLASH_DELAY) {
+ set_color(flash_color, false);
+ flash_timer = timer_read();
+ if (num_extra_flashes_off > 0) {
+ flash_state = flash_off;
+ num_extra_flashes_off--;
+ } else {
+ set_color(underglow, false);
+ flash_state = no_flash;
+ }
+ }
+ return;
+ }
+}
+
+void set_os (uint8_t os, bool update) {
+ current_os = os;
+ if (update) {
+ eeprom_update_byte(EECONFIG_USERSPACE, current_os);
+ }
+ switch (os) {
+ case OS_MAC:
+ set_unicode_input_mode(UC_OSX);
+ underglow = (Color){ 300, 255, 255 };
+ mod_primary_mask = MOD_GUI_MASK;
+ break;
+ case OS_WIN:
+ set_unicode_input_mode(UC_WINC);
+ underglow = (Color){ 180, 255, 255 };
+ mod_primary_mask = MOD_CTL_MASK;
+ break;
+ case OS_NIX:
+ set_unicode_input_mode(UC_LNX);
+ underglow = (Color){ 60, 255, 255 };
+ mod_primary_mask = MOD_CTL_MASK;
+ break;
+ default:
+ underglow = (Color){ 0, 0, 255 };
+ mod_primary_mask = MOD_CTL_MASK;
+ }
+ set_color(underglow, update);
+ flash_color = underglow;
+ flash_state = flash_off;
+ state = boot;
+ num_extra_flashes_off = 1;
+}
+
+void tap_key(uint8_t keycode) {
+ register_code(keycode);
+ unregister_code(keycode);
+}
+
+// register GUI if Mac or Ctrl if other
+void pri_mod(bool press) {
+ if (press) {
+ if (current_os == OS_MAC) {
+ register_code(KC_LGUI);
+ } else {
+ register_code(KC_LCTL);
+ }
+ } else {
+ if (current_os == OS_MAC) {
+ unregister_code(KC_LGUI);
+ } else {
+ unregister_code(KC_LCTL);
+ }
+ }
+}
+
+// register Ctrl if Mac or GUI if other
+void sec_mod(bool press) {
+ if (press) {
+ if (current_os == OS_MAC) {
+ register_code(KC_LCTL);
+ } else {
+ register_code(KC_LGUI);
+ }
+ } else {
+ if (current_os == OS_MAC) {
+ unregister_code(KC_LCTL);
+ } else {
+ unregister_code(KC_LGUI);
+ }
+ }
+}
+
+void surround_type(uint8_t num_of_chars, uint16_t keycode, bool use_shift) {
+ if (use_shift) {
+ register_code(KC_LSFT);
+ }
+ for (int i = 0; i < num_of_chars; i++) {
+ tap_key(keycode);
+ }
+ if (use_shift) {
+ unregister_code(KC_LSFT);
+ }
+ for (int i = 0; i < (num_of_chars/2); i++) {
+ tap_key(KC_LEFT);
+ }
+}
+
+void long_keystroke(size_t num_of_keys, uint16_t keys[]) {
+ for (int i = 0; i < num_of_keys-1; i++) {
+ register_code(keys[i]);
+ }
+ tap_key(keys[num_of_keys-1]);
+ for (int i = 0; i < num_of_keys-1; i++) {
+ unregister_code(keys[i]);
+ }
+}
+
+void dance_grv (qk_tap_dance_state_t *state, void *user_data) {
+ if (state->count == 1) {
+ tap_key(KC_GRV);
+ } else if (state->count == 2) {
+ surround_type(2, KC_GRAVE, false);
+ } else {
+ surround_type(6, KC_GRAVE, false);
+ }
+}
+
+void dance_quot (qk_tap_dance_state_t *state, void *user_data) {
+ if (state->count == 1) {
+ tap_key(KC_QUOT);
+ } else if (state->count == 2) {
+ surround_type(2, KC_QUOTE, false);
+ } else if (state->count == 3) {
+ surround_type(2, KC_QUOTE, true);
+ }
+}
+
+void dance_strk (qk_tap_dance_state_t *state, void *user_data) {
+ if (state->count == 1) {
+ surround_type(4, KC_TILDE, true);
+ } else if (state->count == 2) {
+ if (current_os == OS_MAC) {
+ long_keystroke(3, (uint16_t[]){KC_LGUI, KC_LSFT, KC_4});
+ } else if (current_os == OS_WIN) {
+ long_keystroke(3, (uint16_t[]){KC_LGUI, KC_LSFT, KC_S});
+ } else {
+ return;
+ }
+ }
+}
+
+void dance_3 (qk_tap_dance_state_t *state, void *user_data) {
+ if (state->count == 1) {
+ tap_key(KC_3);
+ } else if (state->count == 2) {
+ send_unicode_hex_string("00E8");
+ } else if (state->count == 3) {
+ send_unicode_hex_string("00E9");
+ }
+}
+
+void dance_c (qk_tap_dance_state_t *state, void *user_data) {
+ if (state->count == 1) {
+ tap_key(KC_C);
+ } else if (state->count == 2) {
+ send_unicode_hex_string("00E7");
+ }
+}
+
+void matrix_init_user(void) {
+ current_os = eeprom_read_byte(EECONFIG_USERSPACE);
+ set_os(current_os, false);
+}
+
+LEADER_EXTERNS();
+
+void matrix_scan_user(void) {
+ check_state();
+ flash_rgb();
+ fade_rgb();
+ LEADER_DICTIONARY() {
+ leading = false;
+ leader_end();
+
+ // begin OS functions
+ SEQ_TWO_KEYS(KC_P, KC_B) {
+ if (current_os == OS_WIN) {
+ SEND_STRING(SS_DOWN(X_LGUI) SS_TAP(X_PAUSE) SS_UP(X_LGUI));
+ } else {
+ }
+ }
+ SEQ_THREE_KEYS(KC_C, KC_A, KC_D) {
+ if (current_os == OS_WIN) {
+ SEND_STRING(SS_DOWN(X_LCTRL) SS_DOWN(X_LALT) SS_TAP(X_DELETE) SS_UP(X_LALT) SS_UP(X_LCTRL));
+ } else {
+ }
+ }
+ SEQ_FOUR_KEYS(KC_C, KC_A, KC_L, KC_C) {
+ if (current_os == OS_WIN) {
+ SEND_STRING(SS_TAP(X_CALCULATOR));
+ } else if (current_os == OS_MAC) {
+ SEND_STRING(SS_DOWN(X_LGUI) SS_TAP(X_SPACE) SS_UP(X_LGUI) "calculator" SS_TAP(X_ENTER));
+ }
+ }
+ // end OS functions
+
+ // begin format functions
+ SEQ_ONE_KEY(KC_B) {
+ surround_type(4, KC_8, true);
+ }
+ SEQ_ONE_KEY(KC_I) {
+ surround_type(2, KC_8, true);
+ }
+ SEQ_ONE_KEY(KC_U) {
+ surround_type(4, KC_MINS, true);
+ }
+ SEQ_ONE_KEY(KC_S) {
+ surround_type(4, KC_GRAVE, true);
+ }
+ SEQ_TWO_KEYS(KC_S, KC_S) {
+ if (current_os == OS_MAC) {
+ long_keystroke(3, (uint16_t[]){KC_LGUI, KC_LSFT, KC_4});
+ } else if (current_os == OS_WIN) {
+ long_keystroke(3, (uint16_t[]){KC_LGUI, KC_LSFT, KC_S});
+ } else {
+ return;
+ }
+ }
+ SEQ_ONE_KEY(KC_C) {
+ surround_type(2, KC_GRAVE, false);
+ }
+ SEQ_TWO_KEYS(KC_C, KC_C) {
+ surround_type(6, KC_GRAVE, false);
+ }
+ // end format functions
+
+ // start fancy functions
+ SEQ_THREE_KEYS(KC_C, KC_C, KC_C) {
+ surround_type(6, KC_GRAVE, false);
+ pri_mod(true);
+ tap_key(KC_V);
+ pri_mod(false);
+ tap_key(KC_RGHT);
+ tap_key(KC_RGHT);
+ tap_key(KC_RGHT);
+ tap_key(KC_ENTER);
+ }
+ // end fancy functions
+
+ // start typing functions
+ SEQ_TWO_KEYS(KC_T, KC_M) {
+ // ™
+ send_unicode_hex_string("2122");
+ }
+ SEQ_THREE_KEYS(KC_G, KC_G, KC_T) {
+ SEND_STRING("@GrahamGoldenTech.com");
+ }
+ SEQ_THREE_KEYS(KC_L, KC_O, KC_D) {
+ // ಠ__ಠ
+ send_unicode_hex_string("0CA0 005F 005F 0CA0");
+ }
+ SEQ_FOUR_KEYS(KC_R, KC_E, KC_P, KC_O) {
+ SEND_STRING("https://github.com/qmk/qmk_firmware/tree/master/users/arkag");
+ }
+ SEQ_FOUR_KEYS(KC_F, KC_L, KC_I, KC_P) {
+ // (╯‵Д′)╯彡┻━┻
+ send_unicode_hex_string("0028 256F 2035 0414 2032 0029 256F 5F61 253B 2501 253B");
+ }
+ SEQ_FIVE_KEYS(KC_U, KC_F, KC_L, KC_I, KC_P) {
+ // ┬─┬ノ( º _ º ノ)
+ send_unicode_hex_string("252C 2500 252C 30CE 0028 0020 00BA 0020 005F 0020 00BA 0020 30CE 0029");
+ }
+ SEQ_FIVE_KEYS(KC_L, KC_E, KC_N, KC_N, KC_Y) {
+ // ( ͡° ͜ʖ ͡°)
+ send_unicode_hex_string("0028 0020 0361 00B0 0020 035C 0296 0020 0361 00B0 0029");
+ }
+ SEQ_FIVE_KEYS(KC_S, KC_H, KC_R, KC_U, KC_G) {
+ // ¯\_(ツ)_/¯
+ send_unicode_hex_string("00AF 005C 005F 0028 30C4 0029 005F 002F 00AF");
+ }
+ // end typing functions
+
+ }
+}
+
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+ switch (keycode) {
+ case M_PMOD:
+ if (record->event.pressed) {
+ pri_mod(true);
+ } else {
+ pri_mod(false);
+ }
+ return false;
+
+ case M_SMOD:
+ if (record->event.pressed) {
+ sec_mod(true);
+ } else {
+ sec_mod(false);
+ }
+ return false;
+
+ case M_OS:
+ if (record->event.pressed) {
+ set_os((current_os+1) % _OS_COUNT, true);
+ }
+ return false;
+
+ default:
+ if (record->event.pressed) {
+ state = active;
+ velocikey_accelerate();
+ }
+ return true;
+ }
+}
+
+//Tap Dance Definitions
+qk_tap_dance_action_t tap_dance_actions[] = {
+ [TD_3_GRV_ACT] = ACTION_TAP_DANCE_FN (dance_3),
+ [TD_C_CED] = ACTION_TAP_DANCE_FN (dance_c),
+ [TD_GRV_3GRV] = ACTION_TAP_DANCE_FN (dance_grv),
+ [TD_SING_DOUB] = ACTION_TAP_DANCE_FN (dance_quot),
+ [TD_STRK_SHOT] = ACTION_TAP_DANCE_FN (dance_strk),
+ [TD_HYPH_UNDR] = ACTION_TAP_DANCE_DOUBLE (KC_MINS, LSFT(KC_MINS)),
+ [TD_BRCK_PARN_O] = ACTION_TAP_DANCE_DOUBLE (KC_LBRC, LSFT(KC_9)),
+ [TD_BRCK_PARN_C] = ACTION_TAP_DANCE_DOUBLE (KC_RBRC, LSFT(KC_0)),
+ [TD_LALT_RALT] = ACTION_TAP_DANCE_DOUBLE (KC_LALT, KC_RALT),
+};
diff --git a/users/arkag/arkag.h b/users/arkag/arkag.h
new file mode 100644
index 0000000000..a4672a8e82
--- /dev/null
+++ b/users/arkag/arkag.h
@@ -0,0 +1,152 @@
+#pragma once
+
+#include "quantum.h"
+#include "process_keycode/process_tap_dance.h"
+
+#define EECONFIG_USERSPACE (uint8_t *)20
+
+#define LRALT TD(TD_LALT_RALT)
+#define QUOTE TD(TD_SING_DOUB)
+#define GRAVE TD(TD_GRV_3GRV)
+#define OBRACK TD(TD_BRCK_PARN_O)
+#define CBRACK TD(TD_BRCK_PARN_C)
+#define THREE TD(TD_3_GRV_ACT)
+#define STRIKE TD(TD_STRK_SHOT)
+#define HYPHEN TD(TD_HYPH_UNDR)
+#define CEDILLA TD(TD_C_CED)
+
+#define RAISE MO(1)
+#define LOWER MO(2)
+#define KEEB MO(3)
+#define MEDIA MO(4)
+#define LAZY MO(5)
+
+#define MOD_CTL_MASK (MOD_BIT(KC_LCTL) | MOD_BIT(KC_RCTL))
+#define MOD_GUI_MASK (MOD_BIT(KC_LGUI) | MOD_BIT(KC_RGUI))
+#define MOD_SFT_MASK (MOD_BIT(KC_LSFT) | MOD_BIT(KC_RSFT))
+
+#define LED_FLASH_DELAY 150
+
+#define ACCEL_DELAY 500
+#define DEACCEL_DELAY 500
+
+#define INACTIVE_DELAY 250
+#define SLEEP_DELAY 180000
+
+enum {
+ _QWERTY = 0,
+ _RAISE,
+ _LOWER,
+ _KEEB,
+ _MEDIA,
+ _LAZY,
+};
+
+typedef enum {
+ OS_MAC, // Don't assign values
+ OS_WIN,
+ OS_NIX,
+ _OS_COUNT,
+} OS;
+
+typedef struct {
+ uint16_t h;
+ uint8_t s;
+ uint8_t v;
+} Color;
+
+typedef enum {
+ no_flash = 0,
+ flash_off,
+ flash_on,
+} flashState;
+
+typedef enum {
+ add_fade = 0,
+ sub_fade,
+} fadeState;
+
+typedef enum {
+ active = 0,
+ inactive,
+ sleeping,
+ boot,
+} activityState;
+
+enum custom_keycodes {
+ M_PMOD = SAFE_RANGE,
+ M_SMOD,
+ M_P_B,
+ M_C_A_D,
+ M_CALC,
+ M_OS,
+ M_TF,
+ M_TM,
+ M_GGT,
+ M_LOD,
+ M_LENNY,
+ M_BOLD,
+ M_ITAL,
+ M_ULIN,
+ M_SNIPT,
+ M_REPO,
+ M_SHRUG,
+ M_UF,
+};
+
+enum tapdances {
+ TD_3_GRV_ACT = 0,
+ TD_C_CED,
+ TD_GRV_3GRV,
+ TD_SLSH_HTTP,
+ TD_SING_DOUB,
+ TD_HYPH_UNDR,
+ TD_STRK_SHOT,
+ TD_SPECIAL,
+ TD_BRCK_PARN_O,
+ TD_BRCK_PARN_C,
+ TD_LALT_RALT,
+ SPC_SFT_NSFT,
+};
+
+void send_unicode_hex_string(const char *str);
+
+void velocikey_accelerate(void);
+void velocikey_decelerate(void);
+uint8_t velocikey_match_speed(uint8_t minValue, uint8_t maxValue);
+
+void set_color (Color new, bool update);
+void save_color(Color to_save);
+void reset_color(void);
+
+Color mod_color(Color current_color, bool should_add, uint8_t change_amount);
+
+void reverse_fade (void);
+
+void check_state (void);
+
+void fade_rgb (void);
+
+void flash_rgb (void);
+
+void set_os (uint8_t os, bool update);
+
+void tap_key(uint8_t keycode);
+
+void pri_mod(bool press);
+
+void sec_mod(bool press);
+
+void surround_type(uint8_t num_of_chars, uint16_t keycode, bool use_shift);
+
+void long_keystroke(size_t num_of_keys, uint16_t keys[]);
+
+void dance_grv (qk_tap_dance_state_t *state, void *user_data);
+void dance_quot (qk_tap_dance_state_t *state, void *user_data);
+void dance_strk (qk_tap_dance_state_t *state, void *user_data);
+void dance_3 (qk_tap_dance_state_t *state, void *user_data);
+void dance_c (qk_tap_dance_state_t *state, void *user_data);
+
+int cur_dance (qk_tap_dance_state_t *state);
+void spc_finished (qk_tap_dance_state_t *state, void *user_data);
+void spc_reset (qk_tap_dance_state_t *state, void *user_data);
diff --git a/users/arkag/config.h b/users/arkag/config.h
new file mode 100644
index 0000000000..2e0a9ad019
--- /dev/null
+++ b/users/arkag/config.h
@@ -0,0 +1,6 @@
+#pragma once
+
+#define TAPPING_TERM 200
+#define LEADER_TIMEOUT 250
+
+#define LEADER_PER_KEY_TIMING
diff --git a/users/arkag/mechmini2.jpg b/users/arkag/mechmini2.jpg
new file mode 100644
index 0000000000..611a0859c0
--- /dev/null
+++ b/users/arkag/mechmini2.jpg
Binary files differ
diff --git a/users/arkag/readme.md b/users/arkag/readme.md
new file mode 100644
index 0000000000..c685892f86
--- /dev/null
+++ b/users/arkag/readme.md
@@ -0,0 +1,42 @@
+# Shot on Pixel 2 XL with Cheap Lamp at Work
+
+![mmm, tasty](mechmini2.jpg)
+
+# I don't know what I'm doing
+
+Some links:
+* [Layout File: Mech Mini 2](layout_mm2)
+* [Userspace Header](arkag_h)
+* [Userspace Main](arkag_c)
+
+Here's a list of some things I have working with my currently [keyboard](mm2_home):
+
+* Reactive (sort of) fading while typing, ported from [Velocikey](https://github.com/qmk/qmk_firmware/pull/3754).
+* OS Switching, storing to EEPROM
+* OS Specific Macros and Shortcuts(WIN+SHIFT+S for Windows and CMD+SHIFT+4 for MacOS)
+* Flashing RGB LED on OS change
+* Hex Unicode Macros dependent on OS(half works on Windows due to [WinCompose](https://github.com/SamHocevar/wincompose) not functioning properly just yet).
+* "Sleep" function activates after 3 minutes (breathing).
+* Markdown style macros for surround type __eve__ ~~ryw~~ *her* **eee** (apparently only certain places support underline and strikethrough ಠ__ಠ)
+
+# License Stuff
+
+Copyright 2018 arkag arkag@pm.me
+
+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, either version 2 of the License, or
+(at your option) any later version.
+
+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/>.
+
+[arkag_c]: /users/arkag/arkag.c
+[arkag_h]: /users/arkag/arkag.h
+[layout_mm2]: /keyboards/mechmini/v2/keymaps/arkag/keymap.c
+[mm2_home]: https://cartel.ltd/projects/mechmini2/
diff --git a/users/arkag/rules.mk b/users/arkag/rules.mk
new file mode 100644
index 0000000000..3513f0ea6c
--- /dev/null
+++ b/users/arkag/rules.mk
@@ -0,0 +1 @@
+ SRC += arkag.c
diff --git a/users/bocaj/bocaj.c b/users/bocaj/bocaj.c
new file mode 100644
index 0000000000..689dbe7b4e
--- /dev/null
+++ b/users/bocaj/bocaj.c
@@ -0,0 +1,189 @@
+/*
+Copyright 2018 Jacob Jerrell <jacob.jerrell@gmail.com> @JacobJerrell
+
+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, either version 2 of the License, or
+(at your option) any later version.
+
+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 "bocaj.h"
+
+userspace_config_t userspace_config;
+#if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ #define BOCAJ_UNICODE_MODE UC_OSX
+#else
+ // set to 2 for UC_WIN, set to 4 for UC_WINC
+ #define BOCAJ_UNICODE_MODE 2
+#endif
+
+void tap(uint16_t keycode){ register_code(keycode); unregister_code(keycode); };
+
+// Add reconfigurable functions here, for keymap customization
+// This allows for a global, userspace functions, and continued
+// customization of the keymap. Use _keymap instead of _user
+// functions in the keymaps
+__attribute__ ((weak))
+void matrix_init_keymap(void) {}
+
+__attribute__ ((weak))
+void startup_keymap(void) {}
+
+__attribute__ ((weak))
+void suspend_power_down_keymap(void) {}
+
+__attribute__ ((weak))
+void suspend_wakeup_init_keymap(void) {}
+
+__attribute__ ((weak))
+void matrix_scan_keymap(void) {}
+
+__attribute__ ((weak))
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
+__attribute__ ((weak))
+void matrix_scan_secrets(void) {}
+
+__attribute__ ((weak))
+uint32_t layer_state_set_keymap (uint32_t state) {
+ return state;
+}
+
+__attribute__ ((weak))
+uint32_t default_layer_state_set_keymap (uint32_t state) {
+ return state;
+}
+
+__attribute__ ((weak))
+void led_set_keymap(uint8_t usb_led) {}
+
+// Call user matrix init, set default RGB colors and then
+// call the keymap's init function
+void matrix_init_user(void) {
+ userspace_config.raw = eeconfig_read_user();
+
+ #if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ set_unicode_input_mode(BOCAJ_UNICODE_MODE);
+ get_unicode_input_mode();
+ #endif //UNICODE_ENABLE
+
+
+ matrix_init_keymap();
+}
+
+void startup_user (void) {
+ startup_keymap();
+}
+
+void suspend_power_down_user(void)
+{
+ suspend_power_down_keymap();
+}
+
+void suspend_wakeup_init_user(void)
+{
+ suspend_wakeup_init_keymap();
+ #ifdef KEYBOARD_ergodox_ez
+ wait_ms(10);
+ #endif
+}
+
+void eeconfig_init_user(void) {
+ userspace_config.raw = 0;
+ eeconfig_update_user(userspace_config.raw);
+ #if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ set_unicode_input_mode(BOCAJ_UNICODE_MODE);
+ get_unicode_input_mode();
+ #else
+ eeprom_update_byte(EECONFIG_UNICODEMODE, BOCAJ_UNICODE_MODE);
+ #endif
+}
+
+LEADER_EXTERNS();
+// No global matrix scan code, so just run keymap's matrix
+// scan function
+void matrix_scan_user(void) {
+ static bool has_ran_yet;
+ if (!has_ran_yet) {
+ has_ran_yet = true;
+ startup_user();
+ }
+ LEADER_DICTIONARY() {
+ leading = false;
+ leader_end();
+
+ // Mac Save (Leader -> s)
+ SEQ_ONE_KEY(KC_S) {
+ SEND_STRING(SS_LGUI("s"));
+ }
+
+ // Mac copy line down (Leader -> d, d)
+ SEQ_TWO_KEYS(KC_D, KC_D) {
+ register_code(KC_LSHIFT);
+ register_code(KC_HOME);
+ unregister_code(KC_HOME);
+ unregister_code(KC_LSHIFT);
+ SEND_STRING(SS_LGUI("c"));
+ tap(KC_END);
+ tap(KC_ENTER);
+ SEND_STRING(SS_LGUI("v"));
+ }
+
+ // Mac copy line up (Leader -> u, u)
+ SEQ_TWO_KEYS(KC_U, KC_U) {
+ register_code(KC_LSHIFT);
+ register_code(KC_HOME);
+ unregister_code(KC_HOME);
+ unregister_code(KC_LSHIFT);
+ SEND_STRING(SS_LGUI("c"));
+ tap(KC_UP);
+ tap(KC_END);
+ tap(KC_ENTER);
+ SEND_STRING(SS_LGUI("v"));
+ }
+
+ // Mac VS Debug
+ SEQ_ONE_KEY(KC_D) {
+ tap(KC_F5);
+ }
+
+ // Mac VS Stop Debug
+ SEQ_TWO_KEYS(KC_S, KC_D) {
+ register_code(KC_LSHIFT);
+ tap(KC_F5);
+ unregister_code(KC_LSHIFT);
+ }
+
+ // Start Diablo 3
+ SEQ_ONE_KEY(KC_3) {
+ SEND_STRING(SS_LCTRL(" "));
+ SEND_STRING("Diablo");
+ tap(KC_ENTER);
+ }
+
+ SEQ_ONE_KEY(KC_B) {
+ SEND_STRING (QMK_KEYBOARD "/" QMK_KEYMAP " @ " QMK_VERSION " ");
+ tap(KC_ENTER);
+ SEND_STRING ("Built at: " QMK_BUILDDATE);
+ }
+#ifndef NO_SECRETS
+ matrix_scan_secrets();
+#endif // !NO_SECRETS
+ }
+
+#ifdef TAP_DANCE_ENABLE // Run Diablo 3 macro checking code.
+ run_diablo_macro_check();
+#endif // TAP_DANCE_ENABLE
+
+ matrix_scan_keymap();
+}
diff --git a/users/bocaj/bocaj.h b/users/bocaj/bocaj.h
new file mode 100644
index 0000000000..04991a0150
--- /dev/null
+++ b/users/bocaj/bocaj.h
@@ -0,0 +1,85 @@
+/*
+Copyright 2018 Jacob Jerrell <jacob.jerrell@gmail.com> @JacobJerrell
+
+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, either version 2 of the License, or
+(at your option) any later version.
+
+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/>.
+*/
+
+#pragma once
+#include "quantum.h"
+#include "version.h"
+#include "eeprom.h"
+#include "wrappers.h"
+#include "process_records.h"
+#ifdef TAP_DANCE_ENABLE
+ #include "tap_dances.h"
+#endif // TAP_DANCE_ENABLE
+
+/* Layer Names */
+enum userspace_layers {
+ _WORKMAN = 0,
+ _WINWORKMAN,
+ _QWERTY,
+ _LOWER,
+ _ADJUST,
+ _DIABLO,
+};
+
+#if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ #define BOCAJ_UNICODE_MODE UC_OSX
+#else
+ // set to 2 for UC_WIN, set to 4 for UC_WINC
+ #define BOCAJ_UNICODE_MODE 2
+#endif
+
+/*
+define modifiers here, since MOD_* doesn't seem to work for these
+ */
+#define MODS_SHIFT_MASK (MOD_BIT(KC_LSHIFT)|MOD_BIT(KC_RSHIFT))
+#define MODS_CTRL_MASK (MOD_BIT(KC_LCTL)|MOD_BIT(KC_RCTRL))
+#define MODS_ALT_MASK (MOD_BIT(KC_LALT)|MOD_BIT(KC_RALT))
+#define MODS_GUI_MASK (MOD_BIT(KC_LGUI)|MOD_BIT(KC_RGUI))
+
+bool mod_key_press_timer (uint16_t code, uint16_t mod_code, bool pressed);
+bool mod_key_press (uint16_t code, uint16_t mod_code, bool pressed, uint16_t this_timer);
+bool send_game_macro(const char *str, keyrecord_t *record, bool override);
+void matrix_init_keymap(void);
+void shutdown_keymap(void);
+void suspend_power_down_keymap(void);
+void suspend_wakeup_init_keymap(void);
+void matrix_scan_keymap(void);
+uint32_t layer_state_set_keymap (uint32_t state);
+uint32_t default_layer_state_set_keymap (uint32_t state);
+void led_set_keymap(uint8_t usb_led);
+void eeconfig_init_keymap(void);
+void tap(uint16_t keycode);
+
+typedef union {
+ uint8_t raw;
+} userspace_config_t;
+
+extern userspace_config_t userspace_config;
+
+// If Tap Dancing is enabled, we manage that here.
+// If it is not, then we define the KC_D3_# codes gracefully
+#ifdef TAP_DANCE_ENABLE
+ #define KC_D3_1 TD(TD_D3_1)
+ #define KC_D3_2 TD(TD_D3_2)
+ #define KC_D3_3 TD(TD_D3_3)
+ #define KC_D3_4 TD(TD_D3_4)
+#else // !TAP_DANCE_ENABLE
+ #define KC_D3_1 KC_1
+ #define KC_D3_2 KC_2
+ #define KC_D3_3 KC_3
+ #define KC_D3_4 KC_4
+#endif // TAP_DANCE_ENABLE
diff --git a/users/bocaj/config.h b/users/bocaj/config.h
new file mode 100644
index 0000000000..1956ea6d96
--- /dev/null
+++ b/users/bocaj/config.h
@@ -0,0 +1,33 @@
+#pragma once
+
+#ifndef QMK_KEYS_PER_SCAN
+ #define QMK_KEYS_PER_SCAN 4
+#endif // QMK KEYS PER SCAN
+
+// this makes it possible to do rolling combos (zx) with keys that
+// convert to other keys on hold (z becomes ctrl when you hold it,
+// and when this option isn't enabled, z rapidly followed by x
+// actually sends Ctrl-x. That's bad.)
+#define IGNORE_MOD_TAP_INTERRUPT
+#undef PERMISSIVE_HOLD
+#define PREVENT_STUCK_MODIFIERS
+
+#ifdef TAPPING_TERM
+#undef TAPPING_TERM
+#endif // TAPPING_TERM
+#define TAPPING_TERM 175
+
+#define RETRO_TAPPING
+
+// Disable action_get_macro and fn_actions, since we don't use these
+// and it saves on space in the firmware.
+#ifndef NO_DEBUG
+#define NO_DEBUG
+#endif // !NO_DEBUG
+#if !defined(NO_PRINT) && !defined(CONSOLE_ENABLE)
+#define NO_PRINT
+#endif // !NO_PRINT
+#define NO_ACTION_MACRO
+#define NO_ACTION_FUNCTION
+
+#define MACRO_TIMER 5
diff --git a/users/bocaj/process_records.c b/users/bocaj/process_records.c
new file mode 100644
index 0000000000..c36683f8ba
--- /dev/null
+++ b/users/bocaj/process_records.c
@@ -0,0 +1,149 @@
+#include "bocaj.h"
+#include QMK_KEYBOARD_H
+
+uint16_t copy_paste_timer;
+uint16_t grave_layer_timer;
+uint16_t heal_layer_timer;
+
+__attribute__ ((weak))
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
+// Defines actions tor my global custom keycodes. Defined in bocaj.h file
+// Then runs the _keymap's record handler if not processed here
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+ switch (keycode) {
+ case KC_MWRK:
+ if (!record->event.pressed) {
+ set_single_persistent_default_layer(_WORKMAN);
+ #if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ set_unicode_input_mode(0);
+ #endif
+ layer_move(0);
+ ergodox_blink_all_leds();
+ }
+ break;
+ case KC_WWRK:
+ if (!record->event.pressed) {
+ set_single_persistent_default_layer(_WINWORKMAN);
+ #if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ set_unicode_input_mode(4);
+ #endif
+ layer_move(0);
+ ergodox_blink_all_leds();
+ }
+ break;
+ case KC_MQWR:
+ if (!record->event.pressed) {
+ set_single_persistent_default_layer(_QWERTY);
+ #if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ set_unicode_input_mode(0);
+ #endif
+ layer_move(0);
+ ergodox_blink_all_leds();
+ }
+ break;
+ case MC_LOCK:
+ if (!record->event.pressed) {
+ layer_move(0);
+ SEND_STRING(SS_LCTRL(SS_LGUI("q")));
+ }
+ break;
+ case KC_MAKE: // Compiles the firmware, and adds the flash command based on keyboard bootloader
+ if (!record->event.pressed) {
+ uint8_t temp_mod = get_mods();
+ uint8_t temp_osm = get_oneshot_mods();
+ clear_mods();
+ clear_oneshot_mods();
+ if (biton32(default_layer_state) == _WINWORKMAN) {
+ send_string_with_delay_P(PSTR("make " QMK_KEYBOARD ":" QMK_KEYMAP), 10);
+ } else {
+ send_string_with_delay_P(PSTR("util/docker_build.sh " QMK_KEYBOARD ":" QMK_KEYMAP), 10);
+ }
+ if (temp_mod & MODS_SHIFT_MASK) {
+ send_string_with_delay_P(PSTR(":teensy"), 10);
+ }
+ if (temp_mod & MODS_CTRL_MASK) {
+ send_string_with_delay_P(PSTR(" -j8 --output-sync"), 10);
+ }
+ send_string_with_delay_P(PSTR(SS_TAP(X_ENTER)), 10);
+ set_mods(temp_mod);
+ layer_move(0);
+ }
+ break;
+ case KC_DCLR: // reset all Diablo timers, disabling them
+#ifdef TAP_DANCE_ENABLE
+ if (record->event.pressed) {
+ uint8_t dtime;
+ for (dtime = 0; dtime < 4; dtime++) {
+ diablo_key_time[dtime] = diablo_times[0];
+ }
+ }
+#endif // TAP_DANCE_ENABLE
+ break;
+ case JJ_ARRW:
+ if (!record->event.pressed) {
+ SEND_STRING("->");
+ }
+ return false;
+ break;
+ case LM_GRAVE:
+ if (record->event.pressed) {
+ grave_layer_timer = timer_read();
+ } else {
+ if (timer_elapsed(grave_layer_timer) < TAPPING_TERM) {
+ uint8_t temp_mod = get_mods();
+ uint8_t one_shot = get_oneshot_mods();
+ clear_mods();
+ if (temp_mod & MODS_SHIFT_MASK || one_shot & MODS_SHIFT_MASK) {
+ register_code(KC_LSFT);
+ tap(KC_GRAVE);
+ unregister_code(KC_LSFT);
+ } else {
+ tap(KC_GRAVE);
+ }
+ set_mods(temp_mod);
+ } else {
+ layer_move(0);
+ }
+ }
+ return false;
+ break;
+ case KC_CCCV:
+ if (record->event.pressed) {
+ copy_paste_timer = timer_read();
+ } else {
+ if (timer_elapsed(copy_paste_timer) > TAPPING_TERM) { // Hold, copy
+ SEND_STRING(SS_LGUI("c"));
+ } else {
+ SEND_STRING(SS_LGUI("v"));
+ }
+ }
+ return false;
+ break;
+#ifdef UNICODE_ENABLE
+ case UC_FLIP: // (ノಠ痊ಠ)ノ彡┻━┻
+ if (record->event.pressed) {
+ send_unicode_hex_string("0028 30CE 0CA0 75CA 0CA0 0029 30CE 5F61 253B 2501 253B");
+ }
+ break;
+ case UC_TABL: // ┬─┬ノ( º _ ºノ)
+ if (record->event.pressed) {
+ send_unicode_hex_string("252C 2500 252C 30CE 0028 0020 00BA 0020 005F 0020 00BA 30CE 0029");
+ }
+ break;
+ case UC_SHRG: // ¯\_(ツ)_/¯
+ if (record->event.pressed) {
+ send_unicode_hex_string("00AF 005C 005F 0028 30C4 0029 005F 002F 00AF");
+ }
+ break;
+ case UC_DISA: // ಠ_ಠ
+ if (record->event.pressed) {
+ send_unicode_hex_string("0CA0 005F 0CA0");
+ }
+ break;
+#endif
+ }
+ return process_record_keymap(keycode, record);
+}
diff --git a/users/bocaj/process_records.h b/users/bocaj/process_records.h
new file mode 100644
index 0000000000..248df13e1b
--- /dev/null
+++ b/users/bocaj/process_records.h
@@ -0,0 +1,52 @@
+#pragma once
+#include "bocaj.h"
+
+#if defined(KEYMAP_SAFE_RANGE)
+ #define PLACEHOLDER_SAFE_RANGE KEYMAP_SAFE_RANGE
+#else
+ #define PLACEHOLDER_SAFE_RANGE SAFE_RANGE
+#endif
+
+enum userspace_custom_keycodes {
+ KC_EPRM = PLACEHOLDER_SAFE_RANGE, // can always be here
+ KC_MWRK,
+ KC_WWRK,
+ KC_MQWR,
+ KC_VRSN,
+ LM_GRAVE, // Shift if held, layer change if tapped
+ JJ_COPY,
+ JJ_PSTE,
+ JJ_ARRW,
+ KC_CCCV,
+ MC_LOCK,
+ KC_DCLR,
+ KC_MAKE,
+ UC_FLIP, // (ಠ痊ಠ)┻━┻
+ UC_TABL, // ┬─┬ノ( º _ ºノ)
+ UC_SHRG, // ¯\_(ツ)_/¯
+ UC_DISA, // ಠ_ಠ
+ NEW_SAFE_RANGE //use "NEWPLACEHOLDER for keymap specific codes
+};
+
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record);
+
+// One Shot
+#define OS_LSFT OSM(MOD_LSFT)
+
+// Space Cadet Hyper/Meh and [/]
+#define HYP_LBK ALL_T(KC_LBRACKET)
+#define MEH_RBK MEH_T(KC_RBRACKET)
+
+#define GUI_CTR(os, kc) MT( (os == 0) ? (MOD_LGUI) : (MOD_LCTL), kc )
+
+// Layout beauti-/simpli-fication
+#define KC_LWEN LT(_LOWER, KC_ENTER)
+#define KC_ADJS TT(_ADJUST)
+#define KC_NUMS TT(_LOWER)
+#define KC_GAME TT(_DIABLO)
+#define XXXXXXX KC_NO
+#define _______ KC_TRNS
+
+// Other Keycodes
+#define KC_RST RESET
+#define KC_BS KC_BSLASH
diff --git a/users/bocaj/readme.md b/users/bocaj/readme.md
new file mode 100644
index 0000000000..669299cb0d
--- /dev/null
+++ b/users/bocaj/readme.md
@@ -0,0 +1,102 @@
+# Overview
+
+My personal QMK userspace. First, I must say that the credit for a majority of the code found here belongs to Drashna and/or the people he derived his code from. My Ergodox layout is briefly described in its respective folder. As for explaining this userspace, you could honestly go to Drashna's userspace and read his well put together readme. Regardless, I am mostly writing this as an excercise for myself to better understand what is going on, and where applicable, describe things that I innovated on my own.
+
+## Bocaj.c
+
+### Unicode
+
+I've always had difficulty implementing unicode in QMK, all of this code is literally copy/pasted from Drashna's userspace and lies dormant here until I can take the time to figure it out.
+
+Update: Got it to work in Mac OS which is more important to me than Windows (probably pretty easy to figure out at this point). So I'm a happy table flipping person now!
+
+(ノಠ痊ಠ)ノ彡┻━┻
+
+┬─┬ノ( º _ ºノ)
+
+### Tap Macro
+
+Not sure why this doesn't exist in QMK already (maybe it does?)
+
+```c
+void tap(uint16_t keycode){ register_code(keycode); unregister_code(keycode); };
+```
+
+### *_keymap functions
+
+We're running *_user functions in the userspace, that way we can add to or reconfigure at the keyboard level. Any *_user functions should call the equivalent *_keymap function at the end. If the *_keymap function isn't defined in the keymap, the `__attribute__ ((weak))` will prevent build problems.
+
+### Startup/Suspend/Shutdown Functions
+
+I have no idea what these do. Non-Ergodox keyboard functions?
+
+### Matrix Scan User
+
+Leader key defines, Diablo macro ancillary function, run matrix_scan_keymap.
+
+#### Leader Key
+
+I've always been interested in this feature, but I've had 0 experience with applications that have similar behavior. My implementation seeks to implement features that I feel VS2017 lacks
+
+## Secrets
+
+Hacked Drashna's secret macro implementation to work with the leader key instead.
+TODO: Finish documentation
+
+## Bocaj.h
+
+Layer defines, some macro ancillary defines, setup Diablo macros and failsafe
+
+## Process_Records.c/.h
+
+Again, taking ideas from Drashna to make maintenance simpler. A couple of things that I'm proud of here, but nothing really ground breaking.
+
+* Features
+ * Change default layer
+ * KC_MWRK, KC_WWRK, KC_MQWR
+ * MacOS Lock Screen Macro
+ * Make macro (Credit: Drashna)
+ * Need to reconfigure so it runs the docker command if one of the Mac OS layers are default because the AVR install fails on the corporate laptop
+ * Arrow macro (->) because I find myself telling people how to get to something quite frequently and typing this manually requires moving the right hand to the top-left of the ergodox and then to the bottom right, which feels unnatural.
+ * LM_GRAVE
+ * While combining _NUMS and _LOWER, I also needed a place to put F1-12 keys. This required me to relocate the grave key. The most comfortable place to put it was over a key that I frequently use to toggle the numpad. I do have other ways to get to/from this layer but my mind has been wired to use them for different workflows, so I would sit here frozen for a moment trying to tell my fingers where to go
+ * How it works
+ * A timer starts when pressed down
+ * If the timer at release was less than the TAPPING_TERM define
+ * Get mods
+ * If Shift was held or one-shot shift was active
+ * Send `~`
+ * Else
+ * Send `
+ * Else (timer at released was greater than the TAPPING_TERM define)
+ * Move to the default layer
+ * KC_CCCV
+ * Another neat idea I found in Drashna's userspace... highly underutilized in my layout but the inspiration for LM_GRAVE was obviously derived from this code
+ * Unicode stuff
+ * All I've ever wanted was a table-flip macro... I managed to get about half of it to work before I gave up and disabled it
+
+## Send_Unicode.c/.h
+
+I have some basic understanding of this, Drashna may already have it documented in his userspace. I'll put it in my own words when I get around to making it work and understanding it better.
+
+## Tap_Dances.c/h
+
+Again, building on Drashna's userspace organization to simplify maintenance of a heavily configured layout. This is all the stuff for the Diablo 3 macros that spam a given skill (1-4) every ~1 second
+
+## Wrappers.h
+
+Traditionally, you would put all of this into the \<username>.h file. But I liked the idea of separating it to simplify modification in the future.
+
+### GUI_CTR(os, kc)
+
+A notable mention in this file is the GUI_CTR(os, kc) custom keycode defined in process_records.h as:
+
+```c
+#define GUI_CTR(os, kc) MT( (os == 0) ? (MOD_LGUI) : (MOD_LCTL), kc )
+```
+
+I tried several things before coming to this one-liner conclusion. I believe it is quite elegant and it definitely solves the problem I had (separate wrappers for Windows/MacOS layers). But I would love to make this into something more intuitive, like a macro that detects which layer you're on and sends the applicable hotkey when held, or keycode when tapped. Ultimately, I was too tired of thinking about it to come up with a solution like that at this time.
+
+Anyhow, if you set `os == 1`, it sends the Windows CTRL hotkey when held. If you set `os == 0`, it sends the Mac OS GUI hotkey when held. If tapped, it sends the keycode.
+
+This is effectively a slightly more advanced `MOD_T(kc)` keycode.
diff --git a/users/bocaj/rules.mk b/users/bocaj/rules.mk
new file mode 100644
index 0000000000..9ed8c250a3
--- /dev/null
+++ b/users/bocaj/rules.mk
@@ -0,0 +1,33 @@
+SRC += bocaj.c \
+ process_records.c
+
+ifneq ("$(wildcard $(USER_PATH)/secrets.c)","")
+ SRC += secrets.c
+endif
+
+ifeq ($(strip $(TAP_DANCE_ENABLE)), yes)
+ SRC += tap_dances.c
+endif
+
+# Caused problems when building via docker on Mac OS
+# EXTRAFLAGS += -flto
+
+ifeq ($(strip $(NO_SECRETS)), yes)
+ OPT_DEFS += -DNO_SECRETS
+endif
+
+ifeq ($(strip $(MACROS_ENABLED)), yes)
+ OPT_DEFS += -DMACROS_ENABLED
+endif
+
+ifeq ($(strip $(UCIS_ENABLE)), yes)
+ SRC += send_unicode.c
+endif
+
+ifeq ($(strip $(UNICODEMAP_ENABLE)), yes)
+ SRC += send_unicode.c
+endif
+
+ifeq ($(strip $(UNICODE_ENABLE)), yes)
+ SRC += send_unicode.c
+endif
diff --git a/users/bocaj/send_unicode.c b/users/bocaj/send_unicode.c
new file mode 100644
index 0000000000..b1290f6319
--- /dev/null
+++ b/users/bocaj/send_unicode.c
@@ -0,0 +1,106 @@
+// Written by konstantin: vomindoraan
+#include "send_unicode.h"
+#include <ctype.h>
+#include <string.h>
+
+__attribute__((weak))
+void send_unicode_hex_string(const char* str) {
+ if (!str) { return; } // Safety net
+
+ while (*str) {
+ // Find the next code point (token) in the string
+ for (; *str == ' '; str++);
+ size_t n = strcspn(str, " "); // Length of the current token
+ char code_point[n+1];
+ strncpy(code_point, str, n);
+ code_point[n] = '\0'; // Make sure it's null-terminated
+
+ // Normalize the code point: make all hex digits lowercase
+ for (char *p = code_point; *p; p++) {
+ *p = tolower((unsigned char)*p);
+ }
+
+ // Send the code point as a Unicode input string
+ unicode_input_start();
+ send_string(code_point);
+ unicode_input_finish();
+
+ str += n; // Move to the first ' ' (or '\0') after the current token
+ }
+}
+
+// (ノಠ痊ಠ)ノ彡┻━┻
+// send_unicode_hex_string("0028 30CE 0CA0 75CA 0CA0 0029 30CE 5F61 253B 2501 253B");
+
+//Old code
+// (╯°□°)╯ ︵ ┻━┻
+ #if 0
+ register_code(KC_RSFT);
+ tap(KC_9);
+ unregister_code(KC_RSFT);
+ process_unicode((0x256F | QK_UNICODE), record); // Arm
+ process_unicode((0x00B0 | QK_UNICODE), record); // Eye
+ process_unicode((0x25A1 | QK_UNICODE), record); // Mouth
+ process_unicode((0x00B0 | QK_UNICODE), record); // Eye
+ register_code(KC_RSFT);
+ tap(KC_0);
+ unregister_code(KC_RSFT);
+ process_unicode((0x256F | QK_UNICODE), record); // Arm
+ tap(KC_SPC);
+ process_unicode((0x0361 | QK_UNICODE), record); // Flippy
+ tap(KC_SPC);
+ process_unicode((0x253B | QK_UNICODE), record); // Table
+ process_unicode((0x2501 | QK_UNICODE), record); // Table
+ process_unicode((0x253B | QK_UNICODE), record); // Table
+ #endif
+
+
+// If you need a good converter: https://r12a.github.io/app-conversion/
+uint8_t saved_mods;
+
+void unicode_input_start (void) {
+ // save current mods
+ saved_mods = get_mods(); // Save current mods
+ clear_mods(); // Unregister mods to start from a clean state
+
+ switch(get_unicode_input_mode()) {
+ case UC_OSX:
+ register_code(KC_LALT);
+ break;
+ case UC_LNX:
+ register_code(KC_LCTL);
+ register_code(KC_LSFT);
+ register_code(KC_U);
+ unregister_code(KC_U);
+ unregister_code(KC_LSFT);
+ unregister_code(KC_LCTL);
+ break;
+ case UC_WIN:
+ register_code(KC_LALT);
+ register_code(KC_PPLS);
+ unregister_code(KC_PPLS);
+ break;
+ case UC_WINC:
+ register_code(KC_RALT);
+ unregister_code(KC_RALT);
+ register_code(KC_U);
+ unregister_code(KC_U);
+ break;
+ }
+ wait_ms(UNICODE_TYPE_DELAY);
+}
+
+void unicode_input_finish (void) {
+ switch(get_unicode_input_mode()) {
+ case UC_OSX:
+ case UC_WIN:
+ unregister_code(KC_LALT);
+ break;
+ case UC_LNX:
+ register_code(KC_SPC);
+ unregister_code(KC_SPC);
+ break;
+ }
+
+ set_mods(saved_mods); // Reregister previously set mods
+}
diff --git a/users/drashna/drashna_unicode.h b/users/bocaj/send_unicode.h
index 3d1bc03f9b..818b6e571b 100644
--- a/users/drashna/drashna_unicode.h
+++ b/users/bocaj/send_unicode.h
@@ -1,10 +1,11 @@
-#ifndef UNICODE_USERSPACE_H
-#define UNICODE_USERSPACE_H
+#pragma once
+#include "quantum.h"
+void send_unicode_hex_string(const char* str);
/* use X(n) to call the */
-
+#ifdef UNICODEMAP_ENABLE
enum unicode_name {
THINK, // thinking face 🤔
GRIN, // grinning face 😊
@@ -67,5 +68,4 @@ const uint32_t PROGMEM unicode_map[] = {
[IRONY] = 0x02E2E,
[DEGREE] = 0x000B0
};
-
- #endif
+#endif // UNICODEMAP_ENABLE
diff --git a/users/bocaj/tap_dances.c b/users/bocaj/tap_dances.c
new file mode 100644
index 0000000000..a9628a345d
--- /dev/null
+++ b/users/bocaj/tap_dances.c
@@ -0,0 +1,64 @@
+#include "tap_dances.h"
+
+
+//define diablo macro timer variables
+uint16_t diablo_timer[4];
+uint8_t diablo_times[] = { 0, 1, 3, 5, 10, 30 };
+uint8_t diablo_key_time[4];
+
+// has the correct number of seconds elapsed (as defined by diablo_times)
+bool check_dtimer(uint8_t dtimer) { return (timer_elapsed(diablo_timer[dtimer]) < (diablo_key_time[dtimer] * 1000)) ? false : true; };
+
+// Cycle through the times for the macro, starting at 0, for disabled.
+// Max of six values, so don't exceed
+void diablo_tapdance_master(qk_tap_dance_state_t *state, void *user_data, uint8_t diablo_key) {
+ if (state->count >= 7) {
+ diablo_key_time[diablo_key] = diablo_times[0];
+ reset_tap_dance(state);
+ } else {
+ diablo_key_time[diablo_key] = diablo_times[state->count - 1];
+ }
+}
+
+// Would rather have one function for all of this, but no idea how to do that...
+void diablo_tapdance1(qk_tap_dance_state_t *state, void *user_data) { diablo_tapdance_master(state, user_data, 0); }
+void diablo_tapdance2(qk_tap_dance_state_t *state, void *user_data) { diablo_tapdance_master(state, user_data, 1); }
+void diablo_tapdance3(qk_tap_dance_state_t *state, void *user_data) { diablo_tapdance_master(state, user_data, 2); }
+void diablo_tapdance4(qk_tap_dance_state_t *state, void *user_data) { diablo_tapdance_master(state, user_data, 3); }
+
+//Tap Dance Definitions
+qk_tap_dance_action_t tap_dance_actions[] = {
+ // tap once to disable, and more to enable timed micros
+ [TD_D3_1] = ACTION_TAP_DANCE_FN(diablo_tapdance1),
+ [TD_D3_2] = ACTION_TAP_DANCE_FN(diablo_tapdance2),
+ [TD_D3_3] = ACTION_TAP_DANCE_FN(diablo_tapdance3),
+ [TD_D3_4] = ACTION_TAP_DANCE_FN(diablo_tapdance4),
+};
+
+// Sends the key press to system, but only if on the Diablo layer
+void send_diablo_keystroke(uint8_t diablo_key) {
+ if (biton32(layer_state) == _DIABLO) {
+ switch (diablo_key) {
+ case 0:
+ tap(KC_1); break;
+ case 1:
+ tap(KC_2); break;
+ case 2:
+ tap(KC_3); break;
+ case 3:
+ tap(KC_4); break;
+ }
+ }
+}
+
+// Checks each of the 4 timers/keys to see if enough time has elapsed
+// Runs the "send string" command if enough time has passed, and resets the timer.
+void run_diablo_macro_check(void) {
+ uint8_t dtime;
+ for (dtime = 0; dtime < 4; dtime++) {
+ if (check_dtimer(dtime) && diablo_key_time[dtime]) {
+ diablo_timer[dtime] = timer_read();
+ send_diablo_keystroke(dtime);
+ }
+ }
+}
diff --git a/users/bocaj/tap_dances.h b/users/bocaj/tap_dances.h
new file mode 100644
index 0000000000..5b1277ec58
--- /dev/null
+++ b/users/bocaj/tap_dances.h
@@ -0,0 +1,19 @@
+#pragma once
+#include "bocaj.h"
+
+//define diablo macro timer variables
+extern uint16_t diablo_timer[4];
+extern uint8_t diablo_times[];
+extern uint8_t diablo_key_time[4];
+
+
+void run_diablo_macro_check(void);
+
+#ifdef TAP_DANCE_ENABLE
+enum {
+ TD_D3_1 = 0,
+ TD_D3_2,
+ TD_D3_3,
+ TD_D3_4
+};
+#endif // TAP_DANCE_ENABLE
diff --git a/users/bocaj/wrappers.h b/users/bocaj/wrappers.h
new file mode 100644
index 0000000000..379edaad29
--- /dev/null
+++ b/users/bocaj/wrappers.h
@@ -0,0 +1,37 @@
+#pragma once
+#include "bocaj.h"
+
+#if (!defined(LAYOUT) && defined(KEYMAP))
+#define LAYOUT KEYMAP
+#endif
+
+#define LAYOUT_ergodox_wrapper(...) LAYOUT_ergodox(__VA_ARGS__)
+#define LAYOUT_ergodox_pretty_wrapper(...) LAYOUT_ergodox_pretty(__VA_ARGS__)
+
+#define _________________QWERTY_L1__________________ KC_Q, KC_W, KC_E, KC_R, KC_T
+#define _________________QWERTY_L2__________________ KC_A, KC_S, GUI_CTR(0, KC_D), KC_F, KC_G
+#define _________________QWERTY_L3__________________ KC_Z, KC_X, KC_C, KC_V, KC_B
+
+#define _________________QWERTY_R1__________________ KC_Y, KC_U, KC_I, KC_O, KC_P
+#define _________________QWERTY_R2__________________ KC_H, KC_J, GUI_CTR(0, KC_K), KC_L, KC_SCLN
+#define _________________QWERTY_R3__________________ KC_N, KC_M, KC_COMM, KC_DOT, KC_SLASH
+
+// Hardware Driven Workman
+#define _________________WORKMAN_L1_________________ KC_Q, KC_D, KC_R, KC_W, KC_B
+#define _________________WORKMAN_L2_________________ KC_A, KC_S, GUI_CTR(0, KC_H), KC_T, KC_G // GUI_CTR(0, kc) behaves as GUI_T(kc)
+#define ________________WWORKMAN_L2_________________ KC_A, KC_S, GUI_CTR(1, KC_H), KC_T, KC_G // GUI_CTR(1, kc) behaves as CTR_T(kc)
+#define _________________WORKMAN_L3_________________ KC_Z, KC_X, KC_M, KC_C, KC_V
+
+#define _________________WORKMAN_R1_________________ KC_J, KC_F, KC_U, KC_P, KC_SCLN
+#define _________________WORKMAN_R2_________________ KC_Y, KC_N, GUI_CTR(0, KC_E), KC_O, KC_I // GUI_CTR(0, kc) behaves as GUI_T(kc)
+#define ________________WWORKMAN_R2_________________ KC_Y, KC_N, GUI_CTR(1, KC_E), KC_O, KC_I // GUI_CTR(1, kc) behaves as CTR_T(kc)
+#define _________________WORKMAN_R3_________________ KC_K, KC_L, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define __________________NUMBER_LEFT_______________ KC_1, KC_2, KC_3, KC_4, KC_5
+#define __________________NUMBER_RIGHT______________ KC_6, KC_7, KC_8, KC_9, KC_0
+
+#define __________________FUNCTION_LEFT_____________ KC_F1, KC_F2, KC_F3, KC_F4, KC_F5
+#define __________________FUNCTION_RIGHT____________ KC_F6, KC_F7, KC_F8, KC_F9, KC_F10
+
+#define ____________________BLANK___________________ KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS
diff --git a/users/doogle999/doogle999.c b/users/doogle999/doogle999.c
new file mode 100644
index 0000000000..320de7cff8
--- /dev/null
+++ b/users/doogle999/doogle999.c
@@ -0,0 +1,460 @@
+#include "doogle999.h"
+
+static unsigned char inputLocation = 0; // Current index in text input
+
+static double calc(const char input[CALC_BUFFER_SIZE +1]) // Finds value of input char array, relatively small and fast I think
+{
+ char inputToken[CALC_BUFFER_SIZE + 1]; // Input buffer, used when a single token (generally a number) takes up more
+ unsigned char inputTokenLocation = 0, inputLocation = 0; // Keep track of indices
+
+ struct Token tokens[CALC_BUFFER_SIZE + 1]; // Input, converted to tokens, one extra large to accomodate for possible negative sign then open parenthesis as first character
+ unsigned char tokenCount = 0; // Keep track of index
+
+ bool dashAsMinus = false; // Kind of a hacky solution to determining whether to treat a dash as a minus sign or a negative sign
+
+ while(inputLocation < CALC_BUFFER_SIZE + 1)
+ {
+ char digit = input[inputLocation];
+
+ if(inputLocation == 0 && input[inputLocation] == CALC_CHAR_SUB && input[inputLocation + 1] == CALC_CHAR_BEG)
+ {
+ tokens[tokenCount].raw.num = 0;
+ tokens[tokenCount].isNum = true;
+
+ tokenCount++;
+ dashAsMinus = true;
+ }
+
+ if ((digit >= '0' && digit <= '9') || /* valid digit */
+ (inputTokenLocation != 0 && input[inputLocation] == CALC_CHAR_DEC) || /* valid floating point */
+ (!dashAsMinus && inputTokenLocation == 0 && input[inputLocation] == CALC_CHAR_SUB)) /* - is negative sign */
+ {
+ inputToken[inputTokenLocation] = input[inputLocation];
+ inputTokenLocation++;
+ inputLocation++;
+ continue;
+ }
+
+ if(inputTokenLocation != 0)
+ {
+ // sscanf(inputToken, "%lf", &tokens[tokenCount].raw.num); // I would like to use sscanf here, but the small version of stdio.h on the chip doesn't allow sscanf or its sister functions to be used to process floats
+ tokens[tokenCount].raw.num = atof(inputToken);
+ tokens[tokenCount].isNum = true;
+ for(unsigned char i = 0; i < inputTokenLocation + 1; i++)
+ {
+ inputToken[i] = '\0';
+ }
+ inputTokenLocation = 0;
+ tokenCount++;
+ dashAsMinus = true;
+ continue;
+ }
+
+ /* inputTokenLocation == 0 */
+ tokens[tokenCount].isNum = false;
+ tokens[tokenCount].raw.op.c = input[inputLocation];
+ tokens[tokenCount].raw.op.priority = 0;
+ tokens[tokenCount].raw.op.ltr = true;
+ dashAsMinus = false;
+
+ switch(input[inputLocation])
+ {
+ case CALC_CHAR_BEG:
+ break;
+ case CALC_CHAR_END:
+ dashAsMinus = true;
+ break;
+ case CALC_CHAR_ADD:
+ tokens[tokenCount].raw.op.priority = CALC_PRIO_ADD;
+ break;
+ case CALC_CHAR_SUB:
+ tokens[tokenCount].raw.op.priority = CALC_PRIO_SUB;
+ break;
+ case CALC_CHAR_MUL:
+ tokens[tokenCount].raw.op.priority = CALC_PRIO_MUL;
+ break;
+ case CALC_CHAR_DIV:
+ tokens[tokenCount].raw.op.priority = CALC_PRIO_DIV;
+ break;
+ case CALC_CHAR_EXP:
+ tokens[tokenCount].raw.op.priority = CALC_PRIO_EXP;
+ tokens[tokenCount].raw.op.ltr = false;
+ break;
+ case CALC_CHAR_SIN:
+ case CALC_CHAR_COS:
+ case CALC_CHAR_TAN:
+ case CALC_CHAR_ASN:
+ case CALC_CHAR_ACS:
+ case CALC_CHAR_ATN:
+ case CALC_CHAR_LGE:
+ case CALC_CHAR_LOG:
+ case CALC_CHAR_SQT:
+ break;
+ case CALC_CHAR_EUL:
+ tokens[tokenCount].isNum = true;
+ tokens[tokenCount].raw.num = CALC_VALU_EUL;
+ dashAsMinus = true;
+ break;
+ case CALC_CHAR_PI:
+ tokens[tokenCount].isNum = true;
+ tokens[tokenCount].raw.num = CALC_VALU_PI;
+ dashAsMinus = true;
+ break;
+ case '\0':
+ tokenCount--;
+ inputLocation = CALC_BUFFER_SIZE;
+ break;
+ default:
+ tokenCount--;
+ break;
+ }
+ tokenCount++;
+ inputLocation++;
+ }
+
+ struct Token output[CALC_BUFFER_SIZE + 1]; // Final output tokens before evaluation
+ struct Token opstack[CALC_BUFFER_SIZE + 1]; // Stack of operators
+ unsigned char outputLocation = 0, opstackLocation = 0; // Keep track of indices
+
+ unsigned char numBrackets = 0; // The number of parenthesis
+
+ for(unsigned char i = 0; i < tokenCount; i++)
+ {
+ if(tokens[i].isNum)
+ {
+ output[outputLocation] = tokens[i];
+ outputLocation++;
+ }
+ else if(tokens[i].raw.op.c == CALC_CHAR_BEG)
+ {
+ opstack[opstackLocation] = tokens[i];
+ opstackLocation++;
+ }
+ else if(tokens[i].raw.op.c == CALC_CHAR_END)
+ {
+ while(opstack[opstackLocation - 1].raw.op.c != CALC_CHAR_BEG)
+ {
+ output[outputLocation] = opstack[opstackLocation - 1];
+ outputLocation++;
+ opstackLocation--;
+ }
+ opstackLocation--;
+
+ numBrackets += 2;
+ }
+ else if(tokens[i].raw.op.priority == 0)
+ {
+ opstack[opstackLocation] = tokens[i];
+ opstackLocation++;
+ }
+ else
+ {
+ while(opstackLocation != 0
+ && (opstack[opstackLocation - 1].raw.op.priority == 0
+ || tokens[i].raw.op.priority < opstack[opstackLocation - 1].raw.op.priority
+ || (tokens[i].raw.op.priority == opstack[opstackLocation - 1].raw.op.priority && opstack[opstackLocation - 1].raw.op.ltr))
+ && opstack[opstackLocation - 1].raw.op.c != CALC_CHAR_BEG)
+ {
+ output[outputLocation] = opstack[opstackLocation - 1];
+ outputLocation++;
+ opstackLocation--;
+ }
+ opstack[opstackLocation] = tokens[i];
+ opstackLocation++;
+ }
+ }
+
+ tokenCount -= numBrackets;
+
+ for(signed char i = opstackLocation - 1; i >= 0; i--)
+ {
+ output[outputLocation] = opstack[i];
+ outputLocation++;
+ opstackLocation--;
+ }
+
+ double answer[CALC_BUFFER_SIZE];
+ unsigned char answerLocation = 0;
+
+ for(unsigned char i = 0; i < tokenCount; i++)
+ {
+ if(output[i].isNum)
+ {
+ answer[answerLocation] = output[i].raw.num;
+ answerLocation++;
+ continue;
+ }
+
+ if(output[i].raw.op.priority == 0)
+ {
+ if (answerLocation < 1) { /* not handled here -- ERROR? */ } else
+ if(answerLocation >= 1)
+ {
+ double (*op)(double);
+ switch(output[i].raw.op.c)
+ {
+ case CALC_CHAR_SIN:
+ op = sin;
+ break;
+ case CALC_CHAR_COS:
+ op = cos;
+ break;
+ case CALC_CHAR_TAN:
+ op = tan;
+ break;
+ case CALC_CHAR_ASN:
+ op = asin;
+ break;
+ case CALC_CHAR_ACS:
+ op = acos;
+ break;
+ case CALC_CHAR_ATN:
+ op = atan;
+ break;
+ case CALC_CHAR_LGE:
+ op = log;
+ break;
+ case CALC_CHAR_LOG:
+ op = log10;
+ break;
+ case CALC_CHAR_SQT:
+ op = sqrt;
+ break;
+ default:
+ continue; /* invalid input */
+ }
+ answer[answerLocation - 1] = op(answer[answerLocation - 1]);
+ }
+ }
+ /* priority != 0 */
+ else if(answerLocation >= 2)
+ {
+ switch(output[i].raw.op.c)
+ {
+ case CALC_CHAR_ADD:
+ answer[answerLocation - 2] += answer[answerLocation - 1];
+ break;
+ case CALC_CHAR_SUB:
+ answer[answerLocation - 2] -= answer[answerLocation - 1];
+ break;
+ case CALC_CHAR_MUL:
+ answer[answerLocation - 2] *= answer[answerLocation - 1];
+ break;
+ case CALC_CHAR_DIV:
+ answer[answerLocation - 2] /= answer[answerLocation - 1];
+ break;
+ case CALC_CHAR_EXP:
+ answer[answerLocation - 2] = pow(answer[answerLocation - 2], answer[answerLocation - 1]);
+ break;
+ }
+
+ answerLocation--;
+ }
+ }
+
+ return answer[0];
+}
+
+/*
+ * @returns 0 when nothing should happen and QMK should work as usual
+ * @returns -1 when invalid input was given, QMK should ignore it
+ * @returns -2 when BSP should be done
+ * @returns -3 when CALC should be done
+ * @returns -4 when ENDCALC should be done
+ * @returns positive value of CALC_* when normal input was processed
+ */
+static int process_input(const uint16_t keycode, const uint8_t mods, const keyevent_t event)
+{
+ /* handle even when no key was pressed */
+ if(!event.pressed)
+ {
+ switch(keycode)
+ {
+ /* QMK should handle those */
+ case KC_RSFT:
+ case KC_LSFT:
+ return 0;
+ break;
+ }
+ /* ??? ignore */
+ return -1;
+ }
+
+ /* when shift key is pressed handle characters differently */
+ char characterPressed;
+ if((get_mods() & MODS_SHIFT_MASK))
+ {
+ switch(keycode)
+ {
+ case KC_9:
+ characterPressed = CALC_CHAR_BEG;
+ break;
+ case KC_0:
+ characterPressed = CALC_CHAR_END;
+ break;
+ case KC_EQUAL:
+ characterPressed = CALC_CHAR_ADD;
+ break;
+ case KC_KP_PLUS:
+ characterPressed = CALC_CHAR_ADD;
+ break;
+ case KC_6:
+ characterPressed = CALC_CHAR_EXP;
+ break;
+ case KC_8:
+ characterPressed = CALC_CHAR_MUL;
+ break;
+ case KC_KP_ASTERISK:
+ characterPressed = CALC_CHAR_MUL;
+ break;
+ case KC_S:
+ characterPressed = CALC_CHAR_ASN;
+ break;
+ case KC_C:
+ characterPressed = CALC_CHAR_ACS;
+ break;
+ case KC_T:
+ characterPressed = CALC_CHAR_ATN;
+ break;
+ case KC_L:
+ characterPressed = CALC_CHAR_LOG;
+ break;
+ default:
+ return -1;
+ break;
+ }
+ return characterPressed;
+ }
+
+ /* normal key handling: shift not pressed */
+
+ /* digits */
+ if (keycode == KC_KP_0 || keycode == KC_0) {
+ return '0';
+ } else if (keycode >= KC_KP_1 && keycode <= KC_KP_9) {
+ return keycode - KC_KP_1 +1 + '0';
+ } else if (keycode >= KC_1 && keycode <= KC_9) {
+ return keycode - KC_1 +1 + '0';
+ }
+
+ /* other tokens */
+ switch (keycode) {
+ case KC_MINUS:
+ case KC_KP_MINUS:
+ return characterPressed = CALC_CHAR_SUB;
+ case KC_SLASH:
+ case KC_KP_SLASH:
+ return characterPressed = CALC_CHAR_DIV;
+ case KC_S:
+ return characterPressed = CALC_CHAR_SIN;
+ case KC_C:
+ return characterPressed = CALC_CHAR_COS;
+ case KC_T:
+ return characterPressed = CALC_CHAR_TAN;
+ case KC_Q:
+ return characterPressed = CALC_CHAR_SQT;
+ case KC_L:
+ return characterPressed = CALC_CHAR_LGE;
+ case KC_DOT:
+ case KC_KP_DOT:
+ return characterPressed = CALC_CHAR_DEC;
+ case KC_P:
+ return characterPressed = CALC_CHAR_PI;
+ case KC_E:
+ return characterPressed = CALC_CHAR_EUL;
+ case KC_BSPC:
+ return -2;
+ case KC_RSFT:
+ return 0;
+ case KC_LSFT:
+ return 0;
+ case CALC:
+ return -3;
+ case ENDCALC:
+ return -4;
+ default:
+ return -1;
+ }
+}
+
+bool process_record_user(uint16_t keycode, keyrecord_t* record)
+{
+ static char text[CALC_BUFFER_SIZE + 1]; // Used to store input and then output when ready to print
+ static char backspaceText[CALC_BUFFER_SIZE + 1]; // Pretty dumb waste of memory because only backspace characters, used with send_string to backspace and remove input
+
+ if((biton32(layer_state) == CALC_LAYER && CALC_FORCE_NUM_LOCK_INSIDE_CALC) || (biton32(layer_state) != CALC_LAYER && CALC_FORCE_NUM_LOCK_OUTSIDE_CALC))
+ {
+ bool numpadKeyPressed = record->event.pressed &&
+ !(get_mods() & MODS_SHIFT_MASK) &&
+ /* KC_KP_1, KC_KP_2, ..., KC_KP_0, KC_KP_DOT */
+ (keycode >= KC_KP_1 && keycode <= KC_KP_DOT);
+
+ if(numpadKeyPressed && !(host_keyboard_leds() & (1 << USB_LED_NUM_LOCK)))
+ {
+ add_key(KC_NLCK);
+ send_keyboard_report();
+ del_key(KC_NLCK);
+ }
+ }
+
+ if(biton32(layer_state) != CALC_LAYER) { return true; }
+
+ int action = process_input(keycode, get_mods(), record->event);
+ switch(action)
+ {
+ case 0:
+ return true;
+ case -1:
+ return false;
+ case -2:
+ if(inputLocation > 0)
+ {
+ inputLocation--;
+ text[inputLocation] = '\0';
+ backspaceText[0] = (char)8;
+ backspaceText[1] = '\0';
+ send_string(backspaceText);
+ }
+ return false;
+ case -3:
+ for(int i = 0; i < inputLocation; i++)
+ {
+ backspaceText[i] = (char)8;
+ }
+ send_string(backspaceText);
+ dtostrf(calc(text), CALC_PRINT_SIZE, CALC_PRINT_SIZE, text);
+ send_string(text);
+ for(unsigned char i = 0; i < CALC_BUFFER_SIZE; i++)
+ {
+ text[i] = '\0';
+ backspaceText[i] = '\0';
+ }
+ inputLocation = 0;
+ return false;
+ case -4:
+ for(unsigned char i = 0; i < CALC_BUFFER_SIZE; i++)
+ {
+ text[i] = '\0';
+ backspaceText[i] = '\0';
+ }
+ inputLocation = 0;
+ layer_off(CALC_LAYER);
+ return false;
+ default:
+ break;
+ }
+ char characterPressed = (char)action;
+
+ if(inputLocation < CALC_BUFFER_SIZE)
+ {
+ text[inputLocation] = characterPressed;
+ inputLocation++;
+
+ char characterToSend[2];
+ characterToSend[0] = characterPressed;
+ characterToSend[1] = '\0';
+
+ send_string(characterToSend);
+ }
+ return false;
+} \ No newline at end of file
diff --git a/users/doogle999/doogle999.h b/users/doogle999/doogle999.h
new file mode 100644
index 0000000000..7ed38fbcc8
--- /dev/null
+++ b/users/doogle999/doogle999.h
@@ -0,0 +1,99 @@
+#ifndef USERSPACE
+#define USERSPACE
+
+#include "quantum.h"
+
+#define NO_ACTION_ONESHOT
+#define NO_ACTION_MACRO
+
+#define MODS_SHIFT_MASK (MOD_BIT(KC_LSHIFT)|MOD_BIT(KC_RSHIFT))
+
+// Layer the calculator is on
+#define CALC_LAYER 2
+
+// Inside is whether when you are in calc mode it should automatically force numlock, outside is whether it should do it outside of calculator mode
+#define CALC_FORCE_NUM_LOCK_INSIDE_CALC true
+#define CALC_FORCE_NUM_LOCK_OUTSIDE_CALC true
+
+// Maximum number of characters the calculator can have
+#define CALC_BUFFER_SIZE 32
+
+// Minimum width of the printed text / the number of decimal places
+#define CALC_PRINT_SIZE 6
+
+/*-----
+ Special
+-----*/
+#define CALC_CHAR_BEG '('
+#define CALC_CHAR_END ')'
+#define CALC_CHAR_DEC '.'
+
+/*-----
+ Operators - Can add more here such as modulo %, factorial !
+-----*/
+#define CALC_CHAR_ADD '+'
+#define CALC_PRIO_ADD 1
+
+#define CALC_CHAR_SUB '-'
+#define CALC_PRIO_SUB 1
+
+#define CALC_CHAR_MUL '*'
+#define CALC_PRIO_MUL 2
+
+#define CALC_CHAR_DIV '/'
+#define CALC_PRIO_DIV 2
+
+#define CALC_CHAR_EXP '^'
+#define CALC_PRIO_EXP 3
+
+/*-----
+ Functions
+-----*/
+#define CALC_CHAR_SIN 's'
+#define CALC_CHAR_COS 'c'
+#define CALC_CHAR_TAN 't'
+
+#define CALC_CHAR_ASN 'S'
+#define CALC_CHAR_ACS 'C'
+#define CALC_CHAR_ATN 'T'
+
+#define CALC_CHAR_LGE 'l'
+#define CALC_CHAR_LOG 'L'
+
+#define CALC_CHAR_SQT 'q'
+
+/*-----
+ Constants
+-----*/
+#define CALC_CHAR_EUL 'e'
+#define CALC_VALU_EUL 2.71828182845904523536
+
+#define CALC_CHAR_PI 'p'
+#define CALC_VALU_PI 3.14159265358979323846
+
+struct OP // Operator/function
+{
+ char c;
+ unsigned char priority;
+ bool ltr;
+};
+
+union TokenRaw // A token after the input has been processed, can either be a number or an operator/function
+{
+ double num;
+ struct OP op;
+};
+
+struct Token // Encapsulator
+{
+ bool isNum;
+ union TokenRaw raw;
+};
+
+enum CalcFunctions // Hardware calculator key functionality
+{
+ CALC = SAFE_RANGE,
+ ENDCALC
+};
+
+#endif
diff --git a/users/doogle999/readme.md b/users/doogle999/readme.md
new file mode 100644
index 0000000000..e108555b9c
--- /dev/null
+++ b/users/doogle999/readme.md
@@ -0,0 +1,41 @@
+Copyright 2018 <name> <email> @doogle999
+
+Overview
+========
+
+This folder is just for some calculator code for my keyboards.
+
+Making Your Keyboard Into A Calculator
+--------------------------------------
+
+If you'd like to make your keyboard into a calculator, you can do it with this userspace (hopefully!)
+
+You can make a keymap for your keyboard of choice named doogle999 and then you can make it regularly.
+
+You should make one layer that is just the functionality for your calculator, so it just has the keys you need (numbers, symbols, some letters for functions). It should also have END_CALC and CALC somewhere. END_CALC gets you out of calculator mode, and CALC evaluates the calculation.
+
+On one of your other keymaps you should make a key that is TO(layer of calculator). This is how you will activate the calculator. You should also define the layer your calculator is on with the define CALC_LAYER in doogle999.h (this means that for all your keyboards, your calculator layer has to be the same layer).
+
+You can change what characters coorespond to what operators and functions and you can add more functions in doogle999.h and doogle999.c, you can also change which characters are sued for which keys. However, as of now standard keys should be used for operations. By that I mean if you want your multiplication sign to be an x, you should change the CALC_CHAR_MUL to an x but you should keep your multiplication keycode on the keymap either as KC_8 (shifted) or KC_KP_ASTERISK. This might be changed in the future so there are custom keycodes so this is less of a pain and more intuitive.
+
+You can look at my dz60 keymap doogle999 for an example.
+
+Issues
+------
+Unfortunately the chip onboard my dz60 only does single precision floating point numbers, but I have everything set up as double so if your chip supports doubles it should work for you.
+
+This Was Here When I Made The ReadMe
+------------------------------------
+
+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, either version 2 of the License, or
+(at your option) any later version.
+
+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/>. \ No newline at end of file
diff --git a/users/doogle999/rules.mk b/users/doogle999/rules.mk
new file mode 100644
index 0000000000..12698a27e5
--- /dev/null
+++ b/users/doogle999/rules.mk
@@ -0,0 +1,14 @@
+SRC += doogle999.c
+
+CFLAGS += -fstrict-aliasing -ftree-vrp
+
+BOOTMAGIC_ENABLE = no # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = no # Mouse keys(+4700)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+450)
+CONSOLE_ENABLE = no # Console for debug(+400)
+COMMAND_ENABLE = no # Commands for debug and configuration
+SLEEP_LED_ENABLE = no # Breathing sleep LED during USB suspend
+NKRO_ENABLE = yes # USB Nkey Rollover - if this doesn't work, see here: https://github.com/tmk/tmk_keyboard/wiki/FAQ#nkro-doesnt-work
+BACKLIGHT_ENABLE = yes # Enable keyboard backlight functionality
+AUDIO_ENABLE = no
+RGBLIGHT_ENABLE = yes
diff --git a/users/drashna/.gitlab-ci.yml b/users/drashna/.gitlab-ci.yml
new file mode 100644
index 0000000000..9b18d44fb3
--- /dev/null
+++ b/users/drashna/.gitlab-ci.yml
@@ -0,0 +1,78 @@
+stages:
+ - test
+ - build
+ - deploy
+
+Tests:
+ stage: test
+ variables:
+ GIT_SUBMODULE_STRATEGY: recursive
+ tags:
+ - linux
+ image: ubuntu:18.10
+ before_script:
+ - apt-get update -qy
+ - apt-get install -y build-essential avr-libc binutils-arm-none-eabi binutils-avr dfu-programmer dfu-util gcc gcc-arm-none-eabi gcc-avr git libnewlib-arm-none-eabi unzip wget zip
+ - avr-gcc --version
+ - uname -a
+ script:
+ - make test:all
+ - make planck/rev6:default
+
+QMK Firmware Defaults:
+ stage: deploy
+ variables:
+ GIT_SUBMODULE_STRATEGY: recursive
+ tags:
+ - linux
+ image: ubuntu:18.10
+ before_script:
+ - apt-get update -qy
+ - apt-get install -y build-essential avr-libc binutils-arm-none-eabi binutils-avr dfu-programmer dfu-util gcc gcc-arm-none-eabi gcc-avr git libnewlib-arm-none-eabi unzip wget zip
+ - avr-gcc --version
+ - uname -a
+ script:
+ - make test:all
+ - make all:default -j16
+
+Drashna Firmware:
+ stage: build
+ variables:
+ GIT_SUBMODULE_STRATEGY: recursive
+ tags:
+ - linux
+ image: ubuntu:18.10
+ before_script:
+ - apt-get update -qy
+ - apt-get install -y build-essential avr-libc binutils-arm-none-eabi binutils-avr dfu-programmer dfu-util gcc gcc-arm-none-eabi gcc-avr git libnewlib-arm-none-eabi unzip wget zip
+ - avr-gcc --version
+ script:
+ - make iris/rev2:drashna iris/rev2:drashna_old ergodox_ez:drashna ergodox_ez:drashna_glow viterbi/rev1:drashna orthodox/rev1:drashna orthodox/rev3:drashna crkbd:drashna planck/light:drashna planck/rev6:drashna fractal:drashna
+ artifacts:
+ name: "$CI_JOB_NAME-$CI_COMMIT_REF_SLUG"
+ paths:
+ - ./*.hex
+ - ./*.bin
+ expire_in: 1 month
+
+Firmware Deploy:
+ stage: deploy
+ dependencies:
+ - Drashna Firmware
+ variables:
+ GIT_SUBMODULE_STRATEGY: recursive
+ tags:
+ - linux
+ image: ubuntu:18.10
+ before_script:
+ - apt-get update -qy
+ - apt-get install -y build-essential avr-libc binutils-arm-none-eabi binutils-avr dfu-programmer dfu-util gcc gcc-arm-none-eabi gcc-avr git libnewlib-arm-none-eabi unzip wget zip
+ - avr-gcc --version
+ script:
+ - make iris/rev2:drashna:production iris/rev2:drashna_old:production ergodox_ez:drashna ergodox_ez:drashna_glow viterbi/rev1:drashna:production orthodox/rev1:drashna:production orthodox/rev3:drashna:production crkbd:drashna:production planck/light:drashna planck/rev6:drashna fractal:drashna:production
+ artifacts:
+ name: "$CI_JOB_NAME-$CI_COMMIT_REF_SLUG"
+ paths:
+ - ./*.hex
+ - ./*.bin
+ expire_in: 1 month
diff --git a/users/drashna/config.h b/users/drashna/config.h
index 87050fbcc7..827b1b8ace 100644
--- a/users/drashna/config.h
+++ b/users/drashna/config.h
@@ -3,7 +3,7 @@
#ifdef AUDIO_ENABLE
#define AUDIO_CLICKY
-#define STARTUP_SONG SONG(E1M1_DOOM)
+#define STARTUP_SONG SONG(RICK_ROLL)
#define GOODBYE_SONG SONG(SONIC_RING)
#define DEFAULT_LAYER_SONGS { SONG(QWERTY_SOUND), \
SONG(COLEMAK_SOUND), \
@@ -11,16 +11,24 @@
SONG(OVERWATCH_THEME) \
}
-#define AUDIO_CLICKY_FREQ_RANDOMNESS 1.0f
-
-#endif
+#define AUDIO_CLICKY_FREQ_RANDOMNESS 1.5f
+// #ifdef RGBLIGHT_ENABLE
+// #define NO_MUSIC_MODE
+// #endif //RGBLIGHT_ENABLE/
+#ifndef __arm__
+#undef NOTE_REST
+#define NOTE_REST 1.00f
+#endif // !__arm__
+#endif // !AUDIO_ENABLE
#ifdef RGBLIGHT_ENABLE
#define RGBLIGHT_SLEEP
+#undef RGBLIGHT_ANIMATIONS
+#define RGBLIGHT_EFFECT_BREATHING
+#define RGBLIGHT_EFFECT_SNAKE
+#define RGBLIGHT_EFFECT_KNIGHT
#endif // RGBLIGHT_ENABLE
-
-
#ifndef ONESHOT_TAP_TOGGLE
#define ONESHOT_TAP_TOGGLE 2
#endif // !ONESHOT_TAP_TOGGLE
@@ -41,8 +49,7 @@
// actually sends Ctrl-x. That's bad.)
#define IGNORE_MOD_TAP_INTERRUPT
#undef PERMISSIVE_HOLD
-#undef PREVENT_STUCK_MODIFIERS
-// #define TAPPING_FORCE_HOLD
+//#define TAPPING_FORCE_HOLD
//#define RETRO_TAPPING
#define FORCE_NKRO
@@ -54,22 +61,18 @@
#ifdef TAPPING_TERM
#undef TAPPING_TERM
#endif // TAPPING_TERM
-#define TAPPING_TERM 175
+#if defined(KEYBOARD_ergodox_ez)
+ #define TAPPING_TERM 185
+#elif defined(KEYBOARD_crkbd)
+ #define TAPPING_TERM 200
+#else
+ #define TAPPING_TERM 175
+#endif
// Disable action_get_macro and fn_actions, since we don't use these
// and it saves on space in the firmware.
-#ifndef NO_DEBUG
-#define NO_DEBUG
-#endif // !NO_DEBUG
-#if !defined(NO_PRINT) && !defined(CONSOLE_ENABLE)
-#define NO_PRINT
-#endif // !NO_PRINT
#define NO_ACTION_MACRO
#define NO_ACTION_FUNCTION
-#define DISABLE_LEADER
-
#define MACRO_TIMER 5
-
-
diff --git a/users/drashna/drashna.c b/users/drashna/drashna.c
index f72902f0b0..2228248379 100644
--- a/users/drashna/drashna.c
+++ b/users/drashna/drashna.c
@@ -16,38 +16,37 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "drashna.h"
-#include "version.h"
-#include "eeprom.h"
-#include "tap_dances.h"
-#include "rgb_stuff.h"
-
-float tone_copy[][2] = SONG(SCROLL_LOCK_ON_SOUND);
-float tone_paste[][2] = SONG(SCROLL_LOCK_OFF_SOUND);
-
-static uint16_t copy_paste_timer;
userspace_config_t userspace_config;
-
-// Helper Functions
+#if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ #define DRASHNA_UNICODE_MODE UC_WIN
+#else
+ // set to 2 for UC_WIN, set to 4 for UC_WINC
+ #define DRASHNA_UNICODE_MODE 2
+#endif
// This block is for all of the gaming macros, as they were all doing
// the same thing, but with differring text sent.
bool send_game_macro(const char *str, keyrecord_t *record, bool override) {
if (!record->event.pressed || override) {
+ uint16_t keycode;
+ if (userspace_config.is_overwatch) {
+ keycode = KC_BSPC;
+ } else {
+ keycode = KC_ENTER;
+ }
clear_keyboard();
- tap(userspace_config.is_overwatch ? KC_BSPC : KC_ENTER);
+ tap_code(keycode);
wait_ms(50);
send_string_with_delay(str, MACRO_TIMER);
wait_ms(50);
- tap(KC_ENTER);
+ tap_code(KC_ENTER);
}
if (override) wait_ms(3000);
return false;
}
-void tap(uint16_t keycode){ register_code(keycode); unregister_code(keycode); };
-
bool mod_key_press_timer (uint16_t code, uint16_t mod_code, bool pressed) {
static uint16_t this_timer;
if(pressed) {
@@ -83,6 +82,21 @@ bool mod_key_press (uint16_t code, uint16_t mod_code, bool pressed, uint16_t thi
return false;
}
+void bootmagic_lite(void) {
+ matrix_scan();
+ #if defined(DEBOUNCING_DELAY) && DEBOUNCING_DELAY > 0
+ wait_ms(DEBOUNCING_DELAY * 2);
+ #elif defined(DEBOUNCE) && DEBOUNCE > 0
+ wait_ms(DEBOUNCE * 2);
+ #else
+ wait_ms(30);
+ #endif
+ matrix_scan();
+ if (matrix_get_row(BOOTMAGIC_LITE_ROW) & (1 << BOOTMAGIC_LITE_COLUMN)) {
+ bootloader_jump();
+ }
+}
+
// Add reconfigurable functions here, for keymap customization
// This allows for a global, userspace functions, and continued
// customization of the keymap. Use _keymap instead of _user
@@ -90,88 +104,65 @@ bool mod_key_press (uint16_t code, uint16_t mod_code, bool pressed, uint16_t thi
__attribute__ ((weak))
void matrix_init_keymap(void) {}
-__attribute__ ((weak))
-void startup_keymap(void) {}
-
-__attribute__ ((weak))
-void suspend_power_down_keymap(void) {}
-
-__attribute__ ((weak))
-void suspend_wakeup_init_keymap(void) {}
-
-__attribute__ ((weak))
-void matrix_scan_keymap(void) {}
-
-__attribute__ ((weak))
-bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
- return true;
-}
-
-__attribute__ ((weak))
-bool process_record_secrets(uint16_t keycode, keyrecord_t *record) {
- return true;
-}
-
-
-__attribute__ ((weak))
-uint32_t layer_state_set_keymap (uint32_t state) {
- return state;
-}
-
-__attribute__ ((weak))
-uint32_t default_layer_state_set_keymap (uint32_t state) {
- return state;
-}
-
-__attribute__ ((weak))
-void led_set_keymap(uint8_t usb_led) {}
-
-
// Call user matrix init, set default RGB colors and then
// call the keymap's init function
void matrix_init_user(void) {
- userspace_config.raw = eeprom_read_byte(EECONFIG_USERSPACE);
+ userspace_config.raw = eeconfig_read_user();
-#ifdef AUDIO_CLICKY
- clicky_enable = userspace_config.clicky_enable;
-#endif
-
-#ifdef BOOTLOADER_CATERINA
- DDRD &= ~(1<<5);
- PORTD &= ~(1<<5);
-
- DDRB &= ~(1<<0);
- PORTB &= ~(1<<0);
-#endif
+ #ifdef BOOTLOADER_CATERINA
+ DDRD &= ~(1<<5);
+ PORTD &= ~(1<<5);
+ DDRB &= ~(1<<0);
+ PORTB &= ~(1<<0);
+ #endif
-#if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
- set_unicode_input_mode(UC_WINC);
-#endif //UNICODE_ENABLE
+ #if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ set_unicode_input_mode(DRASHNA_UNICODE_MODE);
+ get_unicode_input_mode();
+ #endif //UNICODE_ENABLE
matrix_init_keymap();
-}
-
-void startup_user (void) {
#ifdef RGBLIGHT_ENABLE
matrix_init_rgb();
#endif //RGBLIGHT_ENABLE
- startup_keymap();
}
-void suspend_power_down_user(void)
-{
+
+__attribute__ ((weak))
+void shutdown_keymap(void) {}
+
+void shutdown_user (void) {
+ #ifdef RGBLIGHT_ENABLE
+ rgblight_enable_noeeprom();
+ rgblight_mode_noeeprom(1);
+ rgblight_setrgb_red();
+ #endif // RGBLIGHT_ENABLE
+ #ifdef RGB_MATRIX_ENABLE
+ uint16_t timer_start = timer_read();
+ rgb_matrix_set_color_all( 0xFF, 0x00, 0x00 );
+ while(timer_elapsed(timer_start) < 250) { wait_ms(1); }
+ #endif //RGB_MATRIX_ENABLE
+ shutdown_keymap();
+}
+
+__attribute__ ((weak))
+void suspend_power_down_keymap(void) {}
+
+void suspend_power_down_user(void) {
suspend_power_down_keymap();
}
-void suspend_wakeup_init_user(void)
-{
+__attribute__ ((weak))
+void suspend_wakeup_init_keymap(void) {}
+
+void suspend_wakeup_init_user(void) {
suspend_wakeup_init_keymap();
- #ifdef KEYBOARD_ergodox_ez
- wait_ms(10);
- #endif
}
+__attribute__ ((weak))
+void matrix_scan_keymap(void) {}
+
// No global matrix scan code, so just run keymap's matrix
// scan function
void matrix_scan_user(void) {
@@ -193,210 +184,11 @@ void matrix_scan_user(void) {
}
-
-
-// Defines actions tor my global custom keycodes. Defined in drashna.h file
-// Then runs the _keymap's record handier if not processed here
-bool process_record_user(uint16_t keycode, keyrecord_t *record) {
-
- // If console is enabled, it will print the matrix position and status of each key pressed
-#ifdef KEYLOGGER_ENABLE
- xprintf("KL: row: %u, column: %u, pressed: %u\n", record->event.key.col, record->event.key.row, record->event.pressed);
-#endif //KEYLOGGER_ENABLE
-
- switch (keycode) {
- case KC_QWERTY:
- if (record->event.pressed) {
- set_single_persistent_default_layer(_QWERTY);
- }
- return false;
- break;
- case KC_COLEMAK:
- if (record->event.pressed) {
- set_single_persistent_default_layer(_COLEMAK);
- }
- return false;
- break;
- case KC_DVORAK:
- if (record->event.pressed) {
- set_single_persistent_default_layer(_DVORAK);
- }
- return false;
- break;
- case KC_WORKMAN:
- if (record->event.pressed) {
- set_single_persistent_default_layer(_WORKMAN);
- }
- return false;
- break;
-
-
- case KC_MAKE: // Compiles the firmware, and adds the flash command based on keyboard bootloader
- if (!record->event.pressed) {
- send_string_with_delay_P(PSTR("make " QMK_KEYBOARD ":" QMK_KEYMAP
-#if (defined(BOOTLOADER_DFU) || defined(BOOTLOADER_LUFA_DFU) || defined(BOOTLOADER_QMK_DFU))
- ":dfu"
-#elif defined(BOOTLOADER_HALFKAY)
- ":teensy"
-#elif defined(BOOTLOADER_CATERINA)
- ":avrdude"
-#endif // bootloader options
- SS_TAP(X_ENTER)), 10);
- }
- return false;
- break;
-
-
- case KC_RESET: // Custom RESET code that sets RGBLights to RED
- if (!record->event.pressed) {
-#ifdef RGBLIGHT_ENABLE
- rgblight_enable_noeeprom();
- rgblight_mode_noeeprom(1);
- rgblight_setrgb_red();
-#endif // RGBLIGHT_ENABLE
- reset_keyboard();
- }
- return false;
- break;
-
-
- case EPRM: // Resets EEPROM
- if (record->event.pressed) {
- eeconfig_init();
- default_layer_set(1UL<<eeconfig_read_default_layer());
- layer_state_set(layer_state);
- }
- return false;
- break;
- case VRSN: // Prints firmware version
- if (record->event.pressed) {
- send_string_with_delay_P(PSTR(QMK_KEYBOARD "/" QMK_KEYMAP " @ " QMK_VERSION ", Built on: " QMK_BUILDDATE), MACRO_TIMER);
- }
- return false;
- break;
-
-/* Code has been depreciated
- case KC_SECRET_1 ... KC_SECRET_5: // Secrets! Externally defined strings, not stored in repo
- if (!record->event.pressed) {
- clear_oneshot_layer_state(ONESHOT_OTHER_KEY_PRESSED);
- send_string(decoy_secret[keycode - KC_SECRET_1]);
- }
- return false;
- break;
-*/
-
-// These are a serious of gaming macros.
-// Only enables for the viterbi, basically,
-// to save on firmware space, since it's limited.
-#ifdef MACROS_ENABLED
- case KC_OVERWATCH: // Toggle's if we hit "ENTER" or "BACKSPACE" to input macros
- if (record->event.pressed) { userspace_config.is_overwatch ^= 1; eeprom_update_byte(EECONFIG_USERSPACE, userspace_config.raw); }
-#ifdef RGBLIGHT_ENABLE
- userspace_config.is_overwatch ? rgblight_mode_noeeprom(17) : rgblight_mode_noeeprom(18);
-#endif //RGBLIGHT_ENABLE
- return false; break;
- case KC_SALT:
- return send_game_macro("Salt, salt, salt...", record, false);
- case KC_MORESALT:
- return send_game_macro("Please sir, can I have some more salt?!", record, false);
- case KC_SALTHARD:
- return send_game_macro("Your salt only makes me harder, and even more aggressive!", record, false);
- case KC_GOODGAME:
- return send_game_macro("Good game, everyone!", record, false);
- case KC_GLHF:
- return send_game_macro("Good luck, have fun!!!", record, false);
- case KC_SYMM:
- return send_game_macro("Left click to win!", record, false);
- case KC_JUSTGAME:
- return send_game_macro("It may be a game, but if you don't want to actually try, please go play AI, so that people that actually want to take the game seriously and \"get good\" have a place to do so without trolls like you throwing games.", record, false);
- case KC_TORB:
- return send_game_macro("That was positively riveting!", record, false);
- case KC_AIM:
- send_game_macro("That aim is absolutely amazing. It's almost like you're a machine!", record, true);
- return send_game_macro("Wait! That aim is TOO good! You're clearly using an aim hack! CHEATER!", record, false);
- case KC_C9:
- return send_game_macro("OMG!!! C9!!!", record, false);
- case KC_GGEZ:
- return send_game_macro("That was a fantastic game, though it was a bit easy. Try harder next time!", record, false);
-#endif // MACROS_ENABLED
-
-
- case KC_DIABLO_CLEAR: // reset all Diablo timers, disabling them
-#ifdef TAP_DANCE_ENABLE
- if (record->event.pressed) {
- uint8_t dtime;
- for (dtime = 0; dtime < 4; dtime++) {
- diablo_key_time[dtime] = diablo_times[0];
- }
- }
-#endif // TAP_DANCE_ENABLE
- return false; break;
-
-
- case KC_CCCV: // One key copy/paste
- if(record->event.pressed){
- copy_paste_timer = timer_read();
- } else {
- if (timer_elapsed(copy_paste_timer) > TAPPING_TERM) { // Hold, copy
- register_code(KC_LCTL);
- tap(KC_C);
- unregister_code(KC_LCTL);
-#ifdef AUDIO_ENABLE
- PLAY_SONG(tone_copy);
-#endif
- } else { // Tap, paste
- register_code(KC_LCTL);
- tap(KC_V);
- unregister_code(KC_LCTL);
-#ifdef AUDIO_ENABLE
- PLAY_SONG(tone_paste);
-#endif
- }
- }
- return false;
- break;
- case CLICKY_TOGGLE:
-#ifdef AUDIO_CLICKY
- userspace_config.clicky_enable = clicky_enable;
- eeprom_update_byte(EECONFIG_USERSPACE, userspace_config.raw);
-#endif
- break;
-#ifdef UNICODE_ENABLE
- case UC_FLIP: // (╯°□°)╯ ︵ ┻━┻
- if (record->event.pressed) {
- register_code(KC_RSFT);
- tap(KC_9);
- unregister_code(KC_RSFT);
- process_unicode((0x256F | QK_UNICODE), record); // Arm
- process_unicode((0x00B0 | QK_UNICODE), record); // Eye
- process_unicode((0x25A1 | QK_UNICODE), record); // Mouth
- process_unicode((0x00B0 | QK_UNICODE), record); // Eye
- register_code(KC_RSFT);
- tap(KC_0);
- unregister_code(KC_RSFT);
- process_unicode((0x256F | QK_UNICODE), record); // Arm
- tap(KC_SPC);
- process_unicode((0x0361 | QK_UNICODE), record); // Flippy
- tap(KC_SPC);
- process_unicode((0x253B | QK_UNICODE), record); // Table
- process_unicode((0x2501 | QK_UNICODE), record); // Table
- process_unicode((0x253B | QK_UNICODE), record); // Table
- }
- return false;
- break;
-#endif // UNICODE_ENABLE
-
- }
- return process_record_keymap(keycode, record) &&
-#ifdef RGBLIGHT_ENABLE
- process_record_user_rgb(keycode, record) &&
-#endif // RGBLIGHT_ENABLE
- process_record_secrets(keycode, record);
+__attribute__ ((weak))
+uint32_t layer_state_set_keymap (uint32_t state) {
+ return state;
}
-
-
-// Runs state check and changes underglow color and animation
// on layer change, no matter where the change was initiated
// Then runs keymap's layer change check
uint32_t layer_state_set_user(uint32_t state) {
@@ -408,10 +200,22 @@ uint32_t layer_state_set_user(uint32_t state) {
}
-uint32_t default_layer_state_set_kb(uint32_t state) {
- return default_layer_state_set_keymap (state);
+__attribute__ ((weak))
+uint32_t default_layer_state_set_keymap (uint32_t state) {
+ return state;
}
+// Runs state check and changes underglow color and animation
+uint32_t default_layer_state_set_user(uint32_t state) {
+ state = default_layer_state_set_keymap(state);
+#ifdef RGBLIGHT_ENABLE
+ state = default_layer_state_set_rgb(state);
+#endif // RGBLIGHT_ENABLE
+ return state;
+}
+
+__attribute__ ((weak))
+void led_set_keymap(uint8_t usb_led) {}
// Any custom LED code goes here.
// So far, I only have keyboard specific code,
@@ -419,3 +223,18 @@ uint32_t default_layer_state_set_kb(uint32_t state) {
void led_set_user(uint8_t usb_led) {
led_set_keymap(usb_led);
}
+
+__attribute__ ((weak))
+void eeconfig_init_keymap(void) {}
+
+void eeconfig_init_user(void) {
+ userspace_config.raw = 0;
+ userspace_config.rgb_layer_change = true;
+ eeconfig_update_user(userspace_config.raw);
+ #if (defined(UNICODE_ENABLE) || defined(UNICODEMAP_ENABLE) || defined(UCIS_ENABLE))
+ set_unicode_input_mode(DRASHNA_UNICODE_MODE);
+ get_unicode_input_mode();
+ #else
+ eeprom_update_byte(EECONFIG_UNICODEMODE, DRASHNA_UNICODE_MODE);
+ #endif
+}
diff --git a/users/drashna/drashna.h b/users/drashna/drashna.h
index 3efef57046..0a3d0f6327 100644
--- a/users/drashna/drashna.h
+++ b/users/drashna/drashna.h
@@ -15,12 +15,21 @@ You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-#ifndef USERSPACE
-#define USERSPACE
+#pragma once
#include "quantum.h"
+#include "version.h"
+#include "eeprom.h"
+#include "wrappers.h"
+#include "process_records.h"
+#ifdef TAP_DANCE_ENABLE
+ #include "tap_dances.h"
+#endif // TAP_DANCE_ENABLE
+#if defined(RGBLIGHT_ENABLE) || defined(RGB_MATRIX_ENABLE)
+ #include "rgb_stuff.h"
+#endif
-// Define layer names
+/* Define layer names */
enum userspace_layers {
_QWERTY = 0,
_NUMLOCK = 0,
@@ -37,130 +46,47 @@ enum userspace_layers {
_ADJUST,
};
-//define modifiers
+/*
+define modifiers here, since MOD_* doesn't seem to work for these
+ */
#define MODS_SHIFT_MASK (MOD_BIT(KC_LSHIFT)|MOD_BIT(KC_RSHIFT))
#define MODS_CTRL_MASK (MOD_BIT(KC_LCTL)|MOD_BIT(KC_RCTRL))
#define MODS_ALT_MASK (MOD_BIT(KC_LALT)|MOD_BIT(KC_RALT))
#define MODS_GUI_MASK (MOD_BIT(KC_LGUI)|MOD_BIT(KC_RGUI))
-// RGB color codes are no longer located here anymore. Instead, you will want to
-// head to https://github.com/qmk/qmk_firmware/blob/master/quantum/rgblight_list.h
-
-extern bool clicky_enable;
-
-#ifdef RGBLIGHT_ENABLE
-void rgblight_sethsv_default_helper(uint8_t index);
-#endif // RGBLIGHT_ENABLE
-void tap(uint16_t keycode);
bool mod_key_press_timer (uint16_t code, uint16_t mod_code, bool pressed);
bool mod_key_press (uint16_t code, uint16_t mod_code, bool pressed, uint16_t this_timer);
-
-#define EECONFIG_USERSPACE (uint8_t *)19
+bool send_game_macro(const char *str, keyrecord_t *record, bool override);
+void matrix_init_keymap(void);
+void shutdown_keymap(void);
+void suspend_power_down_keymap(void);
+void suspend_wakeup_init_keymap(void);
+void matrix_scan_keymap(void);
+uint32_t layer_state_set_keymap (uint32_t state);
+uint32_t default_layer_state_set_keymap (uint32_t state);
+void led_set_keymap(uint8_t usb_led);
+void eeconfig_init_keymap(void);
typedef union {
- uint8_t raw;
+ uint32_t raw;
struct {
- bool clicky_enable :1;
bool rgb_layer_change :1;
bool is_overwatch :1;
bool nuke_switch :1;
+ uint8_t unicode_mod :4;
};
} userspace_config_t;
-enum userspace_custom_keycodes {
- EPRM = SAFE_RANGE, // Resets EEPROM do defaults (as in eeconfig_init)
- VRSN, // Prints QMK Firmware and board info
- KC_QWERTY, // Sets default layer to QWERTY
- KC_COLEMAK, // Sets default layer to COLEMAK
- KC_DVORAK, // Sets default layer to DVORAK
- KC_WORKMAN, // Sets default layer to WORKMAN
- KC_DIABLO_CLEAR, // Clears all Diablo Timers
- KC_OVERWATCH, // Toggles game macro input mode (so in OW, it defaults to game chat)
- KC_SALT, // See drashna.c for details
- KC_MORESALT,
- KC_SALTHARD,
- KC_GOODGAME,
- KC_SYMM,
- KC_JUSTGAME,
- KC_GLHF,
- KC_TORB,
- KC_AIM,
- KC_C9,
- KC_GGEZ,
- KC_MAKE, // Run keyboard's customized make command
- KC_RESET, // Resets keyboard, with red underglow
- KC_RGB_T, // Toggles RGB Layer Indication mode
- KC_SECRET_1, // test1
- KC_SECRET_2, // test2
- KC_SECRET_3, // test3
- KC_SECRET_4, // test4
- KC_SECRET_5, // test5
- KC_CCCV, // Hold to copy, tap to paste
- KC_NUKE, // NUCLEAR LAUNCH DETECTED!!!
-
-#ifdef UNICODE_ENABLE
- UC_FLIP, // Table flip (not working?)
-#endif //UNICODE_ENABLE
- NEW_SAFE_RANGE //use "NEWPLACEHOLDER for keymap specific codes
-};
-
-#define LOWER MO(_LOWER)
-#define RAISE MO(_RAISE)
-#define ADJUST MO(_ADJUST)
-#define TG_MODS TG(_MODS)
-#define TG_GAME TG(_GAMEPAD)
-
-#define KC_SEC1 KC_SECRET_1
-#define KC_SEC2 KC_SECRET_2
-#define KC_SEC3 KC_SECRET_3
-#define KC_SEC4 KC_SECRET_4
-#define KC_SEC5 KC_SECRET_5
-
-#define QWERTY KC_QWERTY
-#define DVORAK KC_DVORAK
-#define COLEMAK KC_COLEMAK
-#define WORKMAN KC_WORKMAN
-
-#define KC_RST KC_RESET
-
-#ifdef SWAP_HANDS_ENABLE
-#define KC_C1R3 SH_TT
-#else // SWAP_HANDS_ENABLE
-#define KC_C1R3 KC_BSPC
-#endif // SWAP_HANDS_ENABLE
-
-// OSM keycodes, to keep things clean and easy to change
-#define KC_MLSF OSM(MOD_LSFT)
-#define KC_MRSF OSM(MOD_RSFT)
-
-#define OS_LGUI OSM(MOD_LGUI)
-#define OS_RGUI OSM(MOD_RGUI)
-#define OS_LSFT OSM(MOD_LSFT)
-#define OS_RSFT OSM(MOD_RSFT)
-#define OS_LCTL OSM(MOD_LCTL)
-#define OS_RCTL OSM(MOD_RCTL)
-#define OS_LALT OSM(MOD_LALT)
-#define OS_RALT OSM(MOD_RALT)
-#define ALT_APP ALT_T(KC_APP)
-
-#define MG_NKRO MAGIC_TOGGLE_NKRO
-
-
-#ifdef TAP_DANCE_ENABLE
-enum {
- TD_D3_1 = 0,
- TD_D3_2,
- TD_D3_3,
- TD_D3_4
-};
-#endif // TAP_DANCE_ENABLE
+extern userspace_config_t userspace_config;
-// Custom Keycodes for Diablo 3 layer
-// But since TD() doesn't work when tap dance is disabled
-// We use custom codes here, so we can substitute the right stuff
+/*
+Custom Keycodes for Diablo 3 layer
+But since TD() doesn't work when tap dance is disabled
+We use custom codes here, so we can substitute the right stuff
+*/
#ifdef TAP_DANCE_ENABLE
#define KC_D3_1 TD(TD_D3_1)
#define KC_D3_2 TD(TD_D3_2)
@@ -172,182 +98,3 @@ enum {
#define KC_D3_3 KC_3
#define KC_D3_4 KC_4
#endif // TAP_DANCE_ENABLE
-
-
-
-// Since our quirky block definitions are basically a list of comma separated
-// arguments, we need a wrapper in order for these definitions to be
-// expanded before being used as arguments to the LAYOUT_xxx macro.
-#if (!defined(LAYOUT) && defined(KEYMAP))
-#define LAYOUT KEYMAP
-#endif
-
-#define LAYOUT_ergodox_wrapper(...) LAYOUT_ergodox(__VA_ARGS__)
-#define LAYOUT_ergodox_pretty_wrapper(...) LAYOUT_ergodox_pretty(__VA_ARGS__)
-#define KEYMAP_wrapper(...) LAYOUT(__VA_ARGS__)
-#define LAYOUT_wrapper(...) LAYOUT(__VA_ARGS__)
-#define LAYOUT_ortho_4x12_wrapper(...) LAYOUT_ortho_4x12(__VA_ARGS__)
-
-// Blocks for each of the four major keyboard layouts
-// Organized so we can quickly adapt and modify all of them
-// at once, rather than for each keyboard, one at a time.
-// And this allows for much cleaner blocks in the keymaps.
-// For instance Tap/Hold for Control on all of the layouts
-
-// NOTE: These are all the same length. If you do a search/replace
-// then you need to add/remove underscores to keep the
-// lengths consistent.
-
-#define _________________QWERTY_L1_________________ KC_Q, KC_W, KC_E, KC_R, KC_T
-#define _________________QWERTY_L2_________________ KC_A, KC_S, KC_D, KC_F, KC_G
-#define _________________QWERTY_L3_________________ CTL_T(KC_Z), KC_X, KC_C, KC_V, KC_B
-
-#define _________________QWERTY_R1_________________ KC_Y, KC_U, KC_I, KC_O, KC_P
-#define _________________QWERTY_R2_________________ KC_H, KC_J, KC_K, KC_L, KC_SCLN
-#define _________________QWERTY_R3_________________ KC_N, KC_M, KC_COMM, KC_DOT, CTL_T(KC_SLASH)
-
-
-#define _________________COLEMAK_L1________________ KC_Q, KC_W, KC_F, KC_P, KC_G
-#define _________________COLEMAK_L2________________ KC_A, KC_R, KC_S, KC_T, KC_D
-#define _________________COLEMAK_L3________________ CTL_T(KC_Z), KC_X, KC_C, KC_V, KC_B
-
-#define _________________COLEMAK_R1________________ KC_J, KC_L, KC_U, KC_Y, KC_SCLN
-#define _________________COLEMAK_R2________________ KC_H, KC_N, KC_E, KC_I, KC_O
-#define _________________COLEMAK_R3________________ KC_K, KC_M, KC_COMM, KC_DOT, CTL_T(KC_SLASH)
-
-#define ______________COLEMAK_MOD_DH_L1____________ KC_Q, KC_W, KC_F, KC_P, KC_B
-#define ______________COLEMAK_MOD_DH_L2____________ KC_A, KC_R, KC_S, KC_T, KC_G
-#define ______________COLEMAK_MOD_DH_L3____________ CTL_T(KC_Z), KC_X, KC_C, KC_D, KC_V
-
-#define ______________COLEMAK_MOD_DH_R1____________ KC_J, KC_L, KC_U, KC_Y, KC_SCLN
-#define ______________COLEMAK_MOD_DH_R2____________ KC_M, KC_N, KC_E, KC_I, KC_O
-#define ______________COLEMAK_MOD_DH_R3____________ KC_K, KC_H, KC_COMM, KC_DOT, CTL_T(KC_SLASH)
-
-
-#define _________________DVORAK_L1_________________ KC_QUOT, KC_COMM, KC_DOT, KC_P, KC_Y
-#define _________________DVORAK_L2_________________ KC_A, KC_O, KC_E, KC_U, KC_I
-#define _________________DVORAK_L3_________________ CTL_T(KC_SCLN),KC_Q, KC_J, KC_K, KC_X
-
-#define _________________DVORAK_R1_________________ KC_F, KC_G, KC_C, KC_R, KC_L
-#define _________________DVORAK_R2_________________ KC_D, KC_H, KC_T, KC_N, KC_S
-#define _________________DVORAK_R3_________________ KC_B, KC_M, KC_W, KC_V, CTL_T(KC_Z)
-
-
-#define _________________WORKMAN_L1________________ KC_Q, KC_D, KC_R, KC_W, KC_B
-#define _________________WORKMAN_L2________________ KC_A, KC_S, KC_H, KC_T, KC_G
-#define _________________WORKMAN_L3________________ CTL_T(KC_Z), KC_X, KC_M, KC_C, KC_V
-
-#define _________________WORKMAN_R1________________ KC_J, KC_F, KC_U, KC_P, KC_SCLN
-#define _________________WORKMAN_R2________________ KC_Y, KC_N, KC_E, KC_O, KC_I
-#define _________________WORKMAN_R3________________ KC_K, KC_L, KC_COMM, KC_DOT, CTL_T(KC_SLASH)
-
-
-#define _________________NORMAN_L1_________________ KC_Q, KC_W, KC_D, KC_F, KC_K
-#define _________________NORMAN_L2_________________ KC_A, KC_S, KC_E, KC_T, KC_G
-#define _________________NORMAN_L3_________________ CTL_T(KC_Z), KC_X, KC_C, KC_V, KC_B
-
-#define _________________NORMAN_R1_________________ KC_J, KC_U, KC_R, KC_L, KC_SCLN
-#define _________________NORMAN_R2_________________ KC_Y, KC_N, KC_I, KC_O, KC_U
-#define _________________NORMAN_R3_________________ KC_P, KC_M, KC_COMM, KC_DOT, CTL_T(KC_SLASH)
-
-
-#define _________________MALTRON_L1________________ KC_Q, KC_P, KC_Y, KC_C, KC_B
-#define _________________MALTRON_L2________________ KC_A, KC_N, KC_I, KC_S, KC_F
-#define _________________MALTRON_L3________________ CTL_T(KC_SCLN), KC_SLSH, KC_J KC_G, KC_COMM
-
-#define _________________MALTRON_R1________________ KC_V, KC_M, KC_U, KC_Z, KC_L
-#define _________________MALTRON_R2________________ KC_D, KC_T, KC_D, KC_O, KC_R
-#define _________________MALTRON_R3________________ KC_DOT, KC_W, KC_K, KC_MINS, CTL_T(KC_x)
-
-
-#define _________________EUCALYN_L1________________ KC_SLSH, KC_COMM, KC_DOT, KC_F, KC_Q
-#define _________________EUCALYN_L2________________ KC_A, KC_O, KC_E, KC_I, KC_U
-#define _________________EUCALYN_L3________________ CTL_T(KC_Z), KC_X, KC_C, KC_V, KC_W
-
-#define _________________EUCALYN_R1________________ KC_M, KC_R, KC_D, KC_Y, KC_P
-#define _________________EUCALYN_R2________________ KC_G, KC_T, KC_K, KC_S, KC_N
-#define _________________EUCALYN_R3________________ KC_B, KC_H, KC_J, KC_L, CTL_T(KC_SCLN)
-
-
-#define _____________CARPLAX_QFMLWY_L1_____________ KC_Q, KC_F, KC_M, KC_L, KC_W
-#define _____________CARPLAX_QFMLWY_L2_____________ KC_D, KC_S, KC_T, KC_N, KC_R
-#define _____________CARPLAX_QFMLWY_L3_____________ CTL_T(KC_Z), KC_V, KC_G, KC_C, KC_X
-
-#define _____________CARPLAX_QFMLWY_R1_____________ KC_Y, KC_U, KC_O, KC_B, KC_J
-#define _____________CARPLAX_QFMLWY_R2_____________ KC_I, KC_A, KC_E, KC_H, KC_SCLN
-#define _____________CARPLAX_QFMLWY_R3_____________ KC_P, KC_K, KC_COMM, KC_DOT, CTL_T(KC_SLSH)
-
-
-#define _____________CARPLAX_QGMLWB_L1_____________ KC_Q, KC_G, KC_M, KC_L, KC_W
-#define _____________CARPLAX_QGMLWB_L2_____________ KC_D, KC_S, KC_T, KC_N, KC_R
-#define _____________CARPLAX_QGMLWB_L3_____________ CTL_T(KC_Z), KC_X, KC_C, KC_F, KC_J
-
-#define _____________CARPLAX_QGMLWB_R1_____________ KC_B, KC_Y, KC_U, KC_V, KC_SCLN
-#define _____________CARPLAX_QGMLWB_R2_____________ KC_I, KC_A, KC_E, KC_O, KC_H
-#define _____________CARPLAX_QGMLWB_R3_____________ KC_K, KC_P, KC_COMM, KC_DOT, CTL_T(KC_SLSH)
-
-
-#define _____________CARPLAX_QGMLWY_L1_____________ KC_Q, KC_G, KC_M, KC_L, KC_W
-#define _____________CARPLAX_QGMLWY_L2_____________ KC_D, KC_S, KC_T, KC_N, KC_R
-#define _____________CARPLAX_QGMLWY_L3_____________ CTL_T(KC_Z), KC_X, KC_C, KC_V, KC_J
-
-#define _____________CARPLAX_QGMLWY_R1_____________ KC_Y, KC_F, KC_U, KC_B, KC_SCLN
-#define _____________CARPLAX_QGMLWY_R2_____________ KC_I, KC_A, KC_E, KC_O, KC_H
-#define _____________CARPLAX_QGMLWY_R3_____________ KC_K, KC_P, KC_COMM, KC_DOT, CTL_T(KC_SLSH)
-
-
-#define ________________NUMBER_LEFT________________ KC_1, KC_2, KC_3, KC_4, KC_5
-#define ________________NUMBER_RIGHT_______________ KC_6, KC_7, KC_8, KC_9, KC_0
-#define _________________FUNC_LEFT_________________ KC_F1, KC_F2, KC_F3, KC_F4, KC_F5
-#define _________________FUNC_RIGHT________________ KC_F6, KC_F7, KC_F8, KC_F9, KC_F10
-
-#define ___________________BLANK___________________ _______, _______, _______, _______, _______
-
-
-#define _________________LOWER_L1__________________ KC_EXLM, KC_AT, KC_HASH, KC_DLR, KC_PERC
-#define _________________LOWER_L2__________________ _________________FUNC_LEFT_________________
-#define _________________LOWER_L3__________________ _________________FUNC_RIGHT________________
-
-#define _________________LOWER_R1__________________ KC_CIRC, KC_AMPR, KC_ASTR, KC_LPRN, KC_RPRN
-#define _________________LOWER_R2__________________ _______, KC_UNDS, KC_PLUS, KC_LCBR, KC_RCBR
-#define _________________LOWER_R3__________________ _______, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT
-
-
-
-#define _________________RAISE_L1__________________ ________________NUMBER_LEFT________________
-#define _________________RAISE_L2__________________ ___________________BLANK___________________
-#define _________________RAISE_L3__________________ ___________________BLANK___________________
-
-#define _________________RAISE_R1__________________ ________________NUMBER_RIGHT_______________
-#define _________________RAISE_R2__________________ _______, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC
-#define _________________RAISE_R3__________________ _______, KC_HOME, KC_PGDN, KC_PGUP, KC_END
-
-
-
-#define _________________ADJUST_L1_________________ RGB_MOD, RGB_HUI, RGB_SAI, RGB_VAI, RGB_TOG
-#define _________________ADJUST_L2_________________ _______, CK_TOGG, AU_ON, AU_OFF, AG_NORM
-#define _________________ADJUST_L3_________________ RGB_RMOD,RGB_HUD,RGB_SAD, RGB_VAD, KC_RGB_T
-
-#define _________________ADJUST_R1_________________ KC_SEC1, KC_SEC2, KC_SEC3, KC_SEC4, KC_SEC5
-#define _________________ADJUST_R2_________________ AG_SWAP, QWERTY, COLEMAK, DVORAK, WORKMAN
-#define _________________ADJUST_R3_________________ MG_NKRO, KC_MUTE, KC_VOLD, KC_VOLU, KC_MNXT
-
-
-// Since we have 4 default layouts (QWERTY, DVORAK, COLEMAK and WORKMAN),
-// this allows us to quickly modify the bottom row for all of the layouts
-// so we don't have to alter it 4 times and hope that we haven't missed
-// anything
-#define ___________ERGODOX_BOTTOM_LEFT_____________ OSM(MOD_MEH), OSM(MOD_LGUI), KC_LBRC, KC_RBRC
-#define ___________ERGODOX_BOTTOM_RIGHT____________ KC_LEFT, KC_DOWN, KC_UP, KC_RGHT
-
-
-#define ___________ORTHODOX_THUMP_TOP_____________ ALT_APP, OS_LGUI, KC_LALT, OS_RGUI
-#define ___________________ORTHODOX_THUMB_BOTTOM____________________ LOWER, KC_SPACE,KC_BSPC, KC_DEL, KC_ENT, RAISE
-
-
-#define __________________ERGODOX_THUMB_CLUSTER_____________________ ALT_T(KC_APP), OSM(MOD_LGUI), OSM(MOD_RGUI), CTL_T(KC_ESCAPE), \
- KC_HOME, KC_PGUP, \
- LT(_LOWER, KC_SPACE),KC_BSPC, KC_END, KC_PGDN, KC_DEL, LT(_RAISE, KC_ENTER)
-
-
-#endif // !USERSPACE
diff --git a/users/drashna/process_records.c b/users/drashna/process_records.c
new file mode 100644
index 0000000000..17d7dc01c5
--- /dev/null
+++ b/users/drashna/process_records.c
@@ -0,0 +1,178 @@
+#include "drashna.h"
+
+uint16_t copy_paste_timer;
+
+__attribute__ ((weak))
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
+__attribute__ ((weak))
+bool process_record_secrets(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
+
+// Defines actions tor my global custom keycodes. Defined in drashna.h file
+// Then runs the _keymap's record handier if not processed here
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+
+ // If console is enabled, it will print the matrix position and status of each key pressed
+#ifdef KEYLOGGER_ENABLE
+ #if defined(KEYBOARD_ergodox_ez) || defined(KEYBOARD_iris_rev2)
+ xprintf("KL: col: %u, row: %u, pressed: %u\n", record->event.key.row, record->event.key.col, record->event.pressed);
+ #else
+ xprintf("KL: col: %u, row: %u, pressed: %u\n", record->event.key.col, record->event.key.row, record->event.pressed);
+ #endif
+#endif //KEYLOGGER_ENABLE
+
+ switch (keycode) {
+ case KC_QWERTY:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(_QWERTY);
+ }
+ break;
+ case KC_COLEMAK:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(_COLEMAK);
+ }
+ break;
+ case KC_DVORAK:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(_DVORAK);
+ }
+ break;
+ case KC_WORKMAN:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(_WORKMAN);
+ }
+ break;
+
+
+ case KC_MAKE: // Compiles the firmware, and adds the flash command based on keyboard bootloader
+ if (!record->event.pressed) {
+ #if !defined(KEYBOARD_viterbi)
+ uint8_t temp_mod = get_mods();
+ uint8_t temp_osm = get_oneshot_mods();
+ clear_mods(); clear_oneshot_mods();
+ #endif
+ send_string_with_delay_P(PSTR("make " QMK_KEYBOARD ":" QMK_KEYMAP), MACRO_TIMER);
+ #if defined(KEYBOARD_viterbi)
+ send_string_with_delay_P(PSTR(":dfu" SS_TAP(X_ENTER)), MACRO_TIMER);
+ #else
+ if (temp_mod & MODS_SHIFT_MASK || temp_osm & MODS_SHIFT_MASK) {
+ #if defined(__arm__)
+ send_string_with_delay_P(PSTR(":dfu-util"), MACRO_TIMER);
+ #elif defined(BOOTLOADER_DFU)
+ send_string_with_delay_P(PSTR(":dfu"), MACRO_TIMER);
+ #elif defined(BOOTLOADER_HALFKAY)
+ send_string_with_delay_P(PSTR(":teensy"), MACRO_TIMER);
+ #elif defined(BOOTLOADER_CATERINA)
+ send_string_with_delay_P(PSTR(":avrdude"), MACRO_TIMER);
+ #endif // bootloader options
+ }
+ if (temp_mod & MODS_CTRL_MASK || temp_osm & MODS_CTRL_MASK) { send_string_with_delay_P(PSTR(" -j8 --output-sync"), MACRO_TIMER); }
+ send_string_with_delay_P(PSTR(SS_TAP(X_ENTER)), MACRO_TIMER);
+ set_mods(temp_mod);
+ #endif
+ }
+ break;
+
+ case VRSN: // Prints firmware version
+ if (record->event.pressed) {
+ send_string_with_delay_P(PSTR(QMK_KEYBOARD "/" QMK_KEYMAP " @ " QMK_VERSION ", Built on: " QMK_BUILDDATE), MACRO_TIMER);
+ }
+ break;
+
+// These are a serious of gaming macros.
+// Only enables for the viterbi, basically,
+// to save on firmware space, since it's limited.
+#ifdef MACROS_ENABLED
+ case KC_OVERWATCH: // Toggle's if we hit "ENTER" or "BACKSPACE" to input macros
+ if (record->event.pressed) { userspace_config.is_overwatch ^= 1; eeconfig_update_user(userspace_config.raw); }
+#ifdef RGBLIGHT_ENABLE
+ userspace_config.is_overwatch ? rgblight_mode_noeeprom(17) : rgblight_mode_noeeprom(18);
+#endif //RGBLIGHT_ENABLE
+ break;
+ case KC_SALT:
+ return send_game_macro("Salt, salt, salt...", record, false);
+ case KC_MORESALT:
+ return send_game_macro("Please sir, can I have some more salt?!", record, false);
+ case KC_SALTHARD:
+ return send_game_macro("Your salt only makes me harder, and even more aggressive!", record, false);
+ case KC_GOODGAME:
+ return send_game_macro("Good game, everyone!", record, false);
+ case KC_GLHF:
+ return send_game_macro("Good luck, have fun!!!", record, false);
+ case KC_SYMM:
+ return send_game_macro("Left click to win!", record, false);
+ case KC_JUSTGAME:
+ return send_game_macro("It may be a game, but if you don't want to actually try, please go play AI, so that people that actually want to take the game seriously and \"get good\" have a place to do so without trolls like you throwing games.", record, false);
+ case KC_TORB:
+ return send_game_macro("That was positively riveting!", record, false);
+ case KC_AIM:
+ send_game_macro("That aim is absolutely amazing. It's almost like you're a machine!", record, true);
+ return send_game_macro("Wait! That aim is TOO good! You're clearly using an aim hack! CHEATER!", record, false);
+ case KC_C9:
+ return send_game_macro("OMG!!! C9!!!", record, false);
+ case KC_GGEZ:
+ return send_game_macro("That was a fantastic game, though it was a bit easy. Try harder next time!", record, false);
+#endif // MACROS_ENABLED
+
+
+ case KC_DIABLO_CLEAR: // reset all Diablo timers, disabling them
+#ifdef TAP_DANCE_ENABLE
+ if (record->event.pressed) {
+ uint8_t dtime;
+ for (dtime = 0; dtime < 4; dtime++) {
+ diablo_key_time[dtime] = diablo_times[0];
+ }
+ }
+#endif // TAP_DANCE_ENABLE
+ break;
+
+
+ case KC_CCCV: // One key copy/paste
+ if(record->event.pressed){
+ copy_paste_timer = timer_read();
+ } else {
+ if (timer_elapsed(copy_paste_timer) > TAPPING_TERM) { // Hold, copy
+ register_code(KC_LCTL);
+ tap_code(KC_C);
+ unregister_code(KC_LCTL);
+ } else { // Tap, paste
+ register_code(KC_LCTL);
+ tap_code(KC_V);
+ unregister_code(KC_LCTL);
+ }
+ }
+ break;
+#ifdef UNICODE_ENABLE
+ case UC_FLIP: // (ノಠ痊ಠ)ノ彡┻━┻
+ if (record->event.pressed) {
+ send_unicode_hex_string("0028 30CE 0CA0 75CA 0CA0 0029 30CE 5F61 253B 2501 253B");
+ }
+ break;
+ case UC_TABL: // ┬─┬ノ( º _ ºノ)
+ if (record->event.pressed) {
+ send_unicode_hex_string("252C 2500 252C 30CE 0028 0020 00BA 0020 005F 0020 00BA 30CE 0029");
+ }
+ break;
+ case UC_SHRG: // ¯\_(ツ)_/¯
+ if (record->event.pressed) {
+ send_unicode_hex_string("00AF 005C 005F 0028 30C4 0029 005F 002F 00AF");
+ }
+ break;
+ case UC_DISA: // ಠ_ಠ
+ if (record->event.pressed) {
+ send_unicode_hex_string("0CA0 005F 0CA0");
+ }
+ break;
+#endif
+ }
+ return process_record_keymap(keycode, record) &&
+#if defined(RGBLIGHT_ENABLE) || defined(RGB_MATRIX_ENABLE)
+ process_record_user_rgb(keycode, record) &&
+#endif // RGBLIGHT_ENABLE
+ process_record_secrets(keycode, record);
+}
diff --git a/users/drashna/process_records.h b/users/drashna/process_records.h
new file mode 100644
index 0000000000..620997addf
--- /dev/null
+++ b/users/drashna/process_records.h
@@ -0,0 +1,101 @@
+#pragma once
+#include "drashna.h"
+
+#if defined(KEYMAP_SAFE_RANGE)
+ #define PLACEHOLDER_SAFE_RANGE KEYMAP_SAFE_RANGE
+#else
+ #define PLACEHOLDER_SAFE_RANGE SAFE_RANGE
+#endif
+
+enum userspace_custom_keycodes {
+ VRSN = PLACEHOLDER_SAFE_RANGE, // Prints QMK Firmware and board info
+ KC_QWERTY, // Sets default layer to QWERTY
+ KC_COLEMAK, // Sets default layer to COLEMAK
+ KC_DVORAK, // Sets default layer to DVORAK
+ KC_WORKMAN, // Sets default layer to WORKMAN
+ KC_DIABLO_CLEAR, // Clears all Diablo Timers
+ KC_OVERWATCH, // Toggles game macro input mode (so in OW, it defaults to game chat)
+ KC_SALT, // See drashna.c for details
+ KC_MORESALT,
+ KC_SALTHARD,
+ KC_GOODGAME,
+ KC_SYMM,
+ KC_JUSTGAME,
+ KC_GLHF,
+ KC_TORB,
+ KC_AIM,
+ KC_C9,
+ KC_GGEZ,
+ KC_MAKE, // Run keyboard's customized make command
+ KC_RGB_T, // Toggles RGB Layer Indication mode
+ KC_SECRET_1, // test1
+ KC_SECRET_2, // test2
+ KC_SECRET_3, // test3
+ KC_SECRET_4, // test4
+ KC_SECRET_5, // test5
+ KC_CCCV, // Hold to copy, tap to paste
+ KC_NUKE, // NUCLEAR LAUNCH DETECTED!!!
+ UC_FLIP, // (ಠ痊ಠ)┻━┻
+ UC_TABL, // ┬─┬ノ( º _ ºノ)
+ UC_SHRG, // ¯\_(ツ)_/¯
+ UC_DISA, // ಠ_ಠ
+ NEW_SAFE_RANGE //use "NEWPLACEHOLDER for keymap specific codes
+};
+
+bool process_record_secrets(uint16_t keycode, keyrecord_t *record);
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record);
+
+
+
+#define LOWER MO(_LOWER)
+#define RAISE MO(_RAISE)
+#define ADJUST MO(_ADJUST)
+#define TG_MODS TG(_MODS)
+#define TG_GAME TG(_GAMEPAD)
+
+#define KC_SEC1 KC_SECRET_1
+#define KC_SEC2 KC_SECRET_2
+#define KC_SEC3 KC_SECRET_3
+#define KC_SEC4 KC_SECRET_4
+#define KC_SEC5 KC_SECRET_5
+
+#define QWERTY KC_QWERTY
+#define DVORAK KC_DVORAK
+#define COLEMAK KC_COLEMAK
+#define WORKMAN KC_WORKMAN
+
+#define KC_RESET RESET
+#define KC_RST KC_RESET
+
+#ifdef SWAP_HANDS_ENABLE
+#define KC_C1R3 SH_TT
+#else // SWAP_HANDS_ENABLE
+#define KC_C1R3 KC_BSPC
+#endif // SWAP_HANDS_ENABLE
+
+#define BK_LWER LT(_LOWER, KC_BSPC)
+#define SP_LWER LT(_LOWER, KC_SPC)
+#define DL_RAIS LT(_RAISE, KC_DEL)
+#define ET_RAIS LT(_RAISE, KC_ENTER)
+
+/* OSM keycodes, to keep things clean and easy to change */
+#define KC_MLSF OSM(MOD_LSFT)
+#define KC_MRSF OSM(MOD_RSFT)
+
+#define OS_LGUI OSM(MOD_LGUI)
+#define OS_RGUI OSM(MOD_RGUI)
+#define OS_LSFT OSM(MOD_LSFT)
+#define OS_RSFT OSM(MOD_RSFT)
+#define OS_LCTL OSM(MOD_LCTL)
+#define OS_RCTL OSM(MOD_RCTL)
+#define OS_LALT OSM(MOD_LALT)
+#define OS_RALT OSM(MOD_RALT)
+#define OS_MEH OSM(MOD_MEH)
+#define OS_HYPR OSM(MOD_HYPR)
+
+#define ALT_APP ALT_T(KC_APP)
+
+#define MG_NKRO MAGIC_TOGGLE_NKRO
+
+#define UC_IRNY UC(0x2E2E)
+#define UC_CLUE UC(0x203D)
diff --git a/users/drashna/readme.md b/users/drashna/readme.md
index 179960322a..ffc60060f4 100644
--- a/users/drashna/readme.md
+++ b/users/drashna/readme.md
@@ -1,11 +1,8 @@
-Overview
-========
+# Overview
-This is my personal userspace file. Most of my code exists here, as it's heavily shared.
+This is my personal userspace file. Most of my code exists here, as it's heavily shared.
-
-Custom userspace handlers
--------------------------
+## Custom userspace handlers
Specifically QMK works by using customized handlers for everything. This allows for multiple levels of customization.
@@ -15,29 +12,26 @@ The same goes for `matrix_init`, `layer_state_set`, `led_set`, and a few other f
All (most) `_user` functions are handled here instead. To allow keyboard specific configuration, I've created `_keymap` functions that can be called by the keymap.c files instead.
-This allows for keyboard specific configuration while maintaining the ability to customize the board.
-
-My [Ergodox EZ Keymap](https://github.com/qmk/qmk_firmware/blob/master/keyboards/ergodox_ez/keymaps/drashna/keymap.c#L399) is a good example of this, as it uses the LEDs as modifier indicators.
+This allows for keyboard specific configuration while maintaining the ability to customize the board.
+My [Ergodox EZ Keymap](https://github.com/qmk/qmk_firmware/blob/master/layouts/community/ergodox/drashna/keymap.c#L297) is a good example of this, as it uses the LEDs as modifier indicators.
-Keyboard Layout Templates
--------------------------
+## Keyboard Layout Templates
-This borrows from @jola5's "Not quite neo" code. This allows me to maintain blocks of keymaps in the userspace, so that I can modify the userspace, and this is reflected in all of the keyboards that use it, at once.
+This borrows from @jola5's "Not quite neo" code. This allows me to maintain blocks of keymaps in the userspace, so that I can modify the userspace, and this is reflected in all of the keyboards that use it, at once.
This makes adding tap/hold mods, or other special keycodes or functions to all keyboards super easy, as it's done to all of them at once.
-The caveat here is that the keymap needs a processor/wrapper, as it doesn't like the substitutions. However, this is as simple as just pushing it through a define. For instance:
+The caveat here is that the keymap needs a processor/wrapper, as it doesn't like the substitutions. However, this is as simple as just pushing it through a define. For instance:
`#define LAYOUT_ergodox_wrapper(...) LAYOUT_ergodox(__VA_ARGS__)`
-Once that's been done and you've switched the keymaps to use the "wrapper", it will read the substitution blocks just fine.
+Once that's been done and you've switched the keymaps to use the "wrapper", it will read the substitution blocks just fine.
Credit goes to @jola5 for first implementing this awesome idea.
-Custom Keycodes
----------------
+## Custom Keycodes
Keycodes are defined in the drashna.h file and need to be included in the keymap.c files, so that they can be used there.
@@ -45,10 +39,9 @@ A bunch of macros are present and are only included on boards that are not the E
Included is a custom macro for compiling my keyboards. This includes the bootloader target (`:teensy`, `:avrdude`, or `:dfu`), and keeps RGBLIGHT, AUDIO and/or FAUXCLICKY enabled, if it previously was (regardless of the rules file).
-This also includes a modified RESET keycode as well, that sets the underglow to red.
+This also includes a modified RESET keycode as well, that sets the underglow to red.
-Layer Indication
-----------------
+## Layer Indication
This uses the `layer_state_set_*` command to change the layer color, to indicate which layer it is on. This includes the default keymap, as well.
@@ -58,9 +51,7 @@ Additionally, there is a custom keycode to toggle layer indication. And all RGB
Also. I use `rgblight_sethsv` since it works with animation modes (that support it).
-
-Diablo Layer
-------------
+## Diablo Layer
This layer has some special handling.
@@ -72,8 +63,7 @@ Tappind once disables this, and switching layers temporarily disables this, unti
For critics that think this is cheating, search "diablo 3 num lock auto cast". This is just a simpler method, since I no longer own a normal (non QMK) numpad.
-Secret Macros
--------------
+## Secret Macros
With help from gitter and Colinta, this adds the ability to add hidden macros from other users.
@@ -82,7 +72,8 @@ First, I have several files that are hidden/excluded from Git/GitHub. These con
And this requires `KC_SECRET_1` through `KC_SECRET_5` to be defined in your `<name>.h` file to define the keycodes for the new macros.
-###### .git/info/exclude
+### .git/info/exclude
+
```
# git ls-files --others --exclude-from=.git/info/exclude
# Lines that start with '#' are comments.
@@ -96,7 +87,7 @@ And this requires `KC_SECRET_1` through `KC_SECRET_5` to be defined in your `<na
Then you can create these files:
-###### secrets.c
+### secrets.c
```c
#include "drashna.h" // replace with your keymap's "h" file, or whatever file stores the keycodes
@@ -129,7 +120,8 @@ bool process_record_secrets(uint16_t keycode, keyrecord_t *record) {
}
```
-###### secrets.h
+### secrets.h
+
```c
static const char * const secrets[] = {
"secret1",
@@ -142,9 +134,9 @@ static const char * const secrets[] = {
Replacing the strings with the codes that you need.
-###### name.c
+### name.c
-In the `<name>.c` file, you will want to add this to the top:
+In the `<name>.c` file, you will want to add this to the top:
```c
__attribute__ ((weak))
@@ -152,64 +144,37 @@ bool process_record_secrets(uint16_t keycode, keyrecord_t *record) {
return true;
}
```
-This is so that the function can be called here, and replaced in the `secrets.c` file, and so it won't error out if it doesn't exist.
+This is so that the function can be called here, and replaced in the `secrets.c` file, and so it won't error out if it doesn't exist.
And then, in the `process_record_user` function, assuming you have `return process_record_keymap(keycode, record)` here, you'll want to replace the "final" return with the following. Otherwise, you want to replace the `return true;` with `return process_record_secrets(keycode, record);`
+
```c
return process_record_keymap(keycode, record) && process_record_secrets(keycode, record);
}
```
-###### rules.mk
+### rules.mk
-Here, you want your `/users/<name>/rules.mk` file to "detect" the existence of the `secrets.c` file, and only add it if the file exists. To do so, add this block:
-```c
+Here, you want your `/users/<name>/rules.mk` file to "detect" the existence of the `secrets.c` file, and only add it if the file exists. To do so, add this block:
+
+```make
ifneq ("$(wildcard $(USER_PATH)/secrets.c)","")
SRC += secrets.c
endif
```
Additionally, if you want to make sure that you can disable the function without messing with the file, you need to add this to your `/users/<name>/rules.mk`, so that it catches the flag:
-```c
+
+```make
ifeq ($(strip $(NO_SECRETS)), yes)
OPT_DEFS += -DNO_SECRETS
endif
```
-Then, if you run `make keyboard:name NO_SECRETS=yes`, it will default to the test strings in your `<name>.c` file, rather than reading from your file.
-
-
-Userspace EEPROM config
------------------------
-
-This adds EEPROM support fo the userspace, so that certain values are configurable in such a way that persists when power is lost. Namely, just the clicky feature and the Overwatch macro option ("is_overwatch"). This is done by reading and saving the structure from EEPROM.
-
-To implement this, first you need to specify the location:
-
-```c
-#define EECONFIG_USERSPACE (uint8_t *)20
-```
-This tells us where in the EEPROM that the data structure is located, and this specifies that it's a byte (8 bits). However, to maximize it's usage, we want to specify a data structure here, so that we can use multiple settings. To do that:
-
-```c
-typedef union {
- uint8_t raw;
- struct {
- bool clicky_enable :1;
- bool is_overwatch :1;
- };
-} userspace_config_t;
-```
-Then, in your C file, you want to add: `userspace_config_t userspace_config;`, and in your `matrix_init_*` function, you want to add `userspace_config.raw = eeprom_read_byte(EECONFIG_USERSPACE);`
-
-From there, you'd want to use the data structure (such as `userspace_config.is_overwatch`) when you want to check this value.
-
-And if you want to update it, update directly and then use `eeprom_update_byte(EECONFIG_USERSPACE, userspace_config.raw);` to write the value back to the EEPROM.
-
+Then, if you run `make keyboard:name NO_SECRETS=yes`, it will default to the test strings in your `<name>.c` file, rather than reading from your file.
-Pro Micro Hacking
------------------
+## Pro Micro Hacking
Well, you can get the QMK DFU bootloader working on the ProMicro. But you need to change fuses.
diff --git a/users/drashna/rgb_stuff.c b/users/drashna/rgb_stuff.c
index f2a9a47a90..7d00604b4e 100644
--- a/users/drashna/rgb_stuff.c
+++ b/users/drashna/rgb_stuff.c
@@ -2,8 +2,11 @@
#include "rgb_stuff.h"
#include "eeprom.h"
+#if defined(RGBLIGHT_ENABLE)
extern rgblight_config_t rgblight_config;
-extern userspace_config_t userspace_config;
+#elif defined(RGB_MATRIX_ENABLE)
+extern rgb_config_t rgb_matrix_config;
+#endif
#ifdef RGBLIGHT_ENABLE
void rgblight_sethsv_default_helper(uint8_t index) {
@@ -12,14 +15,6 @@ void rgblight_sethsv_default_helper(uint8_t index) {
#endif // RGBLIGHT_ENABLE
#ifdef INDICATOR_LIGHTS
-uint8_t last_mod;
-uint8_t last_led;
-uint8_t last_osm;
-uint8_t current_mod;
-uint8_t current_led;
-uint8_t current_osm;
-
-
void set_rgb_indicators(uint8_t this_mod, uint8_t this_led, uint8_t this_osm) {
if (userspace_config.rgb_layer_change && biton32(layer_state) == 0) {
if (this_mod & MODS_SHIFT_MASK || this_led & (1<<USB_LED_CAPS_LOCK) || this_osm & MODS_SHIFT_MASK) {
@@ -86,16 +81,7 @@ void set_rgb_indicators(uint8_t this_mod, uint8_t this_led, uint8_t this_osm) {
}
void matrix_scan_indicator(void) {
- current_mod = get_mods();
- current_led = host_keyboard_leds();
- current_osm = get_oneshot_mods();
-
- set_rgb_indicators(current_mod, current_led, current_osm);
-
- last_mod = current_mod;
- last_led = current_led;
- last_osm = current_osm;
-
+ set_rgb_indicators(get_mods(), host_keyboard_leds(), get_oneshot_mods());
}
#endif //INDICATOR_LIGHTS
@@ -214,7 +200,10 @@ void start_rgb_light(void) {
bool process_record_user_rgb(uint16_t keycode, keyrecord_t *record) {
- switch (keycode) {
+ if ((keycode >= QK_MOD_TAP && keycode <= QK_MOD_TAP_MAX) || (keycode >= QK_LAYER_TAP && keycode <= QK_LAYER_TAP_MAX)) {
+ keycode = keycode & 0xFF;
+ }
+ switch (keycode) {
#ifdef RGBLIGHT_TWINKLE
case KC_A ... KC_SLASH:
case KC_F1 ... KC_F12:
@@ -226,11 +215,11 @@ bool process_record_user_rgb(uint16_t keycode, keyrecord_t *record) {
return true; break;
#endif // RGBLIGHT_TWINKLE
case KC_RGB_T: // This allows me to use underglow as layer indication, or as normal
-#ifdef RGBLIGHT_ENABLE
+#if defined(RGBLIGHT_ENABLE) || defined(RGB_MATRIX_ENABLE)
if (record->event.pressed) {
userspace_config.rgb_layer_change ^= 1;
xprintf("rgblight layer change [EEPROM]: %u\n", userspace_config.rgb_layer_change);
- eeprom_update_byte(EECONFIG_USERSPACE, userspace_config.raw);
+ eeconfig_update_user(userspace_config.raw);
if (userspace_config.rgb_layer_change) {
layer_state_set(layer_state); // This is needed to immediately set the layer color (looks better)
}
@@ -243,7 +232,7 @@ bool process_record_user_rgb(uint16_t keycode, keyrecord_t *record) {
if (userspace_config.rgb_layer_change) {
userspace_config.rgb_layer_change = false;
xprintf("rgblight layer change [EEPROM]: %u\n", userspace_config.rgb_layer_change);
- eeprom_update_byte(EECONFIG_USERSPACE, userspace_config.raw);
+ eeconfig_update_user(userspace_config.raw);
}
}
return true; break;
@@ -254,27 +243,25 @@ bool process_record_user_rgb(uint16_t keycode, keyrecord_t *record) {
-void matrix_init_rgb(void) {
-#ifdef INDICATOR_LIGHTS
- current_mod = last_mod = get_mods();
- current_led = last_led = host_keyboard_leds();
- current_osm = last_osm = get_oneshot_mods();
-#endif
+ void matrix_init_rgb(void) {
- if (userspace_config.rgb_layer_change) {
- rgblight_enable_noeeprom();
- switch (biton32(eeconfig_read_default_layer())) {
- case _COLEMAK:
- rgblight_sethsv_noeeprom_magenta(); break;
- case _DVORAK:
- rgblight_sethsv_noeeprom_green(); break;
- case _WORKMAN:
- rgblight_sethsv_noeeprom_goldenrod(); break;
- default:
- rgblight_sethsv_noeeprom_cyan(); break;
- }
- }
-}
+// #ifdef RGBLIGHT_ENABLE
+// if (userspace_config.rgb_layer_change) {
+// rgblight_enable_noeeprom();
+// switch (biton32(eeconfig_read_default_layer())) {
+// case _COLEMAK:
+// rgblight_sethsv_noeeprom_magenta(); break;
+// case _DVORAK:
+// rgblight_sethsv_noeeprom_springgreen(); break;
+// case _WORKMAN:
+// rgblight_sethsv_noeeprom_goldenrod(); break;
+// default:
+// rgblight_sethsv_noeeprom_cyan(); break;
+// }
+// rgblight_mode(RGBLIGHT_MODE_STATIC_LIGHT);
+// }
+// #endif
+ }
void matrix_scan_rgb(void) {
#ifdef RGBLIGHT_TWINKLE
@@ -294,44 +281,44 @@ uint32_t layer_state_set_rgb(uint32_t state) {
switch (biton32(state)) {
case _MACROS:
rgblight_sethsv_noeeprom_orange();
- userspace_config.is_overwatch ? rgblight_mode_noeeprom(17) : rgblight_mode_noeeprom(18);
+ userspace_config.is_overwatch ? rgblight_effect_snake(RGBLIGHT_MODE_SNAKE + 2) : rgblight_effect_snake(RGBLIGHT_MODE_SNAKE + 3);
break;
case _MEDIA:
rgblight_sethsv_noeeprom_chartreuse();
- rgblight_mode_noeeprom(22);
+ rgblight_mode_noeeprom(RGBLIGHT_MODE_KNIGHT + 1);
break;
case _GAMEPAD:
rgblight_sethsv_noeeprom_orange();
- rgblight_mode_noeeprom(17);
+ rgblight_mode_noeeprom(RGBLIGHT_MODE_SNAKE + 2);
break;
case _DIABLO:
rgblight_sethsv_noeeprom_red();
- rgblight_mode_noeeprom(5);
+ rgblight_mode_noeeprom(RGBLIGHT_MODE_BREATHING + 3);
break;
case _RAISE:
rgblight_sethsv_noeeprom_yellow();
- rgblight_mode_noeeprom(5);
+ rgblight_mode_noeeprom(RGBLIGHT_MODE_BREATHING + 3);
break;
case _LOWER:
- rgblight_sethsv_noeeprom_orange();
- rgblight_mode_noeeprom(5);
+ rgblight_sethsv_noeeprom_green();
+ rgblight_mode_noeeprom(RGBLIGHT_MODE_BREATHING + 3);
break;
case _ADJUST:
rgblight_sethsv_noeeprom_red();
- rgblight_mode_noeeprom(23);
+ rgblight_mode_noeeprom(RGBLIGHT_MODE_KNIGHT + 2);
break;
default: // for any other layers, or the default layer
switch (biton32(default_layer_state)) {
case _COLEMAK:
rgblight_sethsv_noeeprom_magenta(); break;
case _DVORAK:
- rgblight_sethsv_noeeprom_green(); break;
+ rgblight_sethsv_noeeprom_springgreen(); break;
case _WORKMAN:
rgblight_sethsv_noeeprom_goldenrod(); break;
default:
rgblight_sethsv_noeeprom_cyan(); break;
}
- biton32(state) == _MODS ? rgblight_mode_noeeprom(2) : rgblight_mode_noeeprom(1); // if _MODS layer is on, then breath to denote it
+ biton32(state) == _MODS ? rgblight_mode_noeeprom(RGBLIGHT_MODE_BREATHING) : rgblight_mode_noeeprom(RGBLIGHT_MODE_STATIC_LIGHT); // if _MODS layer is on, then breath to denote it
break;
}
// layer_state_set_indicator(); // Runs every scan, so need to call this here .... since I can't get it working "right" anyhow
@@ -341,4 +328,38 @@ uint32_t layer_state_set_rgb(uint32_t state) {
return state;
}
-
+uint32_t default_layer_state_set_rgb(uint32_t state) {
+#ifdef RGBLIGHT_ENABLE
+ if (userspace_config.rgb_layer_change) {
+ rgblight_config_t temp_rgblight_config = rgblight_config;
+ switch (biton32(state)) {
+ case _COLEMAK:
+ temp_rgblight_config.hue = 300;
+ temp_rgblight_config.val = 255;
+ temp_rgblight_config.sat = 255;
+ temp_rgblight_config.mode = 1;
+ break;
+ case _DVORAK:
+ temp_rgblight_config.hue = 150;
+ temp_rgblight_config.val = 255;
+ temp_rgblight_config.sat = 255;
+ temp_rgblight_config.mode = 1;
+ case _WORKMAN:
+ temp_rgblight_config.hue = 43;
+ temp_rgblight_config.val = 218;
+ temp_rgblight_config.sat = 218;
+ temp_rgblight_config.mode = 1;
+ default:
+ temp_rgblight_config.hue = 180;
+ temp_rgblight_config.val = 255;
+ temp_rgblight_config.sat = 255;
+ temp_rgblight_config.mode = 1;
+ }
+ if (temp_rgblight_config.raw != eeconfig_read_rgblight()) {
+ xprintf("rgblight set default layer hsv [EEPROM]: %u,%u,%u,%u\n", temp_rgblight_config.hue, temp_rgblight_config.sat, temp_rgblight_config.val, temp_rgblight_config.mode);
+ eeconfig_update_rgblight(temp_rgblight_config.raw);
+ }
+ }
+#endif // RGBLIGHT_ENABLE
+ return state;
+}
diff --git a/users/drashna/rgb_stuff.h b/users/drashna/rgb_stuff.h
index 6426ea266f..065bda9f9e 100644
--- a/users/drashna/rgb_stuff.h
+++ b/users/drashna/rgb_stuff.h
@@ -1,4 +1,8 @@
+#pragma once
#include "quantum.h"
+#ifdef RGB_MATRIX_ENABLE
+ #include "rgb_matrix.h"
+#endif
typedef struct {
bool enabled;
@@ -12,5 +16,6 @@ void scan_rgblight_fadeout(void);
void matrix_init_rgb(void);
void matrix_scan_rgb(void);
uint32_t layer_state_set_rgb(uint32_t state);
-
-
+uint32_t default_layer_state_set_rgb(uint32_t state);
+void rgblight_sethsv_default_helper(uint8_t index);
+void rgb_matrix_set_color_all( uint8_t red, uint8_t green, uint8_t blue );
diff --git a/users/drashna/rules.mk b/users/drashna/rules.mk
index e299f24a1e..6d8612e71a 100644
--- a/users/drashna/rules.mk
+++ b/users/drashna/rules.mk
@@ -1,5 +1,5 @@
-
-SRC += drashna.c
+SRC += drashna.c \
+ process_records.c
ifneq ("$(wildcard $(USER_PATH)/secrets.c)","")
SRC += secrets.c
@@ -9,7 +9,7 @@ ifeq ($(strip $(TAP_DANCE_ENABLE)), yes)
SRC += tap_dances.c
endif
-EXTRAFLAGS += -flto
+EXTRAFLAGS += -flto
ifeq ($(strip $(NO_SECRETS)), yes)
OPT_DEFS += -DNO_SECRETS
@@ -28,6 +28,11 @@ ifeq ($(strip $(RGBLIGHT_ENABLE)), yes)
endif
endif
+ifeq ($(strip $(RGB_MATRIX_ENABLE)), yes)
+ SRC += rgb_stuff.c
+endif
+
+
ifeq ($(strip $(MACROS_ENABLED)), yes)
OPT_DEFS += -DMACROS_ENABLED
endif
diff --git a/users/drashna/send_unicode.h b/users/drashna/send_unicode.h
new file mode 100644
index 0000000000..818b6e571b
--- /dev/null
+++ b/users/drashna/send_unicode.h
@@ -0,0 +1,71 @@
+#pragma once
+
+#include "quantum.h"
+
+void send_unicode_hex_string(const char* str);
+
+/* use X(n) to call the */
+#ifdef UNICODEMAP_ENABLE
+enum unicode_name {
+ THINK, // thinking face 🤔
+ GRIN, // grinning face 😊
+ SMRK, // smirk 😏
+ WEARY, // good shit 😩
+ UNAMU, // unamused 😒
+
+ SNEK, // snke 🐍
+ PENGUIN, // 🐧
+ DRAGON, // 🐉
+ MONKEY, // 🐒
+ CHICK, // 🐥
+ BOAR, // 🐗
+
+ OKOK, // 👌
+ EFFU, // 🖕
+ INUP, // 👆
+ THUP, // 👍
+ THDN, // 👎
+
+ BBB, // dat B 🅱
+ POO, // poop 💩
+ HUNDR, // 100 💯
+ EGGPL, // EGGPLANT 🍆
+ WATER, // wet 💦
+ TUMBLER, // 🥃
+
+ LIT, // fire 🔥
+ BANG, // ‽
+ IRONY, // ⸮
+ DEGREE // °
+};
+
+
+const uint32_t PROGMEM unicode_map[] = {
+ [THINK] = 0x1F914,
+ [GRIN] = 0x1F600,
+ [BBB] = 0x1F171,
+ [POO] = 0x1F4A9,
+ [HUNDR] = 0x1F4AF,
+ [SMRK] = 0x1F60F,
+ [WEARY] = 0x1F629,
+ [EGGPL] = 0x1F346,
+ [WATER] = 0x1F4A6,
+ [LIT] = 0x1F525,
+ [UNAMU] = 0x1F612,
+ [SNEK] = 0x1F40D,
+ [PENGUIN] = 0x1F427,
+ [BOAR] = 0x1F417,
+ [MONKEY] = 0x1F412,
+ [CHICK] = 0x1F425,
+ [DRAGON] = 0x1F409,
+ [OKOK] = 0x1F44C,
+ [EFFU] = 0x1F595,
+ [INUP] = 0x1F446,
+ [THDN] = 0x1F44E,
+ [THUP] = 0x1F44D,
+ [TUMBLER] = 0x1F943,
+ [BANG] = 0x0203D,
+ [IRONY] = 0x02E2E,
+ [DEGREE] = 0x000B0
+ };
+#endif // UNICODEMAP_ENABLE
diff --git a/users/drashna/tap_dances.c b/users/drashna/tap_dances.c
index c9e4b1d0ff..cbb3cf54ef 100644
--- a/users/drashna/tap_dances.c
+++ b/users/drashna/tap_dances.c
@@ -1,4 +1,3 @@
-#include "drashna.h"
#include "tap_dances.h"
@@ -38,16 +37,16 @@ qk_tap_dance_action_t tap_dance_actions[] = {
// Sends the key press to system, but only if on the Diablo layer
void send_diablo_keystroke(uint8_t diablo_key) {
- if (biton32(layer_state) == _DIABLO) {
+ if (IS_LAYER_ON(_DIABLO)) {
switch (diablo_key) {
case 0:
- tap(KC_1); break;
+ tap_code(KC_1); break;
case 1:
- tap(KC_2); break;
+ tap_code(KC_2); break;
case 2:
- tap(KC_3); break;
+ tap_code(KC_3); break;
case 3:
- tap(KC_4); break;
+ tap_code(KC_4); break;
}
}
}
diff --git a/users/drashna/tap_dances.h b/users/drashna/tap_dances.h
index 8935753f6c..41d2bacb7b 100644
--- a/users/drashna/tap_dances.h
+++ b/users/drashna/tap_dances.h
@@ -1,3 +1,6 @@
+#pragma once
+#include "drashna.h"
+
//define diablo macro timer variables
extern uint16_t diablo_timer[4];
extern uint8_t diablo_times[];
@@ -5,3 +8,12 @@ extern uint8_t diablo_key_time[4];
void run_diablo_macro_check(void);
+
+#ifdef TAP_DANCE_ENABLE
+enum {
+ TD_D3_1 = 0,
+ TD_D3_2,
+ TD_D3_3,
+ TD_D3_4
+};
+#endif // TAP_DANCE_ENABLE
diff --git a/users/drashna/template.c b/users/drashna/template.c
index 20dbb96d7f..0e188f3a5e 100644
--- a/users/drashna/template.c
+++ b/users/drashna/template.c
@@ -1,7 +1,5 @@
-#include "drashna.h"
-#include "quantum.h"
-#include "action.h"
-#include "version.h"
+#include "template.h"
+
// Add reconfigurable functions here, for keymap customization
// This allows for a global, userspace functions, and continued
@@ -10,25 +8,15 @@
__attribute__ ((weak))
void matrix_init_keymap(void) {}
-__attribute__ ((weak))
-void matrix_scan_keymap(void) {}
-
-__attribute__ ((weak))
-bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
- return true;
-}
-__attribute__ ((weak))
-uint32_t layer_state_set_keymap (uint32_t state) {
- return state;
-}
-__attribute__ ((weak))
-void led_set_keymap(uint8_t usb_led) {}
-
// Call user matrix init, then call the keymap's init function
void matrix_init_user(void) {
matrix_init_keymap();
}
+
+__attribute__ ((weak))
+void matrix_scan_keymap(void) {}
+
// No global matrix scan code, so just run keymap's matix
// scan function
void matrix_scan_user(void) {
@@ -36,11 +24,16 @@ void matrix_scan_user(void) {
}
+__attribute__ ((weak))
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
// Defines actions tor my global custom keycodes. Defined in drashna.h file
// Then runs the _keymap's recod handier if not processed here,
// And use "NEWPLACEHOLDER" for new safe range
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
-
+
switch (keycode) {
case KC_MAKE:
if (!record->event.pressed) {
@@ -56,18 +49,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
}
return false;
break;
- case KC_RESET:
- if (!record->event.pressed) {
- reset_keyboard();
- }
- return false;
- break;
- case EPRM:
- if (record->event.pressed) {
- eeconfig_init();
- }
- return false;
- break;
+
case VRSN:
if (record->event.pressed) {
SEND_STRING(QMK_KEYBOARD "/" QMK_KEYMAP " @ " QMK_VERSION);
@@ -78,13 +60,65 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
return process_record_keymap(keycode, record);
}
-// Runs state check and changes underglow color and animation
-// on layer change, no matter where the change was initiated
-// Then runs keymap's layer change check
+
+__attribute__ ((weak))
+uint32_t layer_state_set_keymap (uint32_t state) {
+ return state;
+}
+
uint32_t layer_state_set_user (uint32_t state) {
return layer_state_set_keymap (state);
}
+
+
+__attribute__ ((weak))
+void led_set_keymap(uint8_t usb_led) {}
+
void led_set_user(uint8_t usb_led) {
led_set_keymap(usb_led);
}
+
+
+
+__attribute__ ((weak))
+void suspend_power_down_keymap(void) {}
+
+void suspend_power_down_user(void)
+{
+ suspend_power_down_keymap();
+}
+
+
+
+__attribute__ ((weak))
+void suspend_wakeup_init_keymap(void) {}
+
+void suspend_wakeup_init_user(void)
+{
+ suspend_wakeup_init_keymap();
+ #ifdef KEYBOARD_ergodox_ez
+ wait_ms(10);
+ #endif
+}
+
+
+
+__attribute__ ((weak))
+void startup_keymap(void) {}
+
+void startup_user (void) {
+ #ifdef RGBLIGHT_ENABLE
+ matrix_init_rgb();
+ #endif //RGBLIGHT_ENABLE
+ startup_keymap();
+}
+
+
+
+__attribute__ ((weak))
+void shutdown_keymap(void) {}
+
+void shutdown_user (void) {
+ shutdown_keymap();
+}
diff --git a/users/drashna/template.h b/users/drashna/template.h
index d1251462b2..dd1c487604 100644
--- a/users/drashna/template.h
+++ b/users/drashna/template.h
@@ -2,14 +2,14 @@
#define USERSPACE
#include "quantum.h"
+#include "version.h"
+#include "eeprom.h"
-// Define layer names
+// Define layer names
#define BASE 0
enum custom_keycodes {
- PLACEHOLDER = SAFE_RANGE, // can always be here
- EPRM,
- VRSN,
+ VRSN = SAFE_RANGE, // can always be here
KC_MAKE,
KC_RESET,
NEWPLACEHOLDER //use "NEWPLACEHOLDER for keymap specific codes
diff --git a/users/drashna/wrappers.h b/users/drashna/wrappers.h
new file mode 100644
index 0000000000..070a5a0a4a
--- /dev/null
+++ b/users/drashna/wrappers.h
@@ -0,0 +1,171 @@
+#pragma once
+#include "drashna.h"
+/*
+Since our quirky block definitions are basically a list of comma separated
+arguments, we need a wrapper in order for these definitions to be
+expanded before being used as arguments to the LAYOUT_xxx macro.
+*/
+#if (!defined(LAYOUT) && defined(KEYMAP))
+#define LAYOUT KEYMAP
+#endif
+
+#define LAYOUT_ergodox_wrapper(...) LAYOUT_ergodox(__VA_ARGS__)
+#define LAYOUT_ergodox_pretty_wrapper(...) LAYOUT_ergodox_pretty(__VA_ARGS__)
+#define KEYMAP_wrapper(...) LAYOUT(__VA_ARGS__)
+#define LAYOUT_wrapper(...) LAYOUT(__VA_ARGS__)
+#define LAYOUT_ortho_4x12_wrapper(...) LAYOUT_ortho_4x12(__VA_ARGS__)
+#define LAYOUT_ortho_5x12_wrapper(...) LAYOUT_ortho_5x12(__VA_ARGS__)
+
+/*
+Blocks for each of the four major keyboard layouts
+Organized so we can quickly adapt and modify all of them
+at once, rather than for each keyboard, one at a time.
+And this allows for much cleaner blocks in the keymaps.
+For instance Tap/Hold for Control on all of the layouts
+
+NOTE: These are all the same length. If you do a search/replace
+ then you need to add/remove underscores to keep the
+ lengths consistent.
+*/
+
+#define _________________QWERTY_L1_________________ KC_Q, KC_W, KC_E, KC_R, KC_T
+#define _________________QWERTY_L2_________________ KC_A, KC_S, KC_D, KC_F, KC_G
+#define _________________QWERTY_L3_________________ KC_Z, KC_X, KC_C, KC_V, KC_B
+
+#define _________________QWERTY_R1_________________ KC_Y, KC_U, KC_I, KC_O, KC_P
+#define _________________QWERTY_R2_________________ KC_H, KC_J, KC_K, KC_L, KC_SCLN
+#define _________________QWERTY_R3_________________ KC_N, KC_M, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define _________________COLEMAK_L1________________ KC_Q, KC_W, KC_F, KC_P, KC_G
+#define _________________COLEMAK_L2________________ KC_A, KC_R, KC_S, KC_T, KC_D
+#define _________________COLEMAK_L3________________ KC_Z, KC_X, KC_C, KC_V, KC_B
+
+#define _________________COLEMAK_R1________________ KC_J, KC_L, KC_U, KC_Y, KC_SCLN
+#define _________________COLEMAK_R2________________ KC_H, KC_N, KC_E, KC_I, KC_O
+#define _________________COLEMAK_R3________________ KC_K, KC_M, KC_COMM, KC_DOT, KC_SLASH
+
+#define ______________COLEMAK_MOD_DH_L1____________ KC_Q, KC_W, KC_F, KC_P, KC_B
+#define ______________COLEMAK_MOD_DH_L2____________ KC_A, KC_R, KC_S, KC_T, KC_G
+#define ______________COLEMAK_MOD_DH_L3____________ KC_Z, KC_X, KC_C, KC_D, KC_V
+
+#define ______________COLEMAK_MOD_DH_R1____________ KC_J, KC_L, KC_U, KC_Y, KC_SCLN
+#define ______________COLEMAK_MOD_DH_R2____________ KC_M, KC_N, KC_E, KC_I, KC_O
+#define ______________COLEMAK_MOD_DH_R3____________ KC_K, KC_H, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define _________________DVORAK_L1_________________ KC_QUOT, KC_COMM, KC_DOT, KC_P, KC_Y
+#define _________________DVORAK_L2_________________ KC_A, KC_O, KC_E, KC_U, KC_I
+#define _________________DVORAK_L3_________________ KC_SCLN, KC_Q, KC_J, KC_K, KC_X
+
+#define _________________DVORAK_R1_________________ KC_F, KC_G, KC_C, KC_R, KC_L
+#define _________________DVORAK_R2_________________ KC_D, KC_H, KC_T, KC_N, KC_S
+#define _________________DVORAK_R3_________________ KC_B, KC_M, KC_W, KC_V, KC_Z
+
+
+#define ________________DVORAK_AU_L1_______________ KC_QUOT, KC_COMM, KC_DOT, KC_P, KC_Y
+#define ________________DVORAK_AU_L2_______________ KC_O, KC_A, KC_E, KC_I, KC_U
+#define ________________DVORAK_AU_L3_______________ KC_SCLN, KC_Q, KC_J, KC_K, KC_X
+
+#define ________________DVORAK_AU_R1_______________ KC_F, KC_G, KC_C, KC_R, KC_L
+#define ________________DVORAK_AU_R2_______________ KC_D, KC_H, KC_T, KC_N, KC_S
+#define ________________DVORAK_AU_R3_______________ KC_B, KC_M, KC_W, KC_V, KC_Z
+
+#define _________________WORKMAN_L1________________ KC_Q, KC_D, KC_R, KC_W, KC_B
+#define _________________WORKMAN_L2________________ KC_A, KC_S, KC_H, KC_T, KC_G
+#define _________________WORKMAN_L3________________ KC_Z, KC_X, KC_M, KC_C, KC_V
+
+#define _________________WORKMAN_R1________________ KC_J, KC_F, KC_U, KC_P, KC_SCLN
+#define _________________WORKMAN_R2________________ KC_Y, KC_N, KC_E, KC_O, KC_I
+#define _________________WORKMAN_R3________________ KC_K, KC_L, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define _________________NORMAN_L1_________________ KC_Q, KC_W, KC_D, KC_F, KC_K
+#define _________________NORMAN_L2_________________ KC_A, KC_S, KC_E, KC_T, KC_G
+#define _________________NORMAN_L3_________________ KC_Z, KC_X, KC_C, KC_V, KC_B
+
+#define _________________NORMAN_R1_________________ KC_J, KC_U, KC_R, KC_L, KC_SCLN
+#define _________________NORMAN_R2_________________ KC_Y, KC_N, KC_I, KC_O, KC_U
+#define _________________NORMAN_R3_________________ KC_P, KC_M, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define _________________MALTRON_L1________________ KC_Q, KC_P, KC_Y, KC_C, KC_B
+#define _________________MALTRON_L2________________ KC_A, KC_N, KC_I, KC_S, KC_F
+#define _________________MALTRON_L3________________ KC_SCLN, KC_SLSH, KC_J KC_G, KC_COMM
+
+#define _________________MALTRON_R1________________ KC_V, KC_M, KC_U, KC_Z, KC_L
+#define _________________MALTRON_R2________________ KC_D, KC_T, KC_D, KC_O, KC_R
+#define _________________MALTRON_R3________________ KC_DOT, KC_W, KC_K, KC_MINS, KC_X
+
+
+#define _________________EUCALYN_L1________________ KC_SLSH, KC_COMM, KC_DOT, KC_F, KC_Q
+#define _________________EUCALYN_L2________________ KC_A, KC_O, KC_E, KC_I, KC_U
+#define _________________EUCALYN_L3________________ KC_Z, KC_X, KC_C, KC_V, KC_W
+
+#define _________________EUCALYN_R1________________ KC_M, KC_R, KC_D, KC_Y, KC_P
+#define _________________EUCALYN_R2________________ KC_G, KC_T, KC_K, KC_S, KC_N
+#define _________________EUCALYN_R3________________ KC_B, KC_H, KC_J, KC_L, KC_SCLN
+
+
+#define _____________CARPLAX_QFMLWY_L1_____________ KC_Q, KC_F, KC_M, KC_L, KC_W
+#define _____________CARPLAX_QFMLWY_L2_____________ KC_D, KC_S, KC_T, KC_N, KC_R
+#define _____________CARPLAX_QFMLWY_L3_____________ KC_Z, KC_V, KC_G, KC_C, KC_X
+
+#define _____________CARPLAX_QFMLWY_R1_____________ KC_Y, KC_U, KC_O, KC_B, KC_J
+#define _____________CARPLAX_QFMLWY_R2_____________ KC_I, KC_A, KC_E, KC_H, KC_SCLN
+#define _____________CARPLAX_QFMLWY_R3_____________ KC_P, KC_K, KC_COMM, KC_DOT, KC_SLSH
+
+
+#define _____________CARPLAX_QGMLWB_L1_____________ KC_Q, KC_G, KC_M, KC_L, KC_W
+#define _____________CARPLAX_QGMLWB_L2_____________ KC_D, KC_S, KC_T, KC_N, KC_R
+#define _____________CARPLAX_QGMLWB_L3_____________ KC_Z, KC_X, KC_C, KC_F, KC_J
+
+#define _____________CARPLAX_QGMLWB_R1_____________ KC_B, KC_Y, KC_U, KC_V, KC_SCLN
+#define _____________CARPLAX_QGMLWB_R2_____________ KC_I, KC_A, KC_E, KC_O, KC_H
+#define _____________CARPLAX_QGMLWB_R3_____________ KC_K, KC_P, KC_COMM, KC_DOT, KC_SLSH
+
+
+#define _____________CARPLAX_QGMLWY_L1_____________ KC_Q, KC_G, KC_M, KC_L, KC_W
+#define _____________CARPLAX_QGMLWY_L2_____________ KC_D, KC_S, KC_T, KC_N, KC_R
+#define _____________CARPLAX_QGMLWY_L3_____________ KC_Z, KC_X, KC_C, KC_V, KC_J
+
+#define _____________CARPLAX_QGMLWY_R1_____________ KC_Y, KC_F, KC_U, KC_B, KC_SCLN
+#define _____________CARPLAX_QGMLWY_R2_____________ KC_I, KC_A, KC_E, KC_O, KC_H
+#define _____________CARPLAX_QGMLWY_R3_____________ KC_K, KC_P, KC_COMM, KC_DOT, KC_SLSH
+
+
+#define ________________NUMBER_LEFT________________ KC_1, KC_2, KC_3, KC_4, KC_5
+#define ________________NUMBER_RIGHT_______________ KC_6, KC_7, KC_8, KC_9, KC_0
+#define _________________FUNC_LEFT_________________ KC_F1, KC_F2, KC_F3, KC_F4, KC_F5
+#define _________________FUNC_RIGHT________________ KC_F6, KC_F7, KC_F8, KC_F9, KC_F10
+
+#define ___________________BLANK___________________ _______, _______, _______, _______, _______
+
+
+#define _________________LOWER_L1__________________ KC_EXLM, KC_AT, KC_HASH, KC_DLR, KC_PERC
+#define _________________LOWER_L2__________________ _________________FUNC_LEFT_________________
+#define _________________LOWER_L3__________________ _________________FUNC_RIGHT________________
+
+#define _________________LOWER_R1__________________ KC_CIRC, KC_AMPR, KC_ASTR, KC_LPRN, KC_RPRN
+#define _________________LOWER_R2__________________ _______, KC_UNDS, KC_PLUS, KC_LCBR, KC_RCBR
+#define _________________LOWER_R3__________________ _______, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT
+
+
+
+#define _________________RAISE_L1__________________ ________________NUMBER_LEFT________________
+#define _________________RAISE_L2__________________ ___________________BLANK___________________
+#define _________________RAISE_L3__________________ ___________________BLANK___________________
+
+#define _________________RAISE_R1__________________ ________________NUMBER_RIGHT_______________
+#define _________________RAISE_R2__________________ _______, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC
+#define _________________RAISE_R3__________________ _______, KC_HOME, KC_PGDN, KC_PGUP, KC_END
+
+
+
+#define _________________ADJUST_L1_________________ RGB_MOD, RGB_HUI, RGB_SAI, RGB_VAI, RGB_TOG
+#define _________________ADJUST_L2_________________ MU_TOG , CK_TOGG, AU_ON, AU_OFF, AG_NORM
+#define _________________ADJUST_L3_________________ RGB_RMOD,RGB_HUD,RGB_SAD, RGB_VAD, KC_RGB_T
+
+#define _________________ADJUST_R1_________________ KC_SEC1, KC_SEC2, KC_SEC3, KC_SEC4, KC_SEC5
+#define _________________ADJUST_R2_________________ AG_SWAP, QWERTY, COLEMAK, DVORAK, WORKMAN
+#define _________________ADJUST_R3_________________ MG_NKRO, KC_MUTE, KC_VOLD, KC_VOLU, KC_MNXT
diff --git a/users/edvorakjp/edvorakjp.c b/users/edvorakjp/edvorakjp.c
index cff1a123e4..1ac6107942 100644
--- a/users/edvorakjp/edvorakjp.c
+++ b/users/edvorakjp/edvorakjp.c
@@ -1,47 +1,12 @@
-#include "eeprom.h"
#include "edvorakjp.h"
-bool japanese_mode;
-uint16_t time_on_pressed;
-
-edvorakjp_config_t edvorakjp_config;
-
-uint8_t eeconfig_read_edvorakjp(void) {
- return eeprom_read_byte(EECONFIG_EDVORAK);
-}
-
-void eeconfig_update_edvorakjp(uint8_t val) {
- eeprom_update_byte(EECONFIG_EDVORAK, val);
-}
-
void dvorakj_layer_off(void) {
layer_off(_EDVORAKJ1);
layer_off(_EDVORAKJ2);
}
-void update_japanese_mode(bool new_state) {
- japanese_mode = new_state;
- if (japanese_mode) {
- if (edvorakjp_config.enable_kc_lang) {
- SEND_STRING(SS_TAP(X_LANG1));
- } else {
- SEND_STRING(SS_LALT("`"));
- }
- } else {
- dvorakj_layer_off();
- if (edvorakjp_config.enable_kc_lang) {
- SEND_STRING(SS_TAP(X_LANG2));
- } else {
- SEND_STRING(SS_LALT("`"));
- }
- }
-}
-
void matrix_init_user(void) {
- japanese_mode = false;
- time_on_pressed = 0;
- edvorakjp_config.raw = eeconfig_read_edvorakjp();
-
+ edvorakjp_status_init();
matrix_init_keymap();
}
@@ -58,189 +23,16 @@ uint32_t layer_state_set_keymap(uint32_t state) {
return state;
}
-/*
- * Each process_record_* methods defined here are
- * return false if handle edvorak_keycodes, or return true others.
- */
-__attribute__ ((weak))
-bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
- return true;
-}
-
-bool process_record_edvorakjp_ext(uint16_t keycode, keyrecord_t *record) {
- if (!(edvorakjp_config.enable_jp_extra_layer &&\
- (default_layer_state == 1UL<<_EDVORAK) &&\
- japanese_mode &&\
- record->event.pressed)) {
- return true;
- }
-
- // consonant keys
- // layer_on(J1) or layer_on(J2) are defined based on key positions.
- switch (keycode) {
- // right hand's left side w/o N
- case KC_F:
- case KC_G:
- case KC_R:
- case KC_D:
- case KC_T:
- case KC_B:
- case KC_H:
- case KC_J:
- layer_on(_EDVORAKJ1);
- register_code(keycode);
- unregister_code(keycode);
- return false;
-
- // N: toggle layer
- case KC_N:
- biton32(layer_state) == _EDVORAK ? layer_on(_EDVORAKJ1) : dvorakj_layer_off();
- register_code(keycode);
- unregister_code(keycode);
- return false;
-
- // left hand and right hand's right side
- case KC_X:
- case KC_C:
- case KC_V:
- case KC_Z:
- case KC_P:
- case KC_Y:
- case KC_W:
- case KC_Q:
- case KC_S:
- case KC_M:
- case KC_K:
- case KC_L:
- layer_on(_EDVORAKJ2);
- register_code(keycode);
- unregister_code(keycode);
- return false;
- }
-
- // vowel keys, symbol keys and modifier keys
- dvorakj_layer_off();
- switch (keycode) {
- // combination vowel keys
- case KC_AI:
- SEND_STRING("ai");
- return false;
- case KC_OU:
- SEND_STRING("ou");
- return false;
- case KC_EI:
- SEND_STRING("ei");
- return false;
- case KC_ANN:
- SEND_STRING("ann");
- return false;
- case KC_ONN:
- SEND_STRING("onn");
- return false;
- case KC_ENN:
- SEND_STRING("enn");
- return false;
- case KC_INN:
- SEND_STRING("inn");
- return false;
- case KC_UNN:
- SEND_STRING("unn");
- return false;
-
- // AOEIU and other (symbol, modifier) keys
- default:
- return true;
- }
-}
-
-bool process_record_edvorakjp_config(uint16_t keycode, keyrecord_t *record) {
- switch (keycode) {
- case KC_MAC:
- edvorakjp_config.enable_kc_lang = true;
- eeconfig_update_edvorakjp(edvorakjp_config.raw);
- return false;
- case KC_WIN:
- edvorakjp_config.enable_kc_lang = false;
- eeconfig_update_edvorakjp(edvorakjp_config.raw);
- return false;
- case KC_EXTON:
- edvorakjp_config.enable_jp_extra_layer = true;
- eeconfig_update_edvorakjp(edvorakjp_config.raw);
- return false;
- case KC_EXTOFF:
- edvorakjp_config.enable_jp_extra_layer = false;
- eeconfig_update_edvorakjp(edvorakjp_config.raw);
- return false;
- }
- return true;
-}
-
-bool process_record_layer(uint16_t keycode, keyrecord_t *record) {
- switch (keycode) {
- case EDVORAK:
- if (record->event.pressed) {
- set_single_persistent_default_layer(_EDVORAK);
- }
- return false;
- case QWERTY:
- if (record->event.pressed) {
- dvorakj_layer_off();
- set_single_persistent_default_layer(_QWERTY);
- }
- return false;
- case LOWER:
- if (record->event.pressed) {
- layer_on(_LOWER);
- time_on_pressed = record->event.time;
- } else {
- layer_off(_LOWER);
-
- if (TIMER_DIFF_16(record->event.time, time_on_pressed) < TAPPING_TERM) {
- update_japanese_mode(false);
- }
- time_on_pressed = 0;
- }
- return false;
- case RAISE:
- if (record->event.pressed) {
- layer_on(_RAISE);
- time_on_pressed = record->event.time;
- } else {
- layer_off(_RAISE);
-
- if (TIMER_DIFF_16(record->event.time, time_on_pressed) < TAPPING_TERM) {
- update_japanese_mode(true);
- }
- time_on_pressed = 0;
- }
- return false;
- default:
- return true;
- }
-}
-
-bool process_record_ime(uint16_t keycode, keyrecord_t *record) {
- switch (keycode) {
- case KC_JPN:
- if (record->event.pressed) {
- update_japanese_mode(true);
- }
- return false;
- case KC_ENG:
- if (record->event.pressed) {
- update_japanese_mode(false);
- }
- return false;
- default:
- return true;
- }
-}
-
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
-
return process_record_keymap(keycode, record) &&\
process_record_edvorakjp_ext(keycode, record) &&\
+ process_record_edvorakjp_swap_scln(keycode, record) &&\
process_record_edvorakjp_config(keycode, record) &&\
process_record_layer(keycode, record) &&\
process_record_ime(keycode, record);
}
+
+__attribute__ ((weak))
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
diff --git a/users/edvorakjp/edvorakjp.h b/users/edvorakjp/edvorakjp.h
index f67400686a..e781bf2378 100644
--- a/users/edvorakjp/edvorakjp.h
+++ b/users/edvorakjp/edvorakjp.h
@@ -1,5 +1,5 @@
-#ifndef USERSPACE
-#define USERSPACE
+#ifndef EDVORAKJP
+#define EDVORAKJP
#include "quantum.h"
#include "action_layer.h"
@@ -8,15 +8,6 @@
extern keymap_config_t keymap_config;
-typedef union {
- uint8_t raw;
- struct {
- bool enable_jp_extra_layer : 1;
- bool enable_kc_lang : 1; // for macOS
- };
-} edvorakjp_config_t;
-extern edvorakjp_config_t edvorakjp_config;
-
enum edvorakjp_layers {
_EDVORAK = 0,
_EDVORAKJ1,
@@ -50,26 +41,38 @@ enum edvorakjp_keycodes {
NEW_SAFE_RANGE
};
-uint8_t eeconfig_read_edvorakjp(void);
-void eeconfig_update_edvorakjp(uint8_t val);
+enum tap_dance_code {
+ TD_LOWER = 0,
+ TD_RAISE
+};
+// base
void dvorakj_layer_off(void);
-void update_japanese_mode(bool new_state);
void matrix_init_user(void);
void matrix_init_keymap(void);
uint32_t layer_state_set_user(uint32_t state);
uint32_t layer_state_set_keymap(uint32_t state);
+bool process_record_user(uint16_t keycode, keyrecord_t *record);
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record);
+
+// status
+void edvorakjp_status_init(void);
+bool get_enable_jp_extra_layer(void);
+void set_enable_jp_extra_layer(bool new_state);
+bool get_enable_kc_lang(void);
+void set_enable_kc_lang(bool new_state);
+bool get_japanese_mode(void);
+void set_japanese_mode(bool new_state);
/*
* Each process_record_* methods defined here are
* return false if processed, or return true if not processed.
* You can add your original macros in process_record_keymap() in keymap.c.
*/
-bool process_record_keymap(uint16_t keycode, keyrecord_t *record);
bool process_record_edvorakjp_ext(uint16_t keycode, keyrecord_t *record);
+bool process_record_edvorakjp_swap_scln(uint16_t keycode, keyrecord_t *record);
bool process_record_edvorakjp_config(uint16_t keycode, keyrecord_t *record);
bool process_record_layer(uint16_t keycode, keyrecord_t *record);
bool process_record_ime(uint16_t keycode, keyrecord_t *record);
-bool process_record_user(uint16_t keycode, keyrecord_t *record);
-#endif
+#endif // EDVORAKJP
diff --git a/users/edvorakjp/edvorakjp_process_record.c b/users/edvorakjp/edvorakjp_process_record.c
new file mode 100644
index 0000000000..2dcdab2a25
--- /dev/null
+++ b/users/edvorakjp/edvorakjp_process_record.c
@@ -0,0 +1,214 @@
+#include "edvorakjp.h"
+
+#if TAP_DANCE_ENABLE != yes
+static uint16_t time_on_pressed;
+#endif
+/*
+ * Each process_record_* methods defined here are
+ * return false if handle edvorak_keycodes, or return true others.
+ */
+bool process_record_edvorakjp_ext(uint16_t keycode, keyrecord_t *record) {
+ if (!(default_layer_state == 1UL<<_EDVORAK &&
+ get_enable_jp_extra_layer() && get_japanese_mode())) {
+ return true;
+ }
+
+ // consonant keys
+ // layer_on(J1) or layer_on(J2) are defined based on key positions.
+ switch (keycode) {
+ // right hand's left side w/o N
+ case KC_F:
+ case KC_G:
+ case KC_R:
+ case KC_D:
+ case KC_T:
+ case KC_B:
+ case KC_H:
+ case KC_J:
+ if (record->event.pressed) {
+ layer_on(_EDVORAKJ1);
+ }
+ return true;
+
+ // N: toggle layer
+ case KC_N:
+ if (record->event.pressed) {
+ biton32(layer_state) == _EDVORAK ? layer_on(_EDVORAKJ1) : dvorakj_layer_off();
+ }
+ return true;
+
+ // left hand up and right hand's right side
+ case KC_Y:
+ case KC_P:
+ case KC_W:
+ case KC_Q:
+ case KC_S:
+ case KC_M:
+ case KC_K:
+ case KC_L:
+ if (record->event.pressed) {
+ layer_on(_EDVORAKJ2);
+ }
+ return true;
+ // left hand down
+ // If return true, QMK sends keycode in new layer,
+ // but these keys are only available in old layer.
+ case KC_X:
+ case KC_C:
+ case KC_V:
+ case KC_Z:
+ if (record->event.pressed) {
+ layer_on(_EDVORAKJ2);
+ tap_code(keycode);
+ }
+ return false;
+ }
+
+ // vowel keys, symbol keys and modifier keys
+ if (record->event.pressed) {
+ dvorakj_layer_off();
+ }
+ switch (keycode) {
+ // combination vowel keys
+ case KC_AI:
+ if (record->event.pressed) {
+ SEND_STRING("ai");
+ }
+ return false;
+ case KC_OU:
+ if (record->event.pressed) {
+ SEND_STRING("ou");
+ }
+ return false;
+ case KC_EI:
+ if (record->event.pressed) {
+ SEND_STRING("ei");
+ }
+ return false;
+ case KC_ANN:
+ if (record->event.pressed) {
+ SEND_STRING("ann");
+ }
+ return false;
+ case KC_ONN:
+ if (record->event.pressed) {
+ SEND_STRING("onn");
+ }
+ return false;
+ case KC_ENN:
+ if (record->event.pressed) {
+ SEND_STRING("enn");
+ }
+ return false;
+ case KC_INN:
+ if (record->event.pressed) {
+ SEND_STRING("inn");
+ }
+ return false;
+ case KC_UNN:
+ if (record->event.pressed) {
+ SEND_STRING("unn");
+ }
+ return false;
+ }
+ // AOEIU and other (symbol, modifier) keys
+ return true;
+}
+
+bool process_record_edvorakjp_swap_scln(uint16_t keycode, keyrecord_t *record) {
+#ifdef SWAP_SCLN
+ static const uint8_t shift_bits = MOD_BIT(KC_LSFT) | MOD_BIT(KC_RSFT);
+ static uint8_t last_mods_status;
+ if (keycode == KC_SCLN) {
+ if (record->event.pressed) {
+ last_mods_status = get_mods();
+
+ // invert shift_bits
+ if (last_mods_status & shift_bits) {
+ set_mods(last_mods_status & ~shift_bits);
+ } else {
+ set_mods(last_mods_status | MOD_BIT(KC_LSFT));
+ }
+ } else {
+ set_mods(last_mods_status);
+ last_mods_status = 0;
+ }
+ }
+#endif
+ return true;
+}
+
+bool process_record_edvorakjp_config(uint16_t keycode, keyrecord_t *record) {
+ switch (keycode) {
+ case KC_MAC:
+ case KC_WIN:
+ if (record->event.pressed) {
+ set_enable_kc_lang(keycode == KC_MAC);
+ }
+ return false;
+ case KC_EXTON:
+ case KC_EXTOFF:
+ if (record->event.pressed) {
+ set_enable_jp_extra_layer(keycode == KC_EXTON);
+ }
+ return false;
+ }
+ return true;
+}
+
+bool process_record_layer(uint16_t keycode, keyrecord_t *record) {
+ switch (keycode) {
+ case EDVORAK:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(_EDVORAK);
+ }
+ return false;
+ case QWERTY:
+ if (record->event.pressed) {
+ dvorakj_layer_off();
+ set_single_persistent_default_layer(_QWERTY);
+ }
+ return false;
+#if TAP_DANCE_ENABLE != yes
+ case LOWER:
+ if (record->event.pressed) {
+ layer_on(_LOWER);
+ time_on_pressed = record->event.time;
+ } else {
+ layer_off(_LOWER);
+
+ if (TIMER_DIFF_16(record->event.time, time_on_pressed) < TAPPING_TERM) {
+ set_japanese_mode(false);
+ }
+ time_on_pressed = 0;
+ }
+ return false;
+ case RAISE:
+ if (record->event.pressed) {
+ layer_on(_RAISE);
+ time_on_pressed = record->event.time;
+ } else {
+ layer_off(_RAISE);
+
+ if (TIMER_DIFF_16(record->event.time, time_on_pressed) < TAPPING_TERM) {
+ set_japanese_mode(true);
+ }
+ time_on_pressed = 0;
+ }
+ return false;
+#endif
+ }
+ return true;
+}
+
+bool process_record_ime(uint16_t keycode, keyrecord_t *record) {
+ switch (keycode) {
+ case KC_JPN:
+ case KC_ENG:
+ if (record->event.pressed) {
+ set_japanese_mode(keycode == KC_JPN);
+ }
+ return false;
+ }
+ return true;
+}
diff --git a/users/edvorakjp/edvorakjp_status.c b/users/edvorakjp/edvorakjp_status.c
new file mode 100644
index 0000000000..a60c8d853b
--- /dev/null
+++ b/users/edvorakjp/edvorakjp_status.c
@@ -0,0 +1,75 @@
+#include "eeprom.h"
+#include "edvorakjp.h"
+
+typedef union {
+ uint8_t raw;
+ struct {
+ bool enable_jp_extra_layer : 1;
+ bool enable_kc_lang : 1; // for macOS
+ };
+} edvorakjp_config_t;
+static edvorakjp_config_t edvorakjp_config;
+
+typedef struct {
+ bool japanese_mode;
+} edvorakjp_state_t;
+static edvorakjp_state_t edvorakjp_state;
+
+/*
+ * private methods
+ */
+uint8_t eeconfig_read_edvorakjp(void) {
+ return eeprom_read_byte(EECONFIG_EDVORAK);
+}
+
+void eeconfig_update_edvorakjp(uint8_t val) {
+ eeprom_update_byte(EECONFIG_EDVORAK, val);
+}
+
+/*
+ * public methods
+ */
+void edvorakjp_status_init(void) {
+ edvorakjp_state.japanese_mode = false;
+ edvorakjp_config.raw = eeconfig_read_edvorakjp();
+}
+
+bool get_enable_jp_extra_layer(void) {
+ return edvorakjp_config.enable_jp_extra_layer;
+}
+
+void set_enable_jp_extra_layer(bool new_state) {
+ edvorakjp_config.enable_jp_extra_layer = new_state;
+ eeconfig_update_edvorakjp(edvorakjp_config.raw);
+}
+
+bool get_enable_kc_lang(void) {
+ return edvorakjp_config.enable_kc_lang;
+}
+
+void set_enable_kc_lang(bool new_state) {
+ edvorakjp_config.enable_kc_lang = new_state;
+ eeconfig_update_edvorakjp(edvorakjp_config.raw);
+}
+
+bool get_japanese_mode(void) {
+ return edvorakjp_state.japanese_mode;
+}
+
+void set_japanese_mode(bool new_state) {
+ edvorakjp_state.japanese_mode = new_state;
+ if (edvorakjp_state.japanese_mode) {
+ if (edvorakjp_config.enable_kc_lang) {
+ SEND_STRING(SS_TAP(X_LANG1));
+ } else {
+ SEND_STRING(SS_LALT("`"));
+ }
+ } else {
+ dvorakj_layer_off();
+ if (edvorakjp_config.enable_kc_lang) {
+ SEND_STRING(SS_TAP(X_LANG2));
+ } else {
+ SEND_STRING(SS_LALT("`"));
+ }
+ }
+}
diff --git a/users/edvorakjp/edvorakjp_tap_dance.c b/users/edvorakjp/edvorakjp_tap_dance.c
new file mode 100644
index 0000000000..62c0c100a2
--- /dev/null
+++ b/users/edvorakjp/edvorakjp_tap_dance.c
@@ -0,0 +1,71 @@
+#include "edvorakjp.h"
+#include "process_keycode/process_tap_dance.h"
+
+enum tap_state {
+ NONE = 0,
+ SINGLE_TAP = 1,
+ DOUBLE_TAP = 2,
+ HOLD
+};
+
+static int td_status_lower = NONE;
+static int td_status_raise = NONE;
+
+int cur_dance(qk_tap_dance_state_t *state) {
+ if (state->interrupted || !state->pressed) {
+ return state->count == 1 ? SINGLE_TAP : DOUBLE_TAP;
+ } else {
+ return HOLD;
+ }
+}
+
+void td_lower_finished(qk_tap_dance_state_t *state, void *user_data) {
+ td_status_lower = cur_dance(state);
+ switch(td_status_lower) {
+ case SINGLE_TAP:
+ set_japanese_mode(false);
+ register_code(KC_ESC);
+ break;
+ case DOUBLE_TAP:
+ set_japanese_mode(false);
+ break;
+ case HOLD:
+ break;
+ }
+ layer_on(_LOWER);
+}
+
+void td_lower_reset(qk_tap_dance_state_t *state, void *user_data) {
+ if (td_status_lower == SINGLE_TAP) {
+ unregister_code(KC_ESC);
+ }
+ layer_off(_LOWER);
+ td_status_lower = NONE;
+}
+
+void td_raise_finished(qk_tap_dance_state_t *state, void *user_data) {
+ td_status_raise = cur_dance(state);
+ switch(td_status_raise) {
+ case SINGLE_TAP:
+ case DOUBLE_TAP:
+ set_japanese_mode(true);
+ break;
+ case HOLD:
+ break;
+ }
+ layer_on(_RAISE);
+}
+
+void td_raise_reset(qk_tap_dance_state_t *state, void *user_data) {
+ layer_off(_RAISE);
+ td_status_raise = NONE;
+}
+
+qk_tap_dance_action_t tap_dance_actions[] = {
+ [TD_LOWER] = ACTION_TAP_DANCE_FN_ADVANCED_TIME(
+ NULL, td_lower_finished, td_lower_reset, TAPPING_TERM * 1.5
+ ),
+ [TD_RAISE] = ACTION_TAP_DANCE_FN_ADVANCED_TIME(
+ NULL, td_raise_finished, td_raise_reset, TAPPING_TERM * 1.5
+ )
+};
diff --git a/users/edvorakjp/readme.md b/users/edvorakjp/readme.md
index d7ec742852..077ba4abdc 100644
--- a/users/edvorakjp/readme.md
+++ b/users/edvorakjp/readme.md
@@ -10,7 +10,7 @@ This is a sample. You can swap any symbol keys and modifier keys.
//+----+----+----+----+----+----+----+----+----+----+----+----+----+---------+
` , ! , @ , # , $ , % , ^ , & , * , ( , ) , [ , ] , BSPC ,
//+----+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+-------+
- TAB , ' , , , . , P , Y , F , G , R , W , Q , / , = , \ ,
+ TAB , ' , , , . , Y , P , F , G , R , W , Q , / , = , \ ,
//+------++---++---++---++---++---++---++---++---++---++---++---++---+-------+
CAPS , A , O , E , I , U , D , T , N , S , M , - , ENT ,
//+-------+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-----------+
@@ -25,7 +25,7 @@ This is a sample. You can swap any symbol keys and modifier keys.
//+----+----+----+----+----+----+----+----+----+----+----+----+----+---------+
` , ! , @ , # , $ , % , ^ , & , * , ( , ) , [ , ] , BSPC ,
//+----+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+-------+
- TAB , ' , , , . , P , Y , F , G , R , W , C , / , = ,
+ TAB , ' , , , . , Y , P , F , G , R , W , C , / , = ,
//+------++---++---++---++---++---++---++---++---++---++---++---++---++
CAPS , A , O , E , I , U , D , T , N , S , M , ; , - , ENT ,
//+-------+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+-+--+------+
@@ -78,11 +78,15 @@ This is a sample. You can swap any symbol keys and modifier keys.
## for Programmer
- Dvorak 配列をベースに、ショートカットでよく利用される XCV は QWERTY 配列の位置を維持
-- Vimユーザのために、HJKL キーを横並びで配置
+- 一部にVimユーザ用のキー配置を実施
+ - HJKL キーを横並びで配置
+ - Shift押下時と非押下時で、";"キーの挙動を入れ替え(`config.h` 内で `#define SWAP_SCLN` の宣言が必要です)
- デフォルトレイヤーには、数字キーの代わりに記号 `!@#$%^&*()` を配置
- mainly based on Dvorak layout, but XCV is available in the same position of QWERTY layout
-- HJKL is lining side by side, for Vim users
+- for Vim users
+ - HJKL is lining side by side
+ - swap the ";" key behavior. i.e. send ":" normally and send ";" when you hold shift. (need `#define SWAP_SCLN` in your `config.h`)
- we can type `!@#$%^&*()` keys without shift keys in base layer
## License
diff --git a/users/edvorakjp/rules.mk b/users/edvorakjp/rules.mk
index 4fb7391864..587c3b8d2e 100644
--- a/users/edvorakjp/rules.mk
+++ b/users/edvorakjp/rules.mk
@@ -1 +1,7 @@
-SRC += edvorakjp.c
+SRC += edvorakjp.c \
+ edvorakjp_process_record.c \
+ edvorakjp_status.c
+
+ifeq ($(TAP_DANCE_ENABLE), yes)
+SRC += edvorakjp_tap_dance.c
+endif
diff --git a/users/ishtob/config.h b/users/ishtob/config.h
new file mode 100755
index 0000000000..1f567f4a5b
--- /dev/null
+++ b/users/ishtob/config.h
@@ -0,0 +1,75 @@
+#ifndef CONFIG_USER_H
+#define CONFIG_USER_H
+
+#include "config_common.h"
+
+#ifdef AUDIO_ENABLE
+ #define STARTUP_SONG SONG(PLANCK_SOUND)
+ // #define STARTUP_SONG SONG(NO_SOUND)
+
+ #define DEFAULT_LAYER_SONGS { SONG(QWERTY_SOUND), \
+ SONG(COLEMAK_SOUND), \
+ SONG(DVORAK_SOUND) \
+ }
+#endif
+
+//#define LEADER_TIMEOUT 300
+//#define BACKLIGHT_BREATHING
+//#define PERMISSIVE_HOLD
+// #define QMK_KEYS_PER_SCAN 4
+
+//audio clicky
+ //#define AUDIO_CLICKY
+ // to enable clicky on startup
+ //#define AUDIO_CLICKY_ON
+ //#define AUDIO_CLICKY_FREQ_RANDOMNESS 1.0f
+
+/* ws2812 RGB LED
+#define RGB_DI_PIN B5
+#define RGBLIGHT_ANIMATIONS
+#define RGBLED_NUM 8 // Number of LEDs
+#define RGBLIGHT_HUE_STEP 10
+#define RGBLIGHT_SAT_STEP 17
+*/
+#undef PLANCK_MIT_LAYOUT
+
+//#define MUON_LEFT
+
+#undef DEBOUNCE
+#define DEBOUNCE 0
+
+//rgb-reactive
+//#define RGB_MATRIX_KEYPRESSES
+//#define EECONFIG_RGB_MATRIX (uint32_t *)16
+
+//skip usb startup check
+//#define NO_USB_STARTUP_CHECK
+
+
+/*
+ * MIDI options
+ */
+
+/* Prevent use of disabled MIDI features in the keymap */
+//#define MIDI_ENABLE_STRICT 1
+
+/* enable basic MIDI features:
+ - MIDI notes can be sent when in Music mode is on
+*/
+#define MIDI_BASIC
+
+/* enable advanced MIDI features:
+ - MIDI notes can be added to the keymap
+ - Octave shift and transpose
+ - Virtual sustain, portamento, and modulation wheel
+ - etc.
+*/
+//#define MIDI_ADVANCED
+
+/* override number of MIDI tone keycodes (each octave adds 12 keycodes and allocates 12 bytes) */
+//#define MIDI_TONE_KEYCODE_OCTAVES 2
+
+// Most tactile encoders have detents every 4 stages
+#define ENCODER_RESOLUTION 4
+
+#endif
diff --git a/users/ishtob/ishtob.c b/users/ishtob/ishtob.c
new file mode 100644
index 0000000000..1b847d6306
--- /dev/null
+++ b/users/ishtob/ishtob.c
@@ -0,0 +1,69 @@
+/*
+Based on userspace written by @drashna 2017
+Copyright 2018 Hsian Chang <ishtob@gmail.com> @ishtob
+
+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, either version 2 of the License, or
+(at your option) any later version.
+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 "ishtob.h"
+#include "action.h"
+#include "action_layer.h"
+// #include "dynamic_macro.h"
+#ifdef AUDIO_ENABLE
+ #include "audio.h"
+#endif
+
+
+// Add reconfigurable functions here, for keymap customization
+// This allows for a global, userspace functions, and continued
+// customization of the keymap. Use _keymap instead of _user
+// functions in the keymaps
+__attribute__ ((weak))
+void matrix_init_keymap(void) {}
+
+__attribute__ ((weak))
+void matrix_scan_keymap(void) {}
+
+__attribute__ ((weak))
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
+__attribute__ ((weak))
+bool process_record_secrets(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
+// Call user matrix init, then call the keymap's init function
+void matrix_init_user(void) {
+ matrix_init_keymap();
+}
+
+// No global matrix scan code, so just run keymap's matix
+// scan function
+void matrix_scan_user(void) {
+ matrix_scan_keymap();
+}
+
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+ switch (keycode) {
+ case DFU:
+ if (record->event.pressed) {
+ clear_keyboard();
+ reset_keyboard();
+ }
+ return false;
+ break;
+ }
+ return process_record_keymap(keycode, record) && process_record_secrets(keycode, record);
+}
+
diff --git a/users/ishtob/ishtob.h b/users/ishtob/ishtob.h
new file mode 100644
index 0000000000..ced78a09d8
--- /dev/null
+++ b/users/ishtob/ishtob.h
@@ -0,0 +1,240 @@
+#ifndef USERSPACE
+#define USERSPACE
+#include "quantum.h"
+
+enum userspace_keycodes {
+ QWERTY = SAFE_RANGE,
+ COLEMAK,
+ DVORAK,
+ PLOVER,
+ LOWER,
+ RAISE,
+ BACKLIT,
+ EXT_PLV,
+ DFU,
+ P_CITRIX, //these macro exsists in macros_private.c, which is excluded from git
+ P_MPASS,
+ P_META,
+ O_DAYRN,
+ O_RTQ6H,
+ O_3DRN,
+ O_AUTODC,
+ M_EMAIL,
+ M_EMAIL2
+};
+
+// Each layer gets a name for readability, which is then used in the keymap matrix below.
+// The underscores don't mean anything - you can have a layer called STUFF or any other name.
+// Layer names don't all need to be of the same length, obviously, and you can also skip them
+// entirely and just use numbers.
+#define _QWERTY 0
+#define _COLEMAK 1
+#define _DVORAK 2
+#define _LOWER 3
+#define _RAISE 4
+#define _PLOVER 5
+#define _FNLAYER 6
+#define _NUMLAY 7
+#define _MOUSECURSOR 8
+#define _ADJUST 16
+
+
+
+#define LOWER MO(_LOWER)
+#define RAISE MO(_RAISE)
+
+// Fillers to make layering more clear
+#define _______ KC_TRNS
+#define XXXXXXX KC_NO
+// Custom macros
+#define CTL_ESC CTL_T(KC_ESC) // Tap for Esc, hold for Ctrl
+#define CTL_TTAB CTL_T(KC_TAB) // Tap for Esc, hold for Ctrl
+#define CTL_ENT CTL_T(KC_ENT) // Tap for Enter, hold for Ctrl
+#define SFT_ENT SFT_T(KC_ENT) // Tap for Enter, hold for Shift
+// Requires KC_TRNS/_______ for the trigger key in the destination layer
+#define LT_FN(kc) LT(_FNLAYER, kc) // L-ayer T-ap Function Layer
+#define LT_MC(kc) LT(_MOUSECURSOR, kc) // L-ayer T-ap M-ouse C-ursor
+#define LT_RAI(kc) LT(_RAISE, kc) // L-ayer T-ap to Raise
+#define TG_NUMLAY TG(_NUMLAY) //Toggle for layer _NUMLAY
+/*
+enum userspace_layers {
+ _QWERTY = 0,
+ _COLEMAK,
+ _DVORAK,
+ _LOWER,
+ _RAISE,
+ _PLOVER,
+ _FNLAYER,
+ _NUMLAY,
+ _MOUSECURSOR,
+ _ADJUST
+};
+*/
+
+/*
+Since our quirky block definitions are basically a list of comma separated
+arguments, we need a wrapper in order for these definitions to be
+expanded before being used as arguments to the LAYOUT_xxx macro.
+*/
+#if (!defined(LAYOUT) && defined(KEYMAP))
+#define LAYOUT KEYMAP
+#endif
+
+#define LAYOUT_ergodox_wrapper(...) LAYOUT_ergodox(__VA_ARGS__)
+#define LAYOUT_ergodox_pretty_wrapper(...) LAYOUT_ergodox_pretty(__VA_ARGS__)
+#define KEYMAP_wrapper(...) LAYOUT(__VA_ARGS__)
+#define LAYOUT_wrapper(...) LAYOUT(__VA_ARGS__)
+#define LAYOUT_ortho_4x12_wrapper(...) LAYOUT_ortho_4x12(__VA_ARGS__)
+
+/*
+Blocks for each of the four major keyboard layouts
+Organized so we can quickly adapt and modify all of them
+at once, rather than for each keyboard, one at a time.
+And this allows for much cleaner blocks in the keymaps.
+For instance Tap/Hold for Control on all of the layouts
+
+NOTE: These are all the same length. If you do a search/replace
+ then you need to add/remove underscores to keep the
+ lengths consistent.
+*/
+
+#define _________________QWERTY_L1_________________ KC_Q, KC_W, KC_E, KC_R, KC_T
+#define _________________QWERTY_L2_________________ KC_A, KC_S, KC_D, KC_F, KC_G
+#define _________________QWERTY_L3_________________ KC_Z, KC_X, KC_C, KC_V, KC_B
+
+#define _________________QWERTY_R1_________________ KC_Y, KC_U, KC_I, KC_O, KC_P
+#define _________________QWERTY_R2_________________ KC_H, KC_J, KC_K, KC_L, LT_MC(KC_SCLN)
+#define _________________QWERTY_R3_________________ KC_N, KC_M, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define _________________COLEMAK_L1________________ KC_Q, KC_W, KC_F, KC_P, KC_G
+#define _________________COLEMAK_L2________________ KC_A, KC_R, KC_S, KC_T, KC_D
+#define _________________COLEMAK_L3________________ KC_Z, KC_X, KC_C, KC_V, KC_B
+
+#define _________________COLEMAK_R1________________ KC_J, KC_L, KC_U, KC_Y, KC_SCLN
+#define _________________COLEMAK_R2________________ KC_H, KC_N, KC_E, KC_I, LT_MC(KC_O)
+#define _________________COLEMAK_R3________________ KC_K, KC_M, KC_COMM, KC_DOT, KC_SLASH
+
+#define ______________COLEMAK_MOD_DH_L1____________ KC_Q, KC_W, KC_F, KC_P, KC_B
+#define ______________COLEMAK_MOD_DH_L2____________ KC_A, KC_R, KC_S, KC_T, KC_G
+#define ______________COLEMAK_MOD_DH_L3____________ KC_Z, KC_X, KC_C, KC_D, KC_V
+
+#define ______________COLEMAK_MOD_DH_R1____________ KC_J, KC_L, KC_U, KC_Y, KC_SCLN
+#define ______________COLEMAK_MOD_DH_R2____________ KC_M, KC_N, KC_E, KC_I, LT_MC(KC_O)
+#define ______________COLEMAK_MOD_DH_R3____________ KC_K, KC_H, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define _________________DVORAK_L1_________________ KC_QUOT, KC_COMM, KC_DOT, KC_P, KC_Y
+#define _________________DVORAK_L2_________________ KC_A, KC_O, KC_E, KC_U, KC_I
+#define _________________DVORAK_L3_________________ KC_SCLN, KC_Q, KC_J, KC_K, KC_X
+
+#define _________________DVORAK_R1_________________ KC_F, KC_G, KC_C, KC_R, KC_L
+#define _________________DVORAK_R2_________________ KC_D, KC_H, KC_T, KC_N, LT_MC(KC_S)
+#define _________________DVORAK_R3_________________ KC_B, KC_M, KC_W, KC_V, KC_Z
+
+
+#define _________________WORKMAN_L1________________ KC_Q, KC_D, KC_R, KC_W, KC_B
+#define _________________WORKMAN_L2________________ KC_A, KC_S, KC_H, KC_T, KC_G
+#define _________________WORKMAN_L3________________ KC_Z, KC_X, KC_M, KC_C, KC_V
+
+#define _________________WORKMAN_R1________________ KC_J, KC_F, KC_U, KC_P, KC_SCLN
+#define _________________WORKMAN_R2________________ KC_Y, KC_N, KC_E, KC_O, LT_MC(KC_I)
+#define _________________WORKMAN_R3________________ KC_K, KC_L, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define _________________NORMAN_L1_________________ KC_Q, KC_W, KC_D, KC_F, KC_K
+#define _________________NORMAN_L2_________________ KC_A, KC_S, KC_E, KC_T, KC_G
+#define _________________NORMAN_L3_________________ KC_Z, KC_X, KC_C, KC_V, KC_B
+
+#define _________________NORMAN_R1_________________ KC_J, KC_U, KC_R, KC_L, KC_SCLN
+#define _________________NORMAN_R2_________________ KC_Y, KC_N, KC_I, KC_O, LT_MC(KC_U)
+#define _________________NORMAN_R3_________________ KC_P, KC_M, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define _________________MALTRON_L1________________ KC_Q, KC_P, KC_Y, KC_C, KC_B
+#define _________________MALTRON_L2________________ KC_A, KC_N, KC_I, KC_S, KC_F
+#define _________________MALTRON_L3________________ KC_SCLN, KC_SLSH, KC_J KC_G, KC_COMM
+
+#define _________________MALTRON_R1________________ KC_V, KC_M, KC_U, KC_Z, KC_L
+#define _________________MALTRON_R2________________ KC_D, KC_T, KC_D, KC_O, LT_MC(KC_R)
+#define _________________MALTRON_R3________________ KC_DOT, KC_W, KC_K, KC_MINS, KC_X
+
+
+#define _________________EUCALYN_L1________________ KC_SLSH, KC_COMM, KC_DOT, KC_F, KC_Q
+#define _________________EUCALYN_L2________________ KC_A, KC_O, KC_E, KC_I, KC_U
+#define _________________EUCALYN_L3________________ KC_Z, KC_X, KC_C, KC_V, KC_W
+
+#define _________________EUCALYN_R1________________ KC_M, KC_R, KC_D, KC_Y, KC_P
+#define _________________EUCALYN_R2________________ KC_G, KC_T, KC_K, KC_S, LT_MC(KC_N)
+#define _________________EUCALYN_R3________________ KC_B, KC_H, KC_J, KC_L, KC_SCLN
+
+
+#define _____________CARPLAX_QFMLWY_L1_____________ KC_Q, KC_F, KC_M, KC_L, KC_W
+#define _____________CARPLAX_QFMLWY_L2_____________ KC_D, KC_S, KC_T, KC_N, KC_R
+#define _____________CARPLAX_QFMLWY_L3_____________ KC_Z, KC_V, KC_G, KC_C, KC_X
+
+#define _____________CARPLAX_QFMLWY_R1_____________ KC_Y, KC_U, KC_O, KC_B, KC_J
+#define _____________CARPLAX_QFMLWY_R2_____________ KC_I, KC_A, KC_E, KC_H, LT_MC(KC_SCLN)
+#define _____________CARPLAX_QFMLWY_R3_____________ KC_P, KC_K, KC_COMM, KC_DOT, KC_SLSH
+
+
+#define _____________CARPLAX_QGMLWB_L1_____________ KC_Q, KC_G, KC_M, KC_L, KC_W
+#define _____________CARPLAX_QGMLWB_L2_____________ KC_D, KC_S, KC_T, KC_N, KC_R
+#define _____________CARPLAX_QGMLWB_L3_____________ KC_Z, KC_X, KC_C, KC_F, KC_J
+
+#define _____________CARPLAX_QGMLWB_R1_____________ KC_B, KC_Y, KC_U, KC_V, KC_SCLN
+#define _____________CARPLAX_QGMLWB_R2_____________ KC_I, KC_A, KC_E, KC_O, LT_MC(KC_H)
+#define _____________CARPLAX_QGMLWB_R3_____________ KC_K, KC_P, KC_COMM, KC_DOT, KC_SLSH
+
+
+#define _____________CARPLAX_QGMLWY_L1_____________ KC_Q, KC_G, KC_M, KC_L, KC_W
+#define _____________CARPLAX_QGMLWY_L2_____________ KC_D, KC_S, KC_T, KC_N, KC_R
+#define _____________CARPLAX_QGMLWY_L3_____________ KC_Z, KC_X, KC_C, KC_V, KC_J
+
+#define _____________CARPLAX_QGMLWY_R1_____________ KC_Y, KC_F, KC_U, KC_B, KC_SCLN
+#define _____________CARPLAX_QGMLWY_R2_____________ KC_I, KC_A, KC_E, KC_O, LT_MC(KC_H)
+#define _____________CARPLAX_QGMLWY_R3_____________ KC_K, KC_P, KC_COMM, KC_DOT, KC_SLSH
+
+
+#define ________________NUMBER_LEFT________________ KC_1, KC_2, KC_3, KC_4, KC_5
+#define ________________NUMBER_RIGHT_______________ KC_6, KC_7, KC_8, KC_9, KC_0
+#define _________________FUNC_LEFT_________________ KC_F1, KC_F2, KC_F3, KC_F4, KC_F5
+#define _________________FUNC_RIGHT________________ KC_F6, KC_F7, KC_F8, KC_F9, KC_F10
+
+#define __________________LONG_FUNC_LEFT___________________ KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6
+#define __________________LONG_FUNC_RIGHT__________________ KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12
+
+#define ___________________BLANK___________________ _______, _______, _______, _______, _______
+
+
+#define _________________LOWER_L1__________________ KC_EXLM, KC_AT, KC_HASH, KC_DLR, KC_PERC
+#define _________________LOWER_L2__________________ _________________FUNC_LEFT_________________
+#define _________________LOWER_L3__________________ _________________FUNC_RIGHT________________
+
+#define _________________LOWER_R1__________________ KC_CIRC, KC_AMPR, KC_ASTR, KC_LPRN, KC_RPRN
+#define _________________LOWER_R2__________________ _______, KC_UNDS, KC_PLUS, KC_LCBR, KC_RCBR
+#define _________________LOWER_R3__________________ _______, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT
+
+
+
+#define _________________RAISE_L1__________________ ________________NUMBER_LEFT________________
+#define _________________RAISE_L2__________________ ___________________BLANK___________________
+#define _________________RAISE_L3__________________ ___________________BLANK___________________
+
+#define _________________RAISE_R1__________________ ________________NUMBER_RIGHT_______________
+#define _________________RAISE_R2__________________ _______, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC
+#define _________________RAISE_R3__________________ _______, KC_HOME, KC_PGDN, KC_PGUP, KC_END
+
+
+
+#define _________________ADJUST_L1_________________ RGB_MOD, RGB_HUI, RGB_SAI, RGB_VAI, RGB_TOG
+#define _________________ADJUST_L2_________________ MU_TOG , CK_TOGG, AU_ON, AU_OFF, AG_NORM
+#define _________________ADJUST_L3_________________ RGB_RMOD,RGB_HUD,RGB_SAD, RGB_VAD, KC_RGB_T
+
+#define _________________ADJUST_R1_________________ KC_SEC1, KC_SEC2, KC_SEC3, KC_SEC4, KC_SEC5
+#define _________________ADJUST_R2_________________ AG_SWAP, QWERTY, COLEMAK, DVORAK, WORKMAN
+#define _________________ADJUST_R3_________________ MG_NKRO, KC_MUTE, KC_VOLD, KC_VOLU, KC_MNXT
+
+
+
+#endif // !USERSPACE \ No newline at end of file
diff --git a/users/ishtob/readme.md b/users/ishtob/readme.md
new file mode 100644
index 0000000000..5b7064de9e
--- /dev/null
+++ b/users/ishtob/readme.md
@@ -0,0 +1,87 @@
+# Ishtob's userspace
+
+under developement
+
+# Secret Macros
+
+This section is a modified version of what @drashna did in his userspace: https://github.com/qmk/qmk_firmware/tree/master/users/drashna#secret-macros
+
+`macros_private.c` will be used if it exsists in the userspace folder during compiling.
+
+To get started, put the following in rules.mk. this will have the compiler include the macros_private.c file if it exsists.
+```
+SRC += ishtob.c
+ifneq ($(wildcard $(USER_PATH)/macros_private.c),"")
+ SRC += macros_private.c
+endif
+ifeq ($(strip $(NO_SECRETS)), yes)
+ OPT_DEFS += -DNO_SECRETS
+endif
+```
+
+Remember that all macro keycode has to be present in the header file (ishtob.h) to prevent error during compile.
+
+Next, you setup macros_private.c, ensure the keycodes are defined in ishtob.h (or your keymap.h).
+Here is an example of my macros with the sensitive login information removed:
+```
+#include "ishtob.h" //replace this with your userspace or keymap
+#include "quantum.h"
+
+#pragma message "secret macros included" //debug line to let me know this file is included in the compile
+
+//this str is for the monthly password rotation per my workplace's security policy
+char my_str[5] = "stuff";
+
+bool process_record_secrets(uint16_t keycode, keyrecord_t *record) {
+ if (record->event.pressed) {
+ switch(keycode) {
+ //my login macros
+ case P_CITRIX:
+ SEND_STRING("username"SS_TAP(X_TAB)"something");
+ send_string(my_str);
+ return false;
+ case P_MPASS:
+ SEND_STRING("something");
+ send_string(my_str);
+ return false;
+ case P_META:
+ SEND_STRING("metausername");
+ return false;
+ //my work macros for the meta application
+ case O_RTQ6H:
+ SEND_STRING(SS_TAP(X_TAB)"0300"SS_TAP(X_TAB)SS_TAP(X_DOWN)SS_TAP(X_TAB)"0900"SS_TAP(X_TAB)SS_TAP(X_DOWN)SS_TAP(X_TAB)"1500"SS_TAP(X_TAB)SS_TAP(X_DOWN)SS_TAP(X_TAB)"2100"SS_TAP(X_TAB)SS_LALT("o"));
+ return false;
+ case O_AUTODC:
+ SEND_STRING(SS_LALT("v")SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)"T"SS_TAP(X_TAB)"N"SS_LALT("s"));
+ return false;
+ case O_DAYRN:
+ SEND_STRING(SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)SS_TAP(X_TAB)"1"SS_LALT("s"));
+ return false;
+ //Ops macros
+ case M_EMAIL:
+ SEND_STRING("privatemail@email.com");
+ return false;
+ case M_EMAIL2:
+ SEND_STRING("workemail@work.com");
+ return false;
+ }
+ }
+ return true;
+}
+```
+
+
+Finally, add the following to .git/info/exclude to prevent private macros from being committed to git.
+```
+# git ls-files --others --exclude-from=.git/info/exclude
+# Lines that start with '#' are comments.
+# For a project mostly in C, the following would be a good set of
+# exclude patterns (uncomment them if you want to use them):
+# *.[oa]
+# *~
+/users/ishtob/macros_private.c
+```
+
+# Special mentions
+
+special thanks to @drashna for helping me through quite a bit of these codes. \ No newline at end of file
diff --git a/users/ishtob/rules.mk b/users/ishtob/rules.mk
new file mode 100755
index 0000000000..909502b50a
--- /dev/null
+++ b/users/ishtob/rules.mk
@@ -0,0 +1,7 @@
+SRC += ishtob.c
+ifneq ("$(wildcard $(USER_PATH)/macros_private.c)","")
+ SRC += macros_private.c
+endif
+ifeq ($(strip $(NO_SECRETS)), yes)
+ OPT_DEFS += -DNO_SECRETS
+endif
diff --git a/users/jarred/config.h b/users/jarred/config.h
new file mode 100644
index 0000000000..f282088144
--- /dev/null
+++ b/users/jarred/config.h
@@ -0,0 +1,50 @@
+/* Copyright 2018 Jarred Steenvoorden
+ *
+ * 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, either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 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/>.
+ */
+
+#pragma once
+
+// Sets good default for the speed of the mouse.
+#undef MOUSEKEY_INTERVAL
+#undef MOUSEKEY_DELAY
+#undef MOUSEKEY_TIME_TO_MAX
+#undef MOUSEKEY_MAX_SPEED
+
+#define MOUSEKEY_INTERVAL 16
+#define MOUSEKEY_DELAY 0
+#define MOUSEKEY_TIME_TO_MAX 40
+#define MOUSEKEY_MAX_SPEED 5
+
+#undef MOUSEKEY_WHEEL_MAX_SPEED
+#undef MOUSEKEY_WHEEL_TIME_TO_MAX
+#undef MOUSEKEY_WHEEL_DELAY
+
+#define MOUSEKEY_WHEEL_MAX_SPEED 4
+#define MOUSEKEY_WHEEL_TIME_TO_MAX 255
+#define MOUSEKEY_WHEEL_DELAY 0
+
+#undef TAPPING_TOGGLE
+#undef TAPPING_TERM
+#undef IGNORE_MOD_TAP_INTERRUPT
+
+#define TAPPING_TOGGLE 1
+#define TAPPING_TERM 200
+#define IGNORE_MOD_TAP_INTERRUPT
+
+#ifdef AUDIO_ENABLE
+ #define STARTUP_SONG SONG(PLANCK_SOUND)
+#endif
+
+#define MACRO_TIMER 5
diff --git a/users/jarred/jarred.c b/users/jarred/jarred.c
index f8413ca3b3..33162b6891 100644
--- a/users/jarred/jarred.c
+++ b/users/jarred/jarred.c
@@ -15,3 +15,18 @@
*/
#include "jarred.h"
+#include "version.h"
+
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+
+ switch (keycode) {
+ case VRSN: // Prints firmware version
+ if (record->event.pressed) {
+ send_string_with_delay_P(PSTR(QMK_KEYBOARD "/" QMK_KEYMAP " @ " QMK_VERSION ", Built on: " QMK_BUILDDATE), MACRO_TIMER);
+ }
+ return false;
+ break;
+ }
+
+ return true;
+}
diff --git a/users/jarred/jarred.h b/users/jarred/jarred.h
index b1253f76a7..a6774ce264 100644
--- a/users/jarred/jarred.h
+++ b/users/jarred/jarred.h
@@ -19,9 +19,9 @@
#include "quantum.h"
-// Use 7 wide characters for keymaps
-#define _______ KC_TRNS
-#define XXXXXXX KC_NO
+enum userspace_custom_keycodes {
+ VRSN = SAFE_RANGE // Prints QMK Firmware and board info
+};
// Layers
#define _QW 0
@@ -72,7 +72,7 @@
#define NUMPAD_L1 RGB_TOG, RGB_MOD, _______, _______, RGB_HUD, RGB_HUI
#define NUMPAD_L2 BL_TOGG, BL_STEP, BL_BRTG, _______, RGB_SAD, RGB_SAI
#define NUMPAD_L3 _______, _______, _______, _______, RGB_VAD, RGB_VAI
-#define NUMPAD_L4 RESET, _______, _______, _______, RGB_SPD, RGB_SPI
+#define NUMPAD_L4 RESET, VRSN, _______, _______, RGB_SPD, RGB_SPI
#define NUMPAD_R1 _______, KC_P7, KC_P8, KC_P9, KC_PMNS, _______
#define NUMPAD_R2 _______, KC_P4, KC_P5, KC_P6, KC_PPLS, _______
diff --git a/users/jarred/rules.mk b/users/jarred/rules.mk
index 3c15cd0f9a..9a00cbf72b 100644
--- a/users/jarred/rules.mk
+++ b/users/jarred/rules.mk
@@ -1 +1,16 @@
SRC += jarred.c
+
+ifneq (,$(findstring planck,$(KEYBOARD)))
+ # Enable backlight for rev4 planck only
+ ifneq (,$(findstring rev4,$(KEYBOARD)))
+ BACKLIGHT_ENABLE = yes
+ BACKLIGHT_BREATHING = yes
+ else
+ BACKLIGHT_ENABLE = no
+ BACKLIGHT_BREATHING = no
+ endif
+
+ AUDIO_ENABLE = yes
+endif
+
+MOUSEKEY_ENABLE = no
diff --git a/users/kageurufu/config.h b/users/kageurufu/config.h
new file mode 100644
index 0000000000..938d43dd5a
--- /dev/null
+++ b/users/kageurufu/config.h
@@ -0,0 +1,4 @@
+#pragma once
+
+#define NO_ACTION_MACRO
+#define NO_ACTION_FUNCTION
diff --git a/users/kageurufu/custom_rgb.c b/users/kageurufu/custom_rgb.c
new file mode 100644
index 0000000000..8e99129b0b
--- /dev/null
+++ b/users/kageurufu/custom_rgb.c
@@ -0,0 +1,18 @@
+#include "custom_rgb.h"
+
+#if defined(RGBLIGHT_ENABLE)
+ extern rgblight_config_t rgblight_config;
+ rgblight_config_t _pushed_rgblight_config;
+ #define push_rgb_config() { if (_pushed_rgblight_config.raw == 0) { _pushed_rgblight_config.raw = rgblight_config.raw; } }
+ #define pop_rgb_config() { if (_pushed_rgblight_config.raw == 0) { rgblight_config.raw = _pushed_rgblight_config.raw; _pushed_rgblight_config.raw = 0; } }
+#elif defined(RGB_MATRIX_ENABLE)
+ extern rgb_config_t rgb_matrix_config;
+ rgb_config_t _pushed_rgb_matrix_config;
+ #define push_rgb_config() _pushed_rgb_matrix_config.raw = rgb_matrix_config.raw
+ #define pop_rgb_config() rgb_matrix_config.raw = _pushed_rgb_matrix_config.raw
+#endif
+
+
+bool process_record_rgb(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
diff --git a/users/kageurufu/custom_rgb.h b/users/kageurufu/custom_rgb.h
new file mode 100644
index 0000000000..62d64fd4c5
--- /dev/null
+++ b/users/kageurufu/custom_rgb.h
@@ -0,0 +1,3 @@
+#pragma once
+
+#include "kageurufu.h"
diff --git a/users/kageurufu/kageurufu.c b/users/kageurufu/kageurufu.c
new file mode 100644
index 0000000000..e16af571bd
--- /dev/null
+++ b/users/kageurufu/kageurufu.c
@@ -0,0 +1,12 @@
+#include "kageurufu.h"
+#include "quantum.h"
+#include "process_records.h"
+
+#ifdef RGBLIGHT_ENABLE
+ //Following line allows macro to read current RGB settings
+ extern rgblight_config_t rgblight_config;
+ rgblight_config_t backup_rgblight_config;
+
+ __attribute__((weak))
+ uint8_t RGBLIGHT_MODS[] = {0};
+#endif
diff --git a/users/kageurufu/kageurufu.h b/users/kageurufu/kageurufu.h
new file mode 100644
index 0000000000..76a0126fec
--- /dev/null
+++ b/users/kageurufu/kageurufu.h
@@ -0,0 +1,5 @@
+#pragma once
+
+#include "quantum.h"
+#include "process_records.h"
+#include "layouts.h"
diff --git a/users/kageurufu/layouts.h b/users/kageurufu/layouts.h
new file mode 100644
index 0000000000..eccfa0700e
--- /dev/null
+++ b/users/kageurufu/layouts.h
@@ -0,0 +1,58 @@
+#pragma once
+
+
+#define _________________NUMROW_L1_________________ KC_1, KC_2, KC_3, KC_4, KC_5
+#define _________________NUMROW_R1_________________ KC_6, KC_7, KC_8, KC_9, KC_0
+
+
+#define _________________QWERTY_L1_________________ KC_Q, KC_W, KC_E, KC_R, KC_T
+#define _________________QWERTY_L2_________________ KC_A, KC_S, KC_D, KC_F, KC_G
+#define _________________QWERTY_L3_________________ KC_Z, KC_X, KC_C, KC_V, KC_B
+
+#define _________________QWERTY_R1_________________ KC_Y, KC_U, KC_I, KC_O, KC_P
+#define _________________QWERTY_R2_________________ KC_H, KC_J, KC_K, KC_L, KC_SCLN
+#define _________________QWERTY_R3_________________ KC_N, KC_M, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define _________________COLEMAK_L1________________ KC_Q, KC_W, KC_F, KC_P, KC_G
+#define _________________COLEMAK_L2________________ KC_A, KC_R, KC_S, KC_T, KC_D
+#define _________________COLEMAK_L3________________ KC_Z, KC_X, KC_C, KC_V, KC_B
+
+#define _________________COLEMAK_R1________________ KC_J, KC_L, KC_U, KC_Y, KC_SCLN
+#define _________________COLEMAK_R2________________ KC_H, KC_N, KC_E, KC_I, KC_O
+#define _________________COLEMAK_R3________________ KC_K, KC_M, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define ______________COLEMAK_MOD_DH_L1____________ KC_Q, KC_W, KC_F, KC_P, KC_B
+#define ______________COLEMAK_MOD_DH_L2____________ KC_A, KC_R, KC_S, KC_T, KC_G
+#define ______________COLEMAK_MOD_DH_L3____________ KC_Z, KC_X, KC_C, KC_D, KC_V
+
+#define ______________COLEMAK_MOD_DH_R1____________ KC_J, KC_L, KC_U, KC_Y, KC_SCLN
+#define ______________COLEMAK_MOD_DH_R2____________ KC_M, KC_N, KC_E, KC_I, KC_O
+#define ______________COLEMAK_MOD_DH_R3____________ KC_K, KC_H, KC_COMM, KC_DOT, KC_SLASH
+
+
+#define ________________FUNCTION_L1________________ KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6
+#define ________________FUNCTION_L2________________ _______, KC_PGDN, KC_UP, KC_PGUP, _______, KC_LBRC
+#define ________________FUNCTION_L3________________ ADJ, KC_LEFT, KC_DOWN, KC_RGHT, _______, _______
+#define ________________FUNCTION_L4________________ _______, _______, _______, _______, _______, _______
+#define ________________FUNCTION_L5________________ _______, _______, _______, _______, ADJ, _______
+
+#define ________________FUNCTION_R1________________ KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12
+#define ________________FUNCTION_R2________________ KC_RBRC, KC_7, KC_UP, KC_9, KC_0, KC_HOME
+#define ________________FUNCTION_R3________________ _______, KC_LEFT, KC_DOWN, KC_RGHT, KC_RBRC, KC_END
+#define ________________FUNCTION_R4________________ _______, _______, _______, KC_PGDN, KC_PGUP, _______
+#define ________________FUNCTION_R5________________ ADJ, KC_MPLY, KC_MNXT, KC_MUTE, KC_VOLD, KC_VOLU
+
+
+#define _________________ADJUST_L1_________________ KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6
+#define _________________ADJUST_L2_________________ _______, RGB_SAD, RGB_VAI, RGB_SAI, RESET, _______
+#define _________________ADJUST_L3_________________ _______, RGB_HUD, RGB_VAD, RGB_HUI, RGBRST, _______
+#define _________________ADJUST_L4_________________ _______, _______, _______, _______, _______, _______
+#define _________________ADJUST_L5_________________ _______, _______, _______, _______, _______, _______
+
+#define _________________ADJUST_R1_________________ KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12
+#define _________________ADJUST_R2_________________ _______, _______, _______, _______, _______, KC_DEL
+#define _________________ADJUST_R3_________________ _______, QWERTY, COLEMAK, CMAK_DH, _______, _______
+#define _________________ADJUST_R4_________________ _______, _______, RGB_TOG, RGB_HUI, RGB_SAI, RGB_VAI
+#define _________________ADJUST_R5_________________ _______, _______, RGB_RMOD,RGB_HUD, RGB_SAD, RGB_VAD
diff --git a/users/kageurufu/process_records.c b/users/kageurufu/process_records.c
new file mode 100644
index 0000000000..63dbcff89b
--- /dev/null
+++ b/users/kageurufu/process_records.c
@@ -0,0 +1,44 @@
+#include "kageurufu.h"
+
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+ switch (keycode) {
+ case QWERTY:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(_QWERTY);
+ }
+ return false;
+ break;
+ case COLEMAK:
+ if(record->event.pressed) {
+ set_single_persistent_default_layer(_COLEMAK);
+ }
+ return false;
+ break;
+ case RGBRST:
+ #ifdef RGBLIGHT_ENABLE
+ if (record->event.pressed) {
+ eeconfig_update_rgblight_default();
+ rgblight_enable();
+ }
+ #endif
+ break;
+ }
+
+
+ return process_record_keymap(keycode, record) &&
+#if defined(RGBLIGHT_ENABLE) || defined(RGB_MATRIX_ENABLE)
+ process_record_rgb(keycode, record) &&
+#endif // RGBLIGHT_ENABLE;
+ true;
+}
+
+__attribute__ ((weak))
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
+
+__attribute__ ((weak))
+bool process_record_rgb(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
diff --git a/users/kageurufu/process_records.h b/users/kageurufu/process_records.h
new file mode 100644
index 0000000000..d1c50a4112
--- /dev/null
+++ b/users/kageurufu/process_records.h
@@ -0,0 +1,27 @@
+#pragma once
+#include "kageurufu.h"
+
+#define FN_ESC LT(_FN, KC_ESC)
+#define FN MO(_FN)
+#define ADJ MO(_ADJ)
+
+enum layer_number {
+ _QWERTY = 0,
+ _COLEMAK,
+ _COLEMAK_DH,
+ _FN,
+ _ADJ,
+ ADDITIONAL_LAYER
+};
+
+enum custom_keycodes {
+ QWERTY = SAFE_RANGE,
+ COLEMAK,
+ CMAK_DH,
+ RGBRST,
+ KAGEURUFU_SAFE_RANGE
+};
+
+
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record);
+bool process_record_rgb(uint16_t keycode, keyrecord_t *record);
diff --git a/users/kageurufu/readme.md b/users/kageurufu/readme.md
new file mode 100644
index 0000000000..57dd85d6be
--- /dev/null
+++ b/users/kageurufu/readme.md
@@ -0,0 +1,14 @@
+Copyright 2018- Franklyn Tackitt franklyn@tackitt.net @kageurufu
+
+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, either version 2 of the License, or
+(at your option) any later version.
+
+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/>.
diff --git a/users/kageurufu/rules.mk b/users/kageurufu/rules.mk
new file mode 100644
index 0000000000..1bd16e2626
--- /dev/null
+++ b/users/kageurufu/rules.mk
@@ -0,0 +1,15 @@
+SRC += kageurufu.c \
+ process_records.c \
+ custom_rgb.c
+
+# Link time optimization, should save on firmware size
+EXTRAFLAGS += -flto
+
+
+# Some usual defaults
+MOUSEKEY_ENABLE = no
+EXTRAKEY_ENABLE = yes
+COMMAND_ENABLE = yes
+CONSOLE_ENABLE = yes
+RGBLIGHT_ENABLE = yes
+RGBLIGHT_ANIMATIONS = yes
diff --git a/users/kuatsure/kuatsure.h b/users/kuatsure/kuatsure.h
index 56fb684ec0..23d3c617cb 100644
--- a/users/kuatsure/kuatsure.h
+++ b/users/kuatsure/kuatsure.h
@@ -8,6 +8,8 @@ void tmux_pane_zoom(void);
void tmux_pane_switch(uint16_t keycode);
void tmux_window_switch(uint16_t keycode);
+#define KT_CESC CTL_T(KC_ESC)
+
#undef LEADER_TIMEOUT
#define LEADER_TIMEOUT 300
diff --git a/users/kuatsure/rules.mk b/users/kuatsure/rules.mk
index 11262d0ecf..f0d295aad0 100644
--- a/users/kuatsure/rules.mk
+++ b/users/kuatsure/rules.mk
@@ -1 +1,3 @@
+CONSOLE_ENABLE = no
+
SRC += kuatsure.c
diff --git a/users/mechmerlin/changelog.md b/users/mechmerlin/changelog.md
new file mode 100644
index 0000000000..11b3ba708f
--- /dev/null
+++ b/users/mechmerlin/changelog.md
@@ -0,0 +1,14 @@
+# Changelog
+All notable changes to my userspace will be documented in this file.
+
+## [0.1.1] - 2018-10-26
+### Added
+- Added a changelog, aka THIS VERY FILE!
+- Added `config.h` to userspace for `RGBLIGHT_SLEEP` feature.
+
+### Changed
+- Spruced up the readme file to better explain the things I use in my keymap for would be keymap snoopers. Also useful as an example when people ask.
+- Use `CTL_T` instead of `MT` for my custom `KC_CTCP` keycode as it was causing issues on some boards.
+
+## [0.1.0] - 2018-08-31
+Initial usage of userspaces!
diff --git a/users/mechmerlin/config.h b/users/mechmerlin/config.h
new file mode 100644
index 0000000000..3d58c230af
--- /dev/null
+++ b/users/mechmerlin/config.h
@@ -0,0 +1,5 @@
+#pragma once
+
+#ifdef RGBLIGHT_ENABLE
+#define RGBLIGHT_SLEEP
+#endif // RGBLIGHT_ENABLE
diff --git a/users/mechmerlin/mechmerlin.c b/users/mechmerlin/mechmerlin.c
new file mode 100644
index 0000000000..8d6cecd18b
--- /dev/null
+++ b/users/mechmerlin/mechmerlin.c
@@ -0,0 +1,20 @@
+#include "mechmerlin.h"
+
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+ static uint16_t fnx_layer_timer;
+
+ switch (keycode){
+ case KC_FNX:
+ if(record->event.pressed){
+ fnx_layer_timer = timer_read();
+ layer_on(_FL);
+ } else {
+ layer_off(_FL);
+ if (timer_elapsed(fnx_layer_timer) < 150) {
+ layer_invert(_AL);
+ }
+ }
+ return false;
+ }
+ return true;
+} \ No newline at end of file
diff --git a/users/mechmerlin/mechmerlin.h b/users/mechmerlin/mechmerlin.h
new file mode 100644
index 0000000000..6b4d50edc8
--- /dev/null
+++ b/users/mechmerlin/mechmerlin.h
@@ -0,0 +1,17 @@
+#pragma once
+
+#include "quantum.h"
+
+enum userspace_layers {
+ _BL = 0, // Base Layer
+ _FL, // Function Layer
+ _AL // Arrow Layer
+};
+
+// Enum of custom keycodes defined in process_record_user
+enum keycodes {
+ KC_FNX, // Hold for FN layer, tap to toggle ARROWS layer.
+};
+
+// Custom #defined keycodes
+#define KC_CTCP CTL_T(KC_CAPS)
diff --git a/users/mechmerlin/readme.md b/users/mechmerlin/readme.md
new file mode 100644
index 0000000000..1e86a64107
--- /dev/null
+++ b/users/mechmerlin/readme.md
@@ -0,0 +1,40 @@
+# MechMerlin's Userspace v0.1.1
+
+This is a collection of my most commonly used QMK features.
+
+A majority of my keyboards are smaller than 75%, ANSI, and staggered.
+
+## Layers
+----
+
+### _BL (Base Layer)
+Typical standard QWERTY keymap.
+
+### _FL (Function Layer)
+This layer is commonly accessed via `MO(_FL)` on the base layer. It consists of your typical function key F1 through F12 and some RGB and Backlight controls.
+
+### _AL (Arrow Layer)
+This layer is only present on my 60% boards. I habitually use the bottom right modifiers as arrows.
+
+### _CL (Control Layer)
+This is not defined in here as it's present only on `LAYOUT_66` boards, or to be specific, my clueboard. It currently uses the default clueboard controls.
+
+## Custom Keycodes
+----
+
+### KC_FNX (Fn Extended)
+
+`KC_FNX` functions as a hold for `MO(X)` and tap for `TG(Y)`. Layer X and Y are different layers.
+
+It is used primarily on my `LAYOUT_60_ansi` boards as my regular toggle (the 1u key to the right of right shift), is not present there.
+
+### KC_CTCP (Control Caps)
+
+This is just a wrapper for `CTL_T(KC_CAPS)`. This is a hold for control and tap for caps lock.
+
+## QMK Features
+----
+
+### RGBLIGHT_SLEEP
+
+Ensures that when my computer is in sleep mode, the keyboard underglow lights will also be off.
diff --git a/users/mechmerlin/rules.mk b/users/mechmerlin/rules.mk
new file mode 100644
index 0000000000..70c20ec71e
--- /dev/null
+++ b/users/mechmerlin/rules.mk
@@ -0,0 +1 @@
+SRC += mechmerlin.c \ No newline at end of file
diff --git a/users/mtdjr/mtdjr.c b/users/mtdjr/mtdjr.c
index d8d6871a17..c31b077b46 100644
--- a/users/mtdjr/mtdjr.c
+++ b/users/mtdjr/mtdjr.c
@@ -5,7 +5,7 @@
#endif
#ifndef RGB_MODE
- #define RGB_MODE 16
+ #define RGB_MODE 2
#endif
#ifndef RGB_HUE
#define RGB_HUE 285
diff --git a/users/mtdjr/mtdjr.h b/users/mtdjr/mtdjr.h
index 3efcb45ec2..85ca1596dc 100644
--- a/users/mtdjr/mtdjr.h
+++ b/users/mtdjr/mtdjr.h
@@ -95,7 +95,7 @@ enum user_tapdance {
#define KC_BLD BL_DEC
#define KC_BLB BL_BRTG
#define KC_BLON BL_ON
-#define KB_BLOF BL_OFF
+#define KC_BLOF BL_OFF
#endif
diff --git a/users/replicaJunction/config.h b/users/replicaJunction/config.h
new file mode 100644
index 0000000000..4b58b579f8
--- /dev/null
+++ b/users/replicaJunction/config.h
@@ -0,0 +1,66 @@
+#pragma once
+
+
+////////////////////////////////////////////////////////////////////////////////
+// Features That Can Be Enabled
+// https://docs.qmk.fm/reference/config-options#features-that-can-be-enabled
+////////////////////////////////////////////////////////////////////////////////
+
+////////////////////////////////////////////////////////////////////////////////
+// Behaviors That Can Be Configured
+// https://docs.qmk.fm/reference/config-options#behaviors-that-can-be-configured
+////////////////////////////////////////////////////////////////////////////////
+
+// MS the button needs to be held before a tap becomes a hold (default: 200)
+#undef TAPPING_TERM
+#define TAPPING_TERM 250
+
+// Makes it easier for fast typists to use dual-role keys. See additional details here:
+// https://docs.qmk.fm/features/advanced-keycodes#permissive-hold
+#define PERMISSIVE_HOLD
+
+// MS after tapping the Leader key to listen for a sequence (default: 300)
+#undef LEADER_TIMEOUT
+#define LEADER_TIMEOUT 750
+
+// This makes it possible to do rolling combos (zx) with keys that convert to other keys on hold
+// (for example, if z becomes ctrl when you hold it, when this option isn't enabled, z rapidly
+// followed by x actually sends Ctrl-x. That's bad.)
+#define IGNORE_MOD_TAP_INTERRUPT
+
+
+
+////////////////////////////////////////////////////////////////////////////////
+// Mouse Key Options
+// https://docs.qmk.fm/reference/config-options#mouse-key-options
+////////////////////////////////////////////////////////////////////////////////
+
+#ifdef MOUSEKEY_ENABLE
+// Mouse key config
+
+// Frequency with which cursor movements are sent. Lower means more resolution / DPI.
+// Default: 20
+// #undef MOUSEKEY_INTERVAL
+// #define MOUSEKEY_INTERVAL 20
+
+// MS after pressing the key before initial movement begins. Lower means quicker response.
+// Default: 0
+// #undef MOUSEKEY_DELAY
+// #define MOUSEKEY_DELAY 0
+
+// MS it takes the cursor to accelerate to max speed
+// Default: 60
+// #undef MOUSEKEY_TIME_TO_MAX
+// #define MOUSEKEY_TIME_TO_MAX 60
+
+// Maximum speed for the mouse keys
+// Default: 7
+// #undef MOUSEKEY_MAX_SPEED
+// #define MOUSEKEY_MAX_SPEED 7
+
+// Delay before the mouse wheel
+// Default: 0
+// #undef MOUSEKEY_WHEEL_DELAY
+// #define MOUSEKEY_WHEEL_DELAY 0
+
+#endif // MOUSEKEY_ENABLE
diff --git a/users/replicaJunction/readme.md b/users/replicaJunction/readme.md
new file mode 100644
index 0000000000..2a9cad2729
--- /dev/null
+++ b/users/replicaJunction/readme.md
@@ -0,0 +1,14 @@
+Copyright 2018 @<replicaJunction>
+
+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, either version 2 of the License, or
+(at your option) any later version.
+
+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/>. \ No newline at end of file
diff --git a/users/replicaJunction/replicaJunction.c b/users/replicaJunction/replicaJunction.c
new file mode 100644
index 0000000000..f0bc59d257
--- /dev/null
+++ b/users/replicaJunction/replicaJunction.c
@@ -0,0 +1,149 @@
+#include "replicaJunction.h"
+#include "version.h"
+
+#ifdef TAP_DANCE_ENABLE
+void dance_layer(qk_tap_dance_state_t *state, void *user_data)
+{
+ uint8_t layer = biton32(layer_state);
+
+ if (state->count >= 5)
+ {
+ // 5 or more taps resets the keyboard
+ reset_keyboard();
+ }
+ #ifdef L_QWERTY
+ else if (state->count == 3)
+ {
+ // Triple tap changes to QWERTY layer
+ if (layer == L_QWERTY)
+ {
+ layer_off(L_QWERTY);
+ }
+ else
+ {
+ layer_on(L_QWERTY);
+ }
+ }
+ #endif
+ #ifdef L_NUM
+ else if (state->count == 2)
+ {
+ // Double tap toggles Number layer
+ if (layer == L_NUM)
+ {
+ layer_off(L_NUM);
+ }
+ else
+ {
+ layer_on(L_NUM);
+ }
+ }
+ #endif
+ else
+ {
+ // Single tap sends Escape, and also turns off layers
+ // That's mostly in case I get stuck and forget where I am
+ #ifdef L_NUM
+ layer_off(L_NUM);
+ #endif
+ #ifdef L_EXTEND
+ layer_off(L_EXTEND);
+ #endif
+ #ifdef L_SYMBOL
+ layer_off(L_SYMBOL);
+ #endif
+ #ifdef L_QWERTY
+ layer_off(L_QWERTY);
+ #endif
+ register_code(KC_ESC);
+ unregister_code(KC_ESC);
+ }
+};
+
+// Tap Dance Definitions
+// Note - this needs to come AFTER the function is declared
+qk_tap_dance_action_t tap_dance_actions[] = {
+ [TD_LAYER_TOGGLE] = ACTION_TAP_DANCE_FN(dance_layer)
+};
+
+#endif // TAP_DANCE_ENABLE
+
+// These functions can be overridden in individual keymap files.
+// This allows a user function to be shared for all my keyboards, while each
+// keyboard can also have a keyboard-specific section.
+
+// Note that keymaps don't need to override these if there's nothing to
+// override them with.
+__attribute__ ((weak))
+void matrix_init_keymap(void) {}
+
+__attribute__ ((weak))
+void matrix_scan_keymap(void) {}
+
+__attribute__ ((weak))
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+};
+
+// Runs just one time when the keyboard initializes.
+void matrix_init_user(void) {
+ #ifdef UNICODEMAP_ENABLE
+ // Set Unicode input to use WinCompose
+ // https://github.com/samhocevar/wincompose
+ set_unicode_input_mode(UC_WINC);
+ #endif // UNICODEMAP_ENABLE
+
+ matrix_init_keymap();
+};
+
+// Runs constantly in the background, in a loop.
+void matrix_scan_user(void) {
+ matrix_scan_keymap();
+}
+
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+ if (record->event.pressed)
+ return true;
+
+ switch(keycode)
+ {
+ case RJ_MAKE: // Compiles the firmware, and adds the flash command based on keyboard bootloader
+ SEND_STRING("make " QMK_KEYBOARD ":" QMK_KEYMAP
+ #if (defined(BOOTLOADER_DFU) || defined(BOOTLOADER_LUFA_DFU) || defined(BOOTLOADER_QMK_DFU))
+ ":dfu"
+ #elif defined(BOOTLOADER_HALFKAY)
+ ":teensy"
+ #elif defined(BOOTLOADER_CATERINA)
+ ":avrdude"
+ #endif // bootloader options
+ //SS_TAP(X_ENTER)
+ );
+ return false;
+ case RJ_QMKV:
+ SEND_STRING (QMK_KEYBOARD "/" QMK_KEYMAP " @ " QMK_VERSION);
+ return false;
+ case RJ_EQ:
+ SEND_STRING("==");
+ return false;
+ case RJ_NEQ:
+ SEND_STRING("!=");
+ return false;
+ case RJ_GEQ:
+ SEND_STRING(">=");
+ return false;
+ case RJ_LEQ:
+ SEND_STRING("<=");
+ return false;
+ case RJ_GEQR:
+ SEND_STRING("=>");
+ return false;
+ case RJ_DUND:
+ SEND_STRING("$_");
+ return false;
+ case RJ_SELS:
+ SEND_STRING("select *");
+ return false;
+ }
+
+ return process_record_keymap(keycode, record);
+};
diff --git a/users/replicaJunction/replicaJunction.h b/users/replicaJunction/replicaJunction.h
new file mode 100644
index 0000000000..ab0e8ab3e3
--- /dev/null
+++ b/users/replicaJunction/replicaJunction.h
@@ -0,0 +1,115 @@
+#pragma once
+
+#include "quantum.h"
+
+///////////////////////////////////////////////////////////////////////////////
+// Keymap definitions
+///////////////////////////////////////////////////////////////////////////////
+
+// Layer definitions
+// #define L_COLEMAK 0
+// #define L_QWERTY 1
+// #define L_NUM 2
+// #define L_EXTEND 3
+// #define L_FUNC 4
+// #define L_GAMING 5
+// #define L_SYMBOL 6
+// #define L_LL_R 7
+// #define L_LL_S 8
+// #define L_LL_E 9
+// #define L_LL_I 10
+
+// Keyboard aliases
+#define _______ KC_TRNS
+#define ooooooo KC_TRNS
+
+#define MO_FUNC MO(L_FUNC)
+#define TT_NUM TT(L_NUM)
+#define TG_GAME TG(L_GAMING)
+#define OSL_SYM OSL(L_SYMBOL)
+
+#define OSM_LSF OSM(MOD_LSFT)
+#define OSM_RSF OSM(MOD_RSFT)
+
+#define KX_CTSF LCTL(KC_LSFT)
+#define KX_STAB LSFT(KC_TAB)
+#define KX_CGR LCTL(KC_GRV)
+#define KX_PAST LCTL(LGUI(LALT(KC_V)))
+#define KX_SRCH LCTL(LGUI(LALT(KC_S)))
+
+#define KX_BKNM LT(L_NUM, KC_BSPC)
+#define KX_DCTL CTL_T(KC_DEL)
+#define KX_NALT ALT_T(KC_ENT)
+#define KX_ECTL CTL_T(KC_ESC)
+#define KX_SPAC LT(L_EXTEND, KC_SPC)
+
+#define KX_Z_MT CTL_T(KC_Z)
+#define KX_X_MT GUI_T(KC_X)
+#define KX_C_MT MT(MOD_LCTL | MOD_LALT, KC_C)
+#define KX_D_MT ALT_T(KC_D)
+
+#define KX_SLMT CTL_T(KC_SLSH)
+#define KX_DOMT GUI_T(KC_DOT)
+#define KX_COMT MT(MOD_LCTL | MOD_LALT, KC_COMM)
+#define KX_H_MT ALT_T(KC_H)
+
+#ifdef L_LL_R
+ #define KC_R_LT LT(L_LL_R, KC_R)
+#else
+ #define KC_R_LT KC_R
+#endif
+
+#ifdef L_LL_S
+ #define KC_S_LT LT(L_LL_S, KC_S)
+#else
+ #define KC_S_LT KC_S
+#endif
+
+#ifdef L_LL_E
+ #define KC_E_LT LT(L_LL_E, KC_E)
+#else
+ #define KC_E_LT KC_E
+#endif
+
+#ifdef L_LL_I
+ #define KC_I_LT LT(L_LL_I, KC_I)
+#else
+ #define KC_I_LT KC_I
+#endif
+
+// "Macro" functions
+enum userspace_custom_keycodes {
+ RJ_MAKE = SAFE_RANGE, // QMK make command
+ RJ_QMKV, // QMK version
+ RJ_EQ, // ==
+ RJ_NEQ, // !=
+ RJ_GEQ, // >=
+ RJ_LEQ, // <=
+ RJ_GEQR, // => ("greater than or equal - right")
+ RJ_DUND, // $_
+ RJ_SELS, // select * (used for PowerShell)
+ RJ_MUTE, // Discord mute (GUI+Shift+M)
+ RJ_DEAF, // Discord deafen (GUI+Shift+D)
+ RJ_DOVR // Toggle Discord overlay (GUI+Shift+O)
+};
+
+// Mouse keys
+#define M_UP KC_MS_UP
+#define M_DOWN KC_MS_DOWN
+#define M_LEFT KC_MS_LEFT
+#define M_RIGHT KC_MS_RIGHT
+#define M_LCLIK KC_MS_BTN1
+#define M_RCLIK KC_MS_BTN2
+#define M_MCLIK KC_MS_BTN3
+#define M_WHLUP KC_WH_U
+#define M_WHLDN KC_WH_D
+
+// Used in macro definitions
+#define TAP(code) register_code (code); unregister_code (code);
+
+// Tap Dance
+#ifdef TAP_DANCE_ENABLE
+#define TD_LAYER_TOGGLE 0
+extern void dance_layer(qk_tap_dance_state_t *state, void *user_data);
+#define TD_LAYR TD(TD_LAYER_TOGGLE)
+#endif // TAP_DANCE_ENABLE
diff --git a/users/replicaJunction/rules.mk b/users/replicaJunction/rules.mk
new file mode 100644
index 0000000000..30a330195d
--- /dev/null
+++ b/users/replicaJunction/rules.mk
@@ -0,0 +1 @@
+SRC += replicaJunction.c
diff --git a/users/romus/README.md b/users/romus/README.md
new file mode 100644
index 0000000000..0de9d9a817
--- /dev/null
+++ b/users/romus/README.md
@@ -0,0 +1,45 @@
+# overview
+
+ this is a modified version of let's split keyboard from bbaserdem. i don't like standard dvorak overuses right pinky
+ so i shifted the columns out. i'm not sure if this is any good, time will tell.
+
+ i have ortholinear let's split eh, which share a lot of functions with other ortholinear keyboards.
+
+# layout
+
+i use dvorak with an unorthodox off layout.
+if you wanna grab my code, and you used a layout with a persistent base
+layer change, change it to layer 0 before proceeding.
+
+# layers
+
+* **dvorak**: base layer,with dvorak layout.
+* **alternative**: has alternate characters.
+* **game**: toggled from *function*, comfortable for gaming use.
+* **numeric**: has numericals and symbols. can be locked.
+* **function**: layer has media and function keys.
+* **mouse**: manipulates mouse. can be locked.
+* **music** allows playing sounds.
+
+# functionality
+
+* **rgb backlight**: with layer indication, and ability to change base layer lighting mode.
+* **secrets**: by placing a secrets.h, and not tracking it, passwords can be stored.
+* **mouse**: mouse emulation, complete with diagonal keys.
+* **turkish**: an altgr-like overlay that allows some non-common letters, in unicode.
+
+i suggest checking out how i enabled turkish keys,
+how i planned out rgb lighting,
+and my mouse implementation;
+they might offer some insight into fringe user cases.
+
+# issues
+
+all features are too big for the 32kb bootloader.
+offenders are audio and rgb lights; it comes down to one or the other.
+
+~the proton board, and rev 6 might fix that.~
+
+# credits
+
+this is a modified version of let's split keyboard from bbaserdem who has previously written his keymap by himself before, but rewrote it here.
diff --git a/users/romus/config.h b/users/romus/config.h
new file mode 100644
index 0000000000..9332febe63
--- /dev/null
+++ b/users/romus/config.h
@@ -0,0 +1,8 @@
+#pragma once
+
+#ifdef TAP_DANCE_ENABLE
+ #define TAPPING_TERM 300
+ #define TAPPING_TOGGLE 1
+#endif
+
+// !USERSPACE_CONFIG_H
diff --git a/users/romus/romus.c b/users/romus/romus.c
new file mode 100644
index 0000000000..35b524f941
--- /dev/null
+++ b/users/romus/romus.c
@@ -0,0 +1,557 @@
+#include "romus.h"
+
+/*---------------*\
+|*-----MOUSE-----*|
+\*---------------*/
+#ifdef MOUSEKEY_ENABLE
+#include "mousekey.h"
+#endif
+
+/*-------------*\
+|*-----RGB-----*|
+\*-------------*/
+#ifdef RGBLIGHT_ENABLE
+#include "rgblight.h"
+#endif
+
+/*-------------*\
+|*---UNICODE---*|
+\*-------------*/
+#ifdef UNICODE_ENABLE
+#endif
+
+/*-----------------*\
+|*-----SECRETS-----*|
+\*-----------------*/
+// Enabled by adding a non-tracked secrets.h to this dir.
+#if (__has_include("secrets.h"))
+#include "secrets.h"
+#endif
+
+/*---------------*\
+|*-----MUSIC-----*|
+\*---------------*/
+#ifdef AUDIO_ENABLE
+float tone_game[][2] = SONG(ZELDA_PUZZLE);
+float tone_return[][2] = SONG(ZELDA_TREASURE);
+float tone_linux[][2] = SONG(UNICODE_LINUX);
+float tone_windows[][2] = SONG(UNICODE_WINDOWS);
+#endif
+
+/*-------------------*\
+|*-----TAP-DANCE-----*|
+\*-------------------*/
+#ifdef TAP_DANCE_ENABLE
+qk_tap_dance_action_t tap_dance_actions[] = {
+ // Shift on double tap of semicolon
+ [SCL] = ACTION_TAP_DANCE_DOUBLE( KC_SCLN, KC_COLN )
+};
+#endif
+
+/* In keymaps, instead of writing _user functions, write _keymap functions
+ * The __attribute__((weak)) allows for empty definitions here, and during
+ * compilation, if these functions are defined elsewhere, they are written
+ * over. This allows to include custom code from keymaps in the generic code
+ * in this file.
+ */
+__attribute__ ((weak)) void matrix_init_keymap(void) { }
+__attribute__ ((weak)) void matrix_scan_keymap(void) { }
+__attribute__ ((weak)) bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+__attribute__ ((weak)) uint32_t layer_state_set_keymap (uint32_t state) {
+ return state;
+}
+__attribute__ ((weak)) void led_set_keymap(uint8_t usb_led) { }
+
+/* ----------------------- *\
+ * -----RGB Functions----- *
+\* ----------------------- */
+#ifdef RGBLIGHT_ENABLE
+
+// Set RGBLIGHT state depending on layer
+void rgblight_change( uint8_t this_layer ) {
+ // Enable RGB light; will not work without this
+ //rgblight_enable_noeeprom();
+ // Change RGB light
+ switch ( this_layer ) {
+ case _DV:
+ // Load base layer
+ rgblight_disable_noeeprom();
+ break;
+ case _AL:
+ // Do yellow for alternate
+ rgblight_enable_noeeprom();
+ rgblight_sethsv_noeeprom( 60,255,255);
+
+
+ break;
+ case _GA:
+ // Do purple for game
+ rgblight_enable_noeeprom();
+ rgblight_sethsv_noeeprom(285,255,255);
+
+
+ break;
+ case _NU:
+ // Do azure for number
+ rgblight_enable_noeeprom();
+ rgblight_sethsv_noeeprom(186,200,255);
+
+
+ break;
+ case _SE:
+ // Do red for settings
+ rgblight_enable_noeeprom();
+
+ rgblight_sethsv_noeeprom( 16,255,255);
+
+ break;
+ case _MO:
+ // Do green for mouse
+ rgblight_enable_noeeprom();
+ rgblight_sethsv_noeeprom(120,255,255);
+
+
+ break;
+ case _MU:
+ // Do orange for music
+
+ rgblight_enable_noeeprom();
+ rgblight_sethsv_noeeprom( 39,255,255);
+
+ break;
+ default:
+ // Something went wrong
+ rgblight_enable_noeeprom();
+ rgblight_sethsv_noeeprom( 0,255,255);
+
+ break;
+ }
+}
+
+#endif
+
+/*---------------------*\
+|*-----MATRIX INIT-----*|
+\*---------------------*/
+void matrix_init_user (void) {
+
+ // Keymap specific things, do it first thing to allow for delays etc
+ matrix_init_keymap();
+
+ // Correct unicode
+#ifdef UNICODE_ENABLE
+ set_unicode_input_mode(UC_LNX);
+#endif
+
+ // Make beginning layer DVORAK
+ set_single_persistent_default_layer(_DV);
+
+}
+
+/*---------------------*\
+|*-----MATRIX SCAN-----*|
+\*---------------------*/
+void matrix_scan_user (void) {
+ // Keymap specific, do it first
+ matrix_scan_keymap();
+}
+
+/*------------------*\
+|*-----KEYCODES-----*|
+\*------------------*/
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+
+ // Shift check
+ bool is_capital = ( keyboard_report->mods & (MOD_BIT(KC_LSFT)|MOD_BIT(KC_RSFT)) );
+ static bool lock_flag = false;
+ uint8_t layer = biton32 (layer_state);
+
+ switch (keycode) {
+ // Secrets implementation
+#if (__has_include("secrets.h"))
+ case SECRET1:
+ if( !record->event.pressed ) {
+ send_string_P( secret[ keycode - SECRET1 ] );
+ }
+ return false;
+ break;
+ case SECRET2:
+ if( !record->event.pressed ) {
+ send_string_P( secret[ keycode - SECRET2 ] );
+ }
+ return false;
+ break;
+ case SECRET3:
+ if( !record->event.pressed ) {
+ send_string_P( secret[ keycode - SECRET3 ] );
+ }
+ return false;
+ break;
+#endif
+
+ // Lock functionality: These layers are locked if the LOCKED buttons are
+ // pressed. Otherwise, they are momentary toggles
+ case K_LOCK:
+ if (record->event.pressed) {
+ lock_flag = !lock_flag;
+ }
+ return false;
+ break;
+ case K_MOUSE:
+ if (record->event.pressed) {
+ layer_on(_MO);
+ lock_flag = false;
+ } else {
+ if ( lock_flag ) {
+ lock_flag = false;
+ } else {
+ layer_off(_MO);
+ }
+ }
+ return false;
+ break;
+ case K_NUMBR:
+ if (record->event.pressed) {
+ layer_on(_NU);
+ lock_flag = false;
+ } else {
+ if ( lock_flag ) {
+ lock_flag = false;
+ } else {
+ layer_off(_NU);
+ }
+ }
+ return false;
+ break;
+
+ // Layer switches with sound
+ case K_GAMES:
+ if (record->event.pressed) {
+ // On press, turn off layer if active
+ if ( layer == _GA ) {
+#ifdef AUDIO_ENABLE
+ stop_all_notes();
+ PLAY_SONG(tone_return);
+#endif
+ layer_off(_GA);
+ }
+ } else {
+ // After click, turn on layer if accessed from setting
+ if ( layer == _SE ) {
+#ifdef AUDIO_ENABLE
+ stop_all_notes();
+ PLAY_SONG(tone_game);
+#endif
+ layer_on(_GA);
+ layer_off(_SE);
+ }
+ }
+ return false;
+ break;
+ case MU_TOG:
+ if (record->event.pressed) {
+ // On press, turn off layer if active
+ if ( layer == _SE ) {
+ layer_off(_SE);
+ layer_on(_MU);
+ } else {
+ layer_off(_MU);
+ }
+ }
+ return true;
+ break;
+
+//------UNICODE
+ // Unicode switches with sound
+#ifdef UNICODE_ENABLE
+ case UNI_LI:
+ if (record->event.pressed) {
+#ifdef AUDIO_ENABLE
+ stop_all_notes();
+ PLAY_SONG(tone_linux);
+#endif
+ set_unicode_input_mode(UC_LNX);
+ }
+ return false;
+ break;
+ case UNI_WN:
+ if (record->event.pressed) {
+#ifdef AUDIO_ENABLE
+ stop_all_notes();
+ PLAY_SONG(tone_windows);
+#endif
+ set_unicode_input_mode(UC_WIN);
+ }
+ return false;
+ break;
+
+ // Turkish letters, with capital functionality
+ case TUR_A:
+ if (record->event.pressed) {
+ if ( is_capital ) {
+ unicode_input_start();
+ register_hex(0x00c2);
+ unicode_input_finish();
+ } else {
+ unicode_input_start();
+ register_hex(0x00e2);
+ unicode_input_finish();
+ }
+ }
+ return false;
+ break;
+ case TUR_O:
+ if (record->event.pressed) {
+ if ( is_capital ) {
+ unicode_input_start();
+ register_hex(0x00d6);
+ unicode_input_finish();
+ } else {
+ unicode_input_start();
+ register_hex(0x00f6);
+ unicode_input_finish();
+ }
+ }
+ return false;
+ break;
+ case TUR_U:
+ if (record->event.pressed) {
+ if ( is_capital ) {
+ unicode_input_start();
+ register_hex(0x00dc);
+ unicode_input_finish();
+ } else {
+ unicode_input_start();
+ register_hex(0x00fc);
+ unicode_input_finish();
+ }
+ }
+ return false;
+ break;
+ case TUR_I:
+ if (record->event.pressed) {
+ if ( is_capital ) {
+ unicode_input_start();
+ register_hex(0x0130);
+ unicode_input_finish();
+ } else {
+ unicode_input_start();
+ register_hex(0x0131);
+ unicode_input_finish();
+ }
+ }
+ return false;
+ break;
+ case TUR_G:
+ if (record->event.pressed) {
+ if ( is_capital ) {
+ unicode_input_start();
+ register_hex(0x011e);
+ unicode_input_finish();
+ } else {
+ unicode_input_start();
+ register_hex(0x011f);
+ unicode_input_finish();
+ }
+ }
+ return false;
+ break;
+ case TUR_C:
+ if (record->event.pressed) {
+ if ( is_capital ) {
+ unicode_input_start();
+ register_hex(0x00c7);
+ unicode_input_finish();
+ } else {
+ unicode_input_start();
+ register_hex(0x00e7);
+ unicode_input_finish();
+ }
+ }
+ return false;
+ break;
+ case TUR_S:
+ if (record->event.pressed) {
+ if ( is_capital ) {
+ unicode_input_start();
+ register_hex(0x015e);
+ unicode_input_finish();
+ } else {
+ unicode_input_start();
+ register_hex(0x015f);
+ unicode_input_finish();
+ }
+ }
+ return false;
+ break;
+#endif
+
+//-------Diagonal mouse movements
+#ifdef MOUSEKEY_ENABLE
+ case MO_NE:
+ if( record->event.pressed ) {
+ mousekey_on(MO_N);
+ mousekey_on(MO_E);
+ mousekey_send();
+ } else {
+ mousekey_off(MO_N);
+ mousekey_off(MO_E);
+ mousekey_send();
+ }
+ return false;
+ break;
+ case MO_NW:
+ if( record->event.pressed ) {
+ mousekey_on(MO_N);
+ mousekey_on(MO_W);
+ mousekey_send();
+ } else {
+ mousekey_off(MO_N);
+ mousekey_off(MO_W);
+ mousekey_send();
+ }
+ return false;
+ break;
+ case MO_SE:
+ if( record->event.pressed ) {
+ mousekey_on(MO_S);
+ mousekey_on(MO_E);
+ mousekey_send();
+ } else {
+ mousekey_off(MO_S);
+ mousekey_off(MO_E);
+ mousekey_send();
+ }
+ return false;
+ break;
+ case MO_SW:
+ if( record->event.pressed ) {
+ mousekey_on(MO_S);
+ mousekey_on(MO_W);
+ mousekey_send();
+ } else {
+ mousekey_off(MO_S);
+ mousekey_off(MO_W);
+ mousekey_send();
+ }
+ return false;
+ break;
+ case MO_S_NE:
+ if( record->event.pressed ) {
+ mousekey_on(MO_S_N);
+ mousekey_on(MO_S_E);
+ mousekey_send();
+ } else {
+ mousekey_off(MO_S_N);
+ mousekey_off(MO_S_E);
+ mousekey_send();
+ }
+ return false;
+ break;
+ case MO_S_NW:
+ if( record->event.pressed ) {
+ mousekey_on(MO_S_N);
+ mousekey_on(MO_S_W);
+ mousekey_send();
+ } else {
+ mousekey_off(MO_S_N);
+ mousekey_off(MO_S_W);
+ mousekey_send();
+ }
+ return false;
+ break;
+ case MO_S_SE:
+ if( record->event.pressed ) {
+ mousekey_on(MO_S_S);
+ mousekey_on(MO_S_E);
+ mousekey_send();
+ } else {
+ mousekey_off(MO_S_S);
+ mousekey_off(MO_S_E);
+ mousekey_send();
+ }
+ return false;
+ break;
+ case MO_S_SW:
+ if( record->event.pressed ) {
+ mousekey_on(MO_S_S);
+ mousekey_on(MO_S_W);
+ mousekey_send();
+ } else {
+ mousekey_off(MO_S_S);
+ mousekey_off(MO_S_W);
+ mousekey_send();
+ }
+ return false;
+ break;
+#endif
+
+//------DOUBLE PRESS, with added left navigation
+ case DBL_SPC:
+ if( record->event.pressed ) {
+ SEND_STRING(" "SS_TAP(X_LEFT));
+ }
+ return false;
+ break;
+ case DBL_ANG:
+ if( record->event.pressed ) {
+ SEND_STRING("<>"SS_TAP(X_LEFT));
+ }
+ return false;
+ break;
+ case DBL_PAR:
+ if( record->event.pressed ) {
+ SEND_STRING("()"SS_TAP(X_LEFT));
+ }
+ return false;
+ break;
+ case DBL_SQR:
+ if( record->event.pressed ) {
+ SEND_STRING("[]"SS_TAP(X_LEFT));
+ }
+ return false;
+ break;
+ case DBL_BRC:
+ if( record->event.pressed ) {
+ SEND_STRING("{}"SS_TAP(X_LEFT));
+ }
+ return false;
+ break;
+ case DBL_QUO:
+ if( record->event.pressed ) {
+ SEND_STRING("\'\'"SS_TAP(X_LEFT));
+ }
+ return false;
+ break;
+ case DBL_DQT:
+ if( record->event.pressed ) {
+ SEND_STRING("\"\""SS_TAP(X_LEFT));
+ }
+ return false;
+ break;
+ case DBL_GRV:
+ if( record->event.pressed ) {
+ SEND_STRING("``"SS_TAP(X_LEFT));
+ }
+ return false;
+ break;
+// END OF KEYCODES
+ }
+ return process_record_keymap(keycode, record);
+}
+
+/*----------------------*\
+|*-----LAYER CHANGE-----*|
+\*----------------------*/
+
+uint32_t layer_state_set_user(uint32_t state) {
+
+ state = layer_state_set_keymap (state);
+#ifdef RGBLIGHT_ENABLE
+ // Change RGB lighting depending on the last layer activated
+ rgblight_change( biton32(state) );
+#endif
+ return state;
+} \ No newline at end of file
diff --git a/users/romus/romus.h b/users/romus/romus.h
new file mode 100644
index 0000000000..265c942e92
--- /dev/null
+++ b/users/romus/romus.h
@@ -0,0 +1,272 @@
+// This is a modified version of Let's Split keyboard from bbaserdem
+
+#pragma once
+
+#include "quantum.h"
+
+// Use 7 wide characters for keymaps
+#define _______ KC_TRNS
+#define XXX KC_NO
+
+// Layers
+#define _DV 0 // Base layer
+#define _AL 1 // Alt char overlay
+#define _GA 2 // Game layer
+#define _NU 3 // Numbers layer
+#define _SE 4 // Settings layer
+#define _MO 5 // Mouse emulation
+#define _MU 6 // Music mode
+
+// Define short macros
+#define UNDO LCTL(KC_Z)
+#define REDO LCTL(KC_Y)
+#define COPY LCTL(KC_C)
+#define CUT LCTL(KC_X)
+#define PASTE LCTL(KC_V)
+#define EXIT LALT(KC_F4)
+#define CAPS SFT_T(KC_CAPS)
+
+
+// Rename mouse keys with 7 letters
+#ifdef MOUSEKEY_ENABLE
+#define MO_S_N KC_MS_WH_UP
+#define MO_S_S KC_MS_WH_DOWN
+#define MO_S_E KC_MS_WH_RIGHT
+#define MO_S_W KC_MS_WH_LEFT
+#define MO_N KC_MS_UP
+#define MO_S KC_MS_DOWN
+#define MO_E KC_MS_RIGHT
+#define MO_W KC_MS_LEFT
+#define MO_CL_L KC_MS_BTN1
+#define MO_CL_R KC_MS_BTN2
+#define MO_CL_M KC_MS_BTN3
+#define MO_CL_4 KC_MS_BTN4
+#define MO_CL_5 KC_MS_BTN5
+#define MO_AC_0 KC_MS_ACCEL0
+#define MO_AC_1 KC_MS_ACCEL1
+#define MO_AC_2 KC_MS_ACCEL2
+#else
+#define MO_S_N KC_NO
+#define MO_S_S KC_NO
+#define MO_S_E KC_NO
+#define MO_S_W KC_NO
+#define MO_N KC_NO
+#define MO_S KC_NO
+#define MO_E KC_NO
+#define MO_W KC_NO
+#define MO_CL_L KC_NO
+#define MO_CL_R KC_NO
+#define MO_CL_M KC_NO
+#define MO_CL_1 KC_NO
+#define MO_CL_2 KC_NO
+#define MO_AC_0 KC_NO
+#define MO_AC_1 KC_NO
+#define MO_AC_2 KC_NO
+#endif
+
+// Rename music keys with <8 letters
+#ifdef AUDIO_ENABLE
+#define MU_REC KC_LCTL
+#define MU_STOP KC_LALT
+#define MU_PLAY KC_LGUI
+#define MU_PLAY KC_LGUI
+#define MU_FAST KC_UP
+#define MU_SLOW KC_DOWN
+#define MU_MASK KC_A
+#else
+#define MU_REC KC_NO
+#define MU_STOP KC_NO
+#define MU_PLAY KC_NO
+#define MU_PLAY KC_NO
+#define MU_FAST KC_NO
+#define MU_SLOW KC_NO
+#define MU_MASK KC_NO
+#endif
+
+// Define non-capitalized UTF shortcuts here
+#ifdef UNICODE_ENABLE
+#define PHY_HBR UC(0x0127)
+#define PHY_DEG UC(0x00b0)
+#define CUR_LIR UC(0x20ba)
+#define CUR_BIT UC(0x20bf)
+#define CUR_EUR UC(0x20ac)
+#define CUR_BPN UC(0x00a3)
+#define CUR_YEN UC(0x00a5)
+#else
+#define PHY_HBR KC_NO
+#define PHY_DEG KC_NO
+#define CUR_LIR KC_NO
+#define CUR_BIT KC_NO
+#define CUR_EUR KC_NO
+#define CUR_BPN KC_NO
+#define CUR_YEN KC_NO
+#endif
+
+// Custom keycodes
+enum userspace_custom_keycodes {
+ // Turkish letters, with shifting
+ TUR_A = SAFE_RANGE,
+ TUR_C,
+ TUR_G,
+ TUR_I,
+ TUR_O,
+ TUR_S,
+ TUR_U,
+ // Unicode mode switch
+ UNI_LI,
+ UNI_WN,
+ // Double keys
+ DBL_SPC,
+ DBL_ANG,
+ DBL_PAR,
+ DBL_SQR,
+ DBL_BRC,
+ DBL_QUO,
+ DBL_DQT,
+ DBL_GRV,
+ // Diagonal mouse movements
+ MO_NE,
+ MO_NW,
+ MO_SE,
+ MO_SW,
+ MO_S_NE,
+ MO_S_NW,
+ MO_S_SE,
+ MO_S_SW,
+ // Layer switches and lock functionality
+ K_MOUSE,
+ K_NUMBR,
+ K_LOCK,
+ K_GAMES,
+ // Secret macros
+ SECRET1,
+ SECRET2,
+ SECRET3
+};
+
+// Do tap dancable semicolon key if available
+#ifdef TAP_DANCE_ENABLE
+enum {
+ SCL = 0
+};
+#define MY_SCL TD(SCL)
+#else
+#define MY_SCL KC_SCLN
+#endif
+
+// Shared keymaps
+#define LAYOUT_planck_wrapper(...) LAYOUT_planck_grid(__VA_ARGS__)
+#define LAYOUT_letssplit_wrapper(...) LAYOUT_ortho_4x12(__VA_ARGS__)
+
+/* Dvorak
+ * ,------------------------------------------------------------------------.
+ * | ' " | , | . | P | Y | Esc || Del | F | G | C | R | L |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | A | O | E | U | I | Bkp || Ent | D | H | T | N | S |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | ; : | Q | J | K | X | Spc || SET | B | M | W | V | Z |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | Ctrl| OS | Alt | Tab | Cps | ACH || SYM | Spc | Lft | Up | Dwn | Rght|
+ * `------------------------------------------------------------------------' */
+#define DVORAK \
+ KC_QUOT,KC_COMM,KC_DOT, KC_P, KC_Y, KC_ESC, KC_DEL, KC_F, KC_G, KC_C, KC_R, KC_L, \
+ KC_A, KC_O, KC_E, KC_U, KC_I, KC_BSPC,KC_ENT, KC_D, KC_H, KC_T, KC_N, KC_S, \
+ MY_SCL, KC_Q, KC_J, KC_K, KC_X, KC_SPC, MO(_SE),KC_B, KC_M, KC_W, KC_V, KC_Z, \
+ KC_LCTL,KC_LGUI,KC_LALT,KC_TAB, CAPS, MO(_AL),K_NUMBR,KC_SPC, KC_LEFT,KC_UP, KC_DOWN,KC_RGHT
+
+/* Alternative character overlay
+ * ,------------------------------------------------------------------------.
+ * | ` ~ | ' ' | " " | Euro|Pound| || Del | Home| PgUp| Prn | \ | | / ? |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | Redo| < > | ( ) | [ ] | { } | Alt || Ins | End |PgDwn| Scl | BTC | - _ |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | Undo| Cut | Copy|Paste| EXIT| Shf || | | | | Yen | = + |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | | | | | | || | | | | | |
+ * `------------------------------------------------------------------------' */
+#define ALTCHAR \
+ KC_GRV, DBL_QUO,DBL_DQT,CUR_EUR,CUR_BPN,_______,_______,KC_HOME,KC_PGUP,KC_PSCREEN, KC_BSLASH, KC_SLSH, \
+ REDO, DBL_ANG,DBL_PAR,DBL_SQR,DBL_BRC,KC_LALT,KC_INS, KC_END, KC_PGDN,KC_SCROLLLOCK, CUR_BIT, KC_MINUS, \
+ UNDO, CUT, COPY, PASTE, EXIT, KC_LSFT,_______,_______,_______,_______, CUR_YEN, KC_EQUAL, \
+ _______,_______,_______,_______,_______,_______,_______,DBL_SPC,_______,_______, _______, _______
+
+/* Game layer
+ * ,------------------------------------------------------------------------.
+ * | OFF | Q | W | E | R | T || Esc | 7 | 8 | 9 |NumLk|Bkspc|
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | Tab | A | S | D | F | G || F1 | 4 | 5 | 6 | \ | Ent |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | Shf | Z | X | C | V | B || F2 | 1 | 2 | 3 | ^ | MSE |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | Ctrl| Alt | / | ` | SYM | Spc || F5 | Ent | 0 | < | v | > |
+ * `------------------------------------------------------------------------' */
+#define GAME \
+ K_GAMES,KC_Q, KC_W, KC_E, KC_R, KC_T, KC_ESC, KC_P7, KC_P8, KC_P9, KC_NLCK,KC_BSPC, \
+ KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_F1, KC_P4, KC_P5, KC_P6, KC_BSLS,KC_ENT , \
+ KC_LSFT,KC_Z, KC_X, KC_C, KC_V, KC_B, KC_F2, KC_P1, KC_P2, KC_P3, KC_UP,K_MOUSE, \
+ KC_LCTL,KC_LALT,KC_SLSH,KC_GRV, K_NUMBR,KC_SPC, KC_F5, KC_ENT, KC_P0, KC_LEFT,KC_DOWN,KC_RGHT
+
+/* Symbols layer
+ * ,------------------------------------------------------------------------.
+ * | OFF | ` | ~ | \ | [ | { || } | ] | - | _ | = | + |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | 1 | 2 | 3 | 4 | 5 | || LCK | 6 | 7 | 8 | 9 | 0 |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | ! | @ | # | $ | % | ||Vol +| ^ | & | * | ( | ) |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | | | | | | | || | | | | | |
+ * `------------------------------------------------------------------------' */
+#define NUMBERS \
+ K_NUMBR,KC_GRV, KC_TILD,KC_BSLS,KC_LBRC,KC_LCBR,KC_RCBR,KC_RBRC,KC_MINS,KC_UNDS,KC_EQL, KC_PLUS, \
+ KC_1, KC_2, KC_3, KC_4, KC_5, _______,K_LOCK, KC_6, KC_7, KC_8, KC_9, KC_0, \
+ KC_EXLM,KC_AT, KC_HASH,KC_DLR, KC_PERC,_______,KC_VOLU,KC_CIRC,KC_AMPR,KC_ASTR,KC_LPRN,KC_RPRN, \
+ KC_PIPE,_______,_______,_______,_______,_______,_______,_______,_______,_______,_______,_______
+
+/* Settings layer
+ * ,------------------------------------------------------------------------.
+ * |BLLed| F1 | F2 | F3 | F4 | Lin || Win | Wake| |Hue -|Hue +|Reset|
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | | F5 | F6 | F7 | F8 | ||Vol 0| |RGBto|Sat -|Sat +| |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | Game| F9 | F10 | F11 | F12 |Vol 0|| |PrtSc|RGBan|Bri -|Bri +| |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * |Musir| | | | |Vol +||Vol -| Prev| Stop|TogMu| Next| |
+ * `------------------------------------------------------------------------' */
+#define SETTINGS \
+ BL_STEP,KC_F1, KC_F2, KC_F3, KC_F4, UNI_LI, UNI_WN, KC_WAKE,_______,RGB_HUD,RGB_HUI,RESET , \
+ _______,KC_F5, KC_F6, KC_F7, KC_F8, _______,KC_MUTE,_______,RGB_TOG,RGB_SAD,RGB_SAI,_______, \
+ K_GAMES,KC_F9, KC_F10, KC_F11, KC_F12, KC_MUTE,_______,KC_PSCR,RGB_MOD,RGB_VAD,RGB_VAI,_______, \
+ MU_TOG, _______,_______,_______,_______,KC_VOLU,KC_VOLD,KC_MPRV,KC_MSTP,KC_MPLY,KC_MNXT,_______
+
+/* Mouse layer
+ * ,------------------------------------------------------------------------.
+ * |Ulock| \ | ^ | / |.....|.....||.....|.....| |\|.| |^| | |/|.| |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | | < | Mid | > |Btn 4|.....||.....|Btn 5| <-- | Mid | --> | |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | | / | v | \ |.....|.....||.....|.....| |/| | |v| | |\| | LCK |
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | | | | | | Left||Right| | |Accl0|Accl1|Accl2|
+ * `------------------------------------------------------------------------' */
+#define MOUSE \
+ K_MOUSE,MO_NW, MO_N, MO_NE, XXX, XXX ,XXX, XXX, MO_S_NW,MO_S_N, MO_S_NE,_______, \
+ _______,MO_W, MO_CL_M,MO_E, MO_CL_4,XXX ,XXX, MO_CL_5,MO_S_W, MO_CL_M,MO_S_E, _______, \
+ _______,MO_SW, MO_S, MO_SE, XXX, XXX ,XXX, XXX, MO_S_SW,MO_S_S, MO_S_SE,K_LOCK , \
+ _______,_______,_______,_______,_______,MO_CL_L,MO_CL_R,_______,MO_AC_0,MO_AC_1,MO_AC_2,_______
+
+/* Music layer
+ * ,------------------------------------------------------------------------.
+ * |.....|.....|.....|.....|.....|.....||.....|.....|.....|.....|.....|.....|
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * |.....|.....|.....|.....|.....|.....||.....|.....|.....|.....|.....|.....|
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * |.....|.....|.....|.....|.....|.....||.....|.....|.....|.....|.....|.....|
+ * |-----+-----+-----+-----+-----+-----++-----+-----+-----+-----+-----+-----|
+ * | togg| rec | stop| play| slow| fast||modes|.....|.....|.....|.....|.....|
+ * `------------------------------------------------------------------------'
+ */
+#define MUSIC \
+ MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK, \
+ MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK, \
+ MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK, \
+ MU_TOG, MU_REC, MU_STOP,MU_PLAY,MU_SLOW,MU_FAST,MU_MOD, MU_MASK,MU_MASK,MU_MASK,MU_MASK,MU_MASK
diff --git a/users/romus/rules.mk b/users/romus/rules.mk
new file mode 100644
index 0000000000..78ce2e93f4
--- /dev/null
+++ b/users/romus/rules.mk
@@ -0,0 +1,24 @@
+SRC += romus.c
+EXTRAFLAGS += -flto # Used to make code smaller
+
+# ENABLE
+UNICODE_ENABLE = yes # Used for unicode character emulation
+EXTRAKEY_ENABLE = yes # OS signals like volume control
+
+# DISABLE
+ifndef BLUETOOTH_ENABLE
+ BLUETOOTH_ENABLE = no # No bluetooth
+endif
+COMMAND_ENABLE = no # Some bootmagic thing i dont use
+BOOTMAGIC_ENABLE = no # Access to EEPROM settings, not needed
+CONSOLE_ENABLE = no # Allows console output with a command
+SLEEP_LED_ENABLE = no # Breathes LED's when computer is asleep. Untested.
+NKRO_ENABLE = no # Default is 6KRO which is plenty
+MIDI_ENABLE = no # Untested feature
+FAUXCLICKY_ENABLE = no # Emulates clicks using speaker
+KEY_LOCK_ENABLE = no # Allows locking any key. Not used
+API_SYSEX_ENABLE = no # Allows OS to send signals.
+
+
+# Disabling this makes it compile, i dont know why
+# VARIABLE_TRACE = no # Allows debugging variables
diff --git a/users/sigma/config.h b/users/sigma/config.h
new file mode 100644
index 0000000000..53b986cdac
--- /dev/null
+++ b/users/sigma/config.h
@@ -0,0 +1,21 @@
+/*
+ Copyright 2018 Yann Hodique <yann.hodique@gmail.com> @sigma
+
+ 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, either version 2 of the License, or
+ (at your option) any later version.
+
+ 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/>.
+*/
+#pragma once
+
+#define LEADER_TIMEOUT 1000
+
+#define MACRO_TIMER 5
diff --git a/users/sigma/rules.mk b/users/sigma/rules.mk
new file mode 100644
index 0000000000..a4cd2b34d3
--- /dev/null
+++ b/users/sigma/rules.mk
@@ -0,0 +1,3 @@
+LEADER_ENABLE = yes
+
+SRC += sigma.c
diff --git a/users/sigma/sigma.c b/users/sigma/sigma.c
new file mode 100644
index 0000000000..b2bf40d576
--- /dev/null
+++ b/users/sigma/sigma.c
@@ -0,0 +1,276 @@
+/*
+ Copyright 2018 Yann Hodique <yann.hodique@gmail.com> @sigma
+
+ 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, either version 2 of the License, or
+ (at your option) any later version.
+
+ 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 "sigma.h"
+
+userspace_config_t runtime_userspace_config;
+userspace_config_t stored_userspace_config;
+
+__attribute__ ((weak))
+void matrix_init_keymap(void) {}
+
+__attribute__ ((weak))
+void startup_keymap(void) {}
+
+__attribute__ ((weak))
+void shutdown_keymap(void) {}
+
+__attribute__ ((weak))
+void suspend_power_down_keymap(void) {}
+
+__attribute__ ((weak))
+void suspend_wakeup_init_keymap(void) {}
+
+__attribute__ ((weak))
+void matrix_scan_keymap(void) {}
+
+__attribute__ ((weak))
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
+__attribute__ ((weak))
+bool process_record_secrets(uint16_t keycode, keyrecord_t *record) {
+ return true;
+}
+
+
+__attribute__ ((weak))
+uint32_t layer_state_set_keymap (uint32_t state) {
+ return state;
+}
+
+__attribute__ ((weak))
+uint32_t default_layer_state_set_keymap (uint32_t state) {
+ return state;
+}
+
+__attribute__ ((weak))
+void led_set_keymap(uint8_t usb_led) {}
+
+void set_os(uint8_t os) {
+ runtime_userspace_config.os_target = os;
+
+ switch (os) {
+ case _OS_MACOS:
+ set_unicode_input_mode(UC_OSX);
+ break;
+ case _OS_LINUX:
+ set_unicode_input_mode(UC_LNX);
+ break;
+ case _OS_WINDOWS:
+ set_unicode_input_mode(UC_WIN);
+ break;
+ }
+}
+
+void matrix_init_user(void) {
+ stored_userspace_config.raw = eeconfig_read_user();
+ runtime_userspace_config.raw = stored_userspace_config.raw;
+
+ set_os(runtime_userspace_config.os_target);
+}
+
+void store_userspace_config(void) {
+ eeconfig_update_user(stored_userspace_config.raw);
+}
+
+LEADER_EXTERNS();
+
+void matrix_scan_user(void) {
+ LEADER_DICTIONARY() {
+ leading = false;
+ leader_end();
+
+ SEQ_TWO_KEYS(KC_F1, KC_L) {
+ set_os(_OS_LINUX);
+ }
+ SEQ_TWO_KEYS(KC_F1, KC_M) {
+ set_os(_OS_MACOS);
+ }
+ SEQ_TWO_KEYS(KC_F1, KC_W) {
+ set_os(_OS_WINDOWS);
+ }
+ SEQ_TWO_KEYS(KC_F1, KC_S) {
+ stored_userspace_config.raw = runtime_userspace_config.raw;
+ store_userspace_config();
+ }
+ }
+}
+
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+ uint8_t os_target = runtime_userspace_config.os_target;
+ bool pressed = record->event.pressed;
+
+ switch (keycode) {
+ case KC_QWERTY:
+ if (pressed) {
+ set_single_persistent_default_layer(_QWERTY);
+ }
+ return false;
+ break;
+
+ case KC_MAKE: // Compiles the firmware, and adds the flash command based on keyboard bootloader
+ if (!pressed) {
+ send_string_with_delay_P(PSTR("make " QMK_KEYBOARD ":" QMK_KEYMAP
+#if defined(__ARM__)
+ ":dfu-util"
+#elif defined(BOOTLOADER_DFU)
+ ":dfu"
+#elif defined(BOOTLOADER_HALFKAY)
+ ":teensy"
+#elif defined(BOOTLOADER_CATERINA)
+ ":avrdude"
+#endif // bootloader options
+ SS_TAP(X_ENTER)), 10);
+ }
+ return false;
+ break;
+
+ case EPRM: // Resets EEPROM
+ if (pressed) {
+ eeconfig_init();
+ default_layer_set(1UL<<eeconfig_read_default_layer());
+ layer_state_set(layer_state);
+ set_os(_OS_MACOS);
+ store_userspace_config();
+ }
+ return false;
+ break;
+ case VRSN: // Prints firmware version
+ if (pressed) {
+ send_string_with_delay_P(PSTR(QMK_KEYBOARD "/" QMK_KEYMAP " @ " QMK_VERSION ", Built on: " QMK_BUILDDATE), MACRO_TIMER);
+ }
+ return false;
+ break;
+
+ case KC_OS_CUT:
+ switch (os_target) {
+ case _OS_MACOS:
+ if (pressed)
+ SEND_STRING(SS_LGUI("x"));
+ break;
+ case _OS_LINUX:
+ pressed ?
+ register_code(KC_CUT)
+ : unregister_code(KC_CUT);
+ break;
+ default:
+ if (pressed)
+ SEND_STRING(SS_LCTRL("x"));
+ break;
+ }
+ break;
+
+ case KC_OS_COPY:
+ switch (os_target) {
+ case _OS_MACOS:
+ if (pressed)
+ SEND_STRING(SS_LGUI("c"));
+ break;
+ case _OS_LINUX:
+ pressed ?
+ register_code(KC_COPY)
+ : unregister_code(KC_COPY);
+ break;
+ default:
+ if (pressed)
+ SEND_STRING(SS_LCTRL("c"));
+ break;
+ }
+ break;
+
+ case KC_OS_PASTE:
+ switch (os_target) {
+ case _OS_MACOS:
+ if (pressed)
+ SEND_STRING(SS_LGUI("v"));
+ break;
+ case _OS_LINUX:
+ pressed ?
+ register_code(KC_PASTE)
+ : unregister_code(KC_PASTE);
+ break;
+ default:
+ if (pressed)
+ SEND_STRING(SS_LCTRL("v"));
+ break;
+ }
+ break;
+
+ case KC_OS_UNDO:
+ switch (os_target) {
+ case _OS_MACOS:
+ if (pressed)
+ SEND_STRING(SS_LGUI("z"));
+ break;
+ case _OS_LINUX:
+ pressed ?
+ register_code(KC_UNDO)
+ : unregister_code(KC_UNDO);
+ break;
+ default:
+ if (pressed)
+ SEND_STRING(SS_LCTRL("z"));
+ break;
+ }
+ break;
+
+ case KC_OS_REDO:
+ switch (os_target) {
+ case _OS_MACOS:
+ if (pressed)
+ SEND_STRING(SS_LGUI(SS_LSFT("z")));
+ break;
+ case _OS_LINUX:
+ pressed ?
+ register_code(KC_AGAIN)
+ : unregister_code(KC_AGAIN);
+ break;
+ default:
+ if (pressed)
+ SEND_STRING(SS_LCTRL(SS_LSFT("z")));
+ break;
+ }
+ break;
+
+ case KC_OS_LOCK:
+ switch (os_target) {
+ case _OS_MACOS:
+ if (pressed)
+ SEND_STRING(SS_LGUI(SS_LCTRL("q")));
+ break;
+ case _OS_LINUX:
+ pressed ?
+ register_code(KC_PWR)
+ : unregister_code(KC_PWR);
+ break;
+ default:
+ if (pressed)
+ SEND_STRING(SS_LGUI("l"));
+ break;
+ }
+ break;
+
+ case KC_SCRT:
+ if (pressed) {
+ SEND_STRING(SS_LGUI("`"));
+ }
+ break;
+ }
+
+ return process_record_keymap(keycode, record);
+}
diff --git a/users/sigma/sigma.h b/users/sigma/sigma.h
new file mode 100644
index 0000000000..e47e889b8c
--- /dev/null
+++ b/users/sigma/sigma.h
@@ -0,0 +1,58 @@
+/*
+ Copyright 2018 Yann Hodique <yann.hodique@gmail.com> @sigma
+
+ 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, either version 2 of the License, or
+ (at your option) any later version.
+
+ 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/>.
+*/
+#pragma once
+
+#include "quantum.h"
+#include "version.h"
+#include "eeprom.h"
+
+// Define os types
+enum os_types
+ {
+ _OS_MACOS = 0,
+ _OS_LINUX,
+ _OS_WINDOWS,
+ };
+
+// Define layer names
+enum userspace_layers
+ {
+ _QWERTY = 0,
+ };
+
+typedef union {
+ uint32_t raw;
+ struct {
+ uint8_t os_target :2;
+ };
+} userspace_config_t;
+
+enum userspace_custom_keycodes
+ {
+ EPRM = SAFE_RANGE, // Resets EEPROM
+ VRSN, // Prints QMK Firmware and board info
+ KC_QWERTY, // Sets default layer to QWERTY
+ KC_MAKE, // Rebuild the current firmware
+ KC_OS_CUT,
+ KC_OS_COPY,
+ KC_OS_PASTE,
+ KC_OS_UNDO,
+ KC_OS_REDO,
+ KC_OS_LOCK,
+ KC_SCRT,
+ NEW_SAFE_RANGE //use NEW_SAFE_RANGE for keymap specific codes
+ };
diff --git a/users/spacebarracecar/config.h b/users/spacebarracecar/config.h
new file mode 100644
index 0000000000..e69de29bb2
--- /dev/null
+++ b/users/spacebarracecar/config.h
diff --git a/users/spacebarracecar/readme.md b/users/spacebarracecar/readme.md
new file mode 100644
index 0000000000..172764c074
--- /dev/null
+++ b/users/spacebarracecar/readme.md
@@ -0,0 +1,111 @@
+# SpacebarRacecar Userspace
+
+The main purpose of this userspace is to keep my personal keymaps clean by moving shared code in here and also allowing me to easily change all my keymaps at once. However it also contains code that might be interesting to QMK Users living in Germany. Most of this code will be explained here.
+
+
+## US Layout Keys for German PCs
+
+I'm using the US Ansi layout however I'm living in Germany which means that every PC here has its input language set to German. My goal was to create custom keycodes that emulate the US Keys so that I can plug my keyboards into any German PC and have them working without changing any settings.
+
+### How to use
+
+- To activate the custom keycodes set GERMAN_ENABLE = yes in the keyboards rules.mk file.
+- The keycodes are listed and explained in [spacebarracecar.h](spacebarracecar.h) under `enum userspace_custom_keycodes`.
+- The keycodes are handled by the `process_record_user` function which is now located in [spacebarracecar.c](spacebarracecar.c). To change keyboard specific configuration `process_record_keymap` is used (see [drashna userspace readme](../drashna/readme.md) for better explanation).
+- There is a predefined `_DEADKEY` layer in [spacebarracecar.h](spacebarracecar.h) under `enum userspace_layers`. Shifted CU_QUOT enables the dead key layer, just like KC_QUOT would when using the US International layout. (See `enum userspace_custom_keycodes` for more explanation).
+- On Windows grave and circonflexe are defined as dead keys when using the standard german layout. Those are automatically escaped when using the custom keycodes. `CU_ESCT` can be used to enable/disable this behavior.
+- For a complete example see my [fc660c](../../keyboards/fc660c/keymaps/spacebarracecar/keymap.c) or [planck](../../keyboards/planck/keymaps/spacebarracecar/keymap.c) keymaps.
+
+### How it works
+
+Creating the custom keycodes was not a trivial task because it is necessary that they are able to send different keycodes depending on the physical shift state. Also the shift state of the actual send keycodes has to be completely independent of the physical shift state. At the same time it has to be ensured that shift never gets stuck or disabled accidentaly.
+
+(Shift state: If shift keycode is registered; Physical shift state: If shift key is actually pressed)
+
+Here is an example for a custom *US Equal* keycode that illustrates the problem:
+
+| Physical Shift State | Custom keycode | Actual send keycodes |
+|----------------------|----------------|----------------------|
+| Unshifted | = | Shifted DE_0 |
+| Shifted | + | Unshifted DE_PLUS |
+
+#### Tracking the physical shift state
+
+To track the physical shift state there are two custom left and right shift keycodes `CU_LSFT` and `CU_RSFT`. These track the current physical shift state using two booleans `lshift` and `rshift`. To make things easier both custom shifts use KC_LSFT. A space cadet shift functionality is also included. The preexisting space cadet shift implementation could not be used because it doesn't reset when custom keycodes are pressed and therefore produces unwated parenthesis.
+
+#### Custom keycode templates
+
+To ease the creation of custom keycodes there are a few templates defined in [spacebarracecar.h](spacebarracecar.h).
+
+- `SHIFT_NORM(kc1, kc2)` Sends independent keycodes kc1 and kc2 depending on physical shift state without changing shift state.
+- `SHIFT_SWITCH(kc1, kc2)` Sends independent keycodes kc1 and kc2 depending on physical shift state while flipping shift state.
+- `SHIFT_ALL(kc1, kc2)` Sends independent keycodes kc1 and kc2 depending on physical shift state while always sending shift.
+- `SHIFT_NO(kc1, kc2)` Sends independent keycodes kc1 and kc2 depending on physical shift state while never sending shift.
+- `SHIFT_ALGR(kc1, kc2)` Sends independent keycodes kc1 and kc2 depending on physical shift state while never sending shift and always sending ralt.
+- `UML(kc)` Sends keycode kc without changing shift state and then escapes the `_DEADKEY` layer.
+
+Here is `SHIFT_NORM` as an example:
+```c
+#define SHIFT_NORM(kc1, kc2) \
+if (record->event.pressed) { \
+ timer_timeout(); \
+ if (lshift || rshift) { \
+ register_code(KC_LSFT); \
+ unregister_code(kc2); \
+ register_code(kc2); \
+ add_to_prev(kc2); \
+ } else { \
+ unregister_code(KC_LSFT); \
+ unregister_code(kc1); \
+ register_code(kc1); \
+ } \
+} else { \
+ unregister_code(kc1); \
+ unregister_code(kc2); \
+} \
+return false;
+```
+
+It is noticeable that before registering a keycode the same keycode gets unregistered first. The reason for this is that there can now be two physical keys that use the same keycode only with different shift states. When rolling those two keys the keycode has to be unregistered first, otherwise the second key doesn't register. Also noticable is that sometimes the `add_to_prev` function is called. This will be explained later. The `timer_timeout` function is necessary to reset the timers of the custom space cadet shift functionality.
+
+It's worth mentioning that `SHIFT_ALGR` unlike the other templates doesn't allow repetition of characters when held. This is because it would otherwise require extensive checking of physical ralt status similar to shift to prevent ralt from getting stuck.
+
+#### Ensuring that shift state is always correct when pressing normal keycodes
+
+To ensure that non custom keycodes always get send with the correct shift state the default case in `process_record_user` includes a physical shift check that sets shift accordingly before registering the keycode. Also `timer_timeout` is always called to reset the space cadet shift timers to prevent unwanted parenthesis.
+
+```c
+default:
+ if(record->event.pressed) {
+ timer_timeout();
+
+ #ifdef GERMAN_ENABLE
+ if (lshift || rshift)
+ register_code(KC_LSFT);
+ else
+ unregister_code(KC_LSFT);
+ #endif
+
+ }
+ return process_record_keymap(keycode, record);
+```
+
+#### Ensuring that custom keycodes always produce the correct character
+
+When very specific key combinations that include custom keycodes and/or shift are pressed it can happen that wrong characters are produced due to changing shift states. The previously mentioned `add_to_prev` function is there to prevent that. It can be used to add a keycode to the `prev_kcs` array that can hold up to 6 keycodes. On various occasions, but mainly when shift is released `unreg_prev` is called, which then unregisters all saved keycodes.
+
+For real use this is probably not needed, but it doesn't hurt either.
+
+#### Adapting the templates for other languages
+
+In theory the templates can be used to create custom keycodes that map any layout to any other layout.
+
+## Other stuff
+
+### Custom Nav/Esc Key
+
+Since I'm always using a navigation layer with all my keyboards there is a `_NAV` layer predefined in [spacebarracecar.h](spacebarracecar.h) under `enum userspace_layers`. In addition to that I wanted to have a keycode that activates the navigation layer when held, but acts as Escape when pressed. In QMK there already exists `LT(layer, kc)`, however I found that there is some amount of lag before the layer is actived. Therefore I created a custom keycode CU_NAV that does the same without lag using a custom timer. Since I already need timers for the custom space cadet shift implementing this was very easy by adding the timer to the `timer_timeout` function.
+
+### Gamemode
+
+The userspace includes the custom keycode `CU_GAME` that is used to flip a boolean variable called `game`. That variable is used to enable/disable windows keys and space cadet shift. In my [planck keymap](../../keyboards/planck/keymaps/spacebarracecar/keymap.c) it also makes Lower act like Space which is more comfortable when resting on wasd and it could also be used to change various other things when gaming.
diff --git a/users/spacebarracecar/rules.mk b/users/spacebarracecar/rules.mk
new file mode 100644
index 0000000000..319e887ae3
--- /dev/null
+++ b/users/spacebarracecar/rules.mk
@@ -0,0 +1,5 @@
+SRC += spacebarracecar.c
+
+ifeq ($(strip $(GERMAN_ENABLE)), yes)
+ OPT_DEFS += -DGERMAN_ENABLE
+endif
diff --git a/users/spacebarracecar/spacebarracecar.c b/users/spacebarracecar/spacebarracecar.c
new file mode 100644
index 0000000000..130d7dc2d4
--- /dev/null
+++ b/users/spacebarracecar/spacebarracecar.c
@@ -0,0 +1,342 @@
+#include "spacebarracecar.h"
+
+#ifdef GERMAN_ENABLE
+// These indicate if left and right shift are physically pressed
+bool lshift = false;
+bool rshift = false;
+
+// Interrupt and times for space cadet shift
+bool lshiftp = false;
+bool rshiftp = false;
+uint16_t lshift_timer = 0;
+uint16_t rshift_timer = 0;
+
+// Number of items that are saved in prev_kcs
+uint8_t prev_indx = 0;
+// Used to save the last 6 actual keycodes activated by frankenkeycodes
+uint16_t prev_kcs[6] = {0, 0, 0, 0, 0, 0};
+
+// If true the deadkey characters grave and circonflexe are not automatically escaped
+bool esct = false;
+
+/*
+Used to add a keycode to a prev_kcs to remember it.
+When full the last code gets discarded and replaced by
+the new one.
+*/
+void add_to_prev(uint16_t kc){
+ for (int i=0; i<prev_indx; i++){
+ if (kc == prev_kcs[i])
+ return;
+ }
+ if (prev_indx == 6){
+ for (int i=5; i>0; i--){
+ prev_kcs[i] = prev_kcs[i-1];
+ }
+ prev_kcs[0] = kc;
+ } else {
+ prev_kcs[prev_indx] = kc;
+ prev_indx++;
+ }
+}
+
+/*
+Unregisters all codes saved in prev_kcs and resets prev_indx.
+gets called on multiple occasions mainly when shift is released
+and when frankenkeycodes are pressed. Prevents output of
+wrong characters when really specific key combinations
+that would never occur during normal usage are pressed.
+*/
+void unreg_prev(void){
+ if (prev_indx == 0)
+ return;
+ for (int i=0; i<prev_indx; i++){
+ unregister_code(prev_kcs[i]);
+ }
+ prev_indx = 0;
+}
+#endif
+
+// Interrupt and times for Nav/Esc
+bool navesc = false;
+uint16_t navesc_timer = 0;
+
+// If true Gui keys and Space Cadet Shift get disabled
+bool game = false;
+
+// Interrupts all timers
+void timer_timeout(void){
+ #ifdef GERMAN_ENABLE
+ lshiftp = false;
+ rshiftp = false;
+ #endif
+ navesc = false;
+}
+
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+ switch (keycode) {
+ case CU_GAME:
+ if(record->event.pressed) {
+ timer_timeout();
+ game = !game;
+ }
+ // allows keymap to execute further commands when CU_GAME is pressed, for example enabling a macro layer
+ return process_record_keymap(keycode, record) && false;
+ case KC_LGUI:
+ case KC_RGUI:
+ if (record->event.pressed)
+ timer_timeout();
+ if (game)
+ return false;
+ else
+ return true;
+ case CU_NAV:
+ if(record->event.pressed) {
+ navesc = true;
+ navesc_timer = timer_read();
+ layer_on(_NAV);
+ } else {
+ if (timer_elapsed(navesc_timer) < 200 && navesc) {
+ register_code(KC_ESC);
+ unregister_code(KC_ESC);
+ }
+ layer_off(_NAV);
+ }
+ return false;
+ case KC_P00:
+ if(record->event.pressed) {
+ timer_timeout();
+ register_code(KC_P0);
+ unregister_code(KC_P0);
+ register_code(KC_P0);
+ unregister_code(KC_P0);
+ }
+ return false;
+
+ #ifdef RGBLIGHT_ENABLE
+ case CU_RGBV:
+ if(record->event.pressed) {
+ timer_timeout();
+ if (rgblight_get_val()+32>255)
+ rgblight_sethsv(rgblight_get_hue(), rgblight_get_sat(), 31);
+ else
+ rgblight_sethsv(rgblight_get_hue(), rgblight_get_sat(), rgblight_get_val()+32);
+ }
+ return false;
+ #endif
+
+ #ifdef GERMAN_ENABLE
+ case CU_LSFT:
+ if(record->event.pressed) {
+ lshiftp = true;
+ lshift_timer = timer_read();
+ unregister_code(KC_LSFT);
+ register_code(KC_LSFT);
+ lshift = true;
+ } else {
+ if (timer_elapsed(lshift_timer) < 200 && lshiftp && !game) {
+ register_code(KC_LSFT);
+ register_code(KC_8);
+ unregister_code(KC_8);
+ unregister_code(KC_LSFT);
+ }
+ unreg_prev();
+ if (!rshift)
+ unregister_code(KC_LSFT);
+ lshift = false;
+ }
+ return false;
+ case CU_RSFT:
+ if(record->event.pressed) {
+ rshiftp = true;
+ rshift_timer = timer_read();
+ unregister_code(KC_LSFT);
+ register_code(KC_LSFT);
+ rshift = true;
+ } else {
+ if (timer_elapsed(rshift_timer) < 200 && rshiftp && !game) {
+ register_code(KC_LSFT);
+ register_code(KC_9);
+ unregister_code(KC_9);
+ unregister_code(KC_LSFT);
+ }
+ unreg_prev();
+ if (!lshift)
+ unregister_code(KC_LSFT);
+ rshift = false;
+ }
+ return false;
+ case CU_ESCT:
+ if(record->event.pressed) {
+ timer_timeout();
+ esct = !esct;
+ }
+ return false;
+ case CU_AE:
+ UML(DE_AE)
+ case CU_OE:
+ UML(DE_OE)
+ case CU_UE:
+ UML(DE_UE)
+ case CU_SS:
+ if(record->event.pressed) {
+ timer_timeout();
+ unregister_code(KC_LSFT);
+ register_code(DE_SS);
+ unregister_code(DE_SS);
+ if (lshift || rshift)
+ register_code(KC_LSFT);
+ layer_off(_DEADKEY);
+ }
+ return false;
+ case CU_DDQ:
+ if(record->event.pressed) {
+ timer_timeout();
+ register_code(KC_LSFT);
+ register_code(KC_2);
+ unregister_code(KC_2);
+ if (!lshift && !rshift)
+ unregister_code(KC_LSFT);
+ layer_off(_DEADKEY);
+ }
+ return false;
+ case CU_ED:
+ if(record->event.pressed) {
+ timer_timeout();
+ layer_off(_DEADKEY);
+ }
+ return false;
+ case CU_GRV:
+ if(record->event.pressed) {
+ timer_timeout();
+ if (lshift || rshift){
+ unregister_code(KC_LSFT);
+ register_code(KC_ALGR);
+ unregister_code(DE_PLUS);
+ register_code(DE_PLUS);
+ unregister_code(DE_PLUS);
+ unregister_code(KC_ALGR);
+ register_code(KC_LSFT);
+ } else {
+ register_code(KC_LSFT);
+ unregister_code(DE_ACUT);
+ register_code(DE_ACUT);
+ unregister_code(DE_ACUT);
+ unregister_code(KC_LSFT);
+ if (!esct) {
+ register_code(KC_SPC);
+ unregister_code(KC_SPC);
+ }
+ }
+ }
+ return false;
+ case CU_CIRC:
+ if(record->event.pressed) {
+ timer_timeout();
+ unregister_code(KC_LSFT);
+ unregister_code(DE_CIRC);
+ register_code(DE_CIRC);
+ unregister_code(DE_CIRC);
+ if (!esct) {
+ register_code(KC_SPC);
+ unregister_code(KC_SPC);
+ }
+ if (lshift || rshift)
+ register_code(KC_LSFT);
+ }
+ return false;
+ case CU_QUOT:
+ if(record->event.pressed){
+ timer_timeout();
+ register_code(KC_LSFT);
+ if (lshift || rshift){
+ layer_on(_DEADKEY);
+ } else {
+ unregister_code(DE_HASH);
+ register_code(DE_HASH);
+ add_to_prev(DE_HASH);
+ }
+ } else {
+ unregister_code(DE_HASH);
+ unreg_prev();
+ if (lshift || rshift)
+ register_code(KC_LSFT);
+ else
+ unregister_code(KC_LSFT);
+ }
+ return false;
+ case CU_6:
+ if(record->event.pressed){
+ timer_timeout();
+ unregister_code(KC_LSFT);
+ if (lshift || rshift){
+ unregister_code(DE_CIRC);
+ register_code(DE_CIRC);
+ unregister_code(DE_CIRC);
+ if (!esct) {
+ register_code(KC_SPC);
+ unregister_code(KC_SPC);
+ }
+ register_code(KC_LSFT);
+ } else {
+ register_code(DE_6);
+ }
+ } else {
+ unregister_code(DE_6);
+ }
+ return false;
+ case CU_COMM:
+ SHIFT_NO(DE_COMM, DE_LESS)
+ case CU_DOT:
+ SHIFT_NORM(DE_DOT, DE_LESS)
+ case CU_SLSH:
+ SHIFT_ALL(DE_7, DE_SS)
+ case CU_SCLN:
+ SHIFT_ALL(DE_COMM, DE_DOT)
+ case CU_3:
+ SHIFT_NO(DE_3, DE_HASH)
+ case CU_7:
+ SHIFT_NORM(DE_7, DE_6)
+ case CU_8:
+ SHIFT_NORM(DE_8, DE_PLUS)
+ case CU_9:
+ SHIFT_NORM(DE_9, DE_8)
+ case CU_0:
+ SHIFT_NORM(DE_0, DE_9)
+ case CU_EQL:
+ SHIFT_SWITCH(DE_0, DE_PLUS)
+ case CU_LBRC:
+ SHIFT_ALGR(DE_8, DE_7)
+ case CU_RBRC:
+ SHIFT_ALGR(DE_9, DE_0)
+ case CU_BSLS:
+ SHIFT_ALGR(DE_SS, DE_LESS)
+ case CU_Z:
+ CTRL(DE_Z, KC_Z)
+ case CU_Y:
+ CTRL(DE_Y, KC_Y)
+ case KC_LCTL:
+ case KC_RCTL:
+ if(!record->event.pressed) {
+ timer_timeout();
+ unregister_code(KC_Z);
+ unregister_code(KC_Y);
+ }
+ return true;
+ #endif
+
+ default:
+ if(record->event.pressed) {
+ timer_timeout();
+
+ #ifdef GERMAN_ENABLE
+ if (lshift || rshift)
+ register_code(KC_LSFT);
+ else
+ unregister_code(KC_LSFT);
+ #endif
+
+ }
+ return process_record_keymap(keycode, record);
+ }
+}
diff --git a/users/spacebarracecar/spacebarracecar.h b/users/spacebarracecar/spacebarracecar.h
new file mode 100644
index 0000000000..d0259b73cc
--- /dev/null
+++ b/users/spacebarracecar/spacebarracecar.h
@@ -0,0 +1,241 @@
+#pragma once
+
+#include "quantum.h"
+#include "keymap_german.h"
+
+enum userspace_layers {
+ _DEADKEY = 14, // Change if more than 16 layers are required
+ _NAV
+};
+
+enum userspace_custom_keycodes {
+ CU_GAME = SAFE_RANGE, // Toggle game mode on/off
+ CU_NAV, // NAV | ESC
+ KC_P00, // Numpad double zero
+
+ #ifdef GERMAN_ENABLE
+ CU_LSFT, // LSFT | (
+ CU_RSFT, // LSFT | )
+ CU_COMM, // , | <
+ CU_DOT, // . | >
+ CU_SLSH, // / | ?
+ CU_SCLN, // ; | :
+ CU_QUOT, // ' | Enable deadkey layer
+ CU_GRV, // ` | ~
+ CU_CIRC, // ^
+ CU_3, // 3 | #
+ CU_6, // 6 | ^
+ CU_7, // 7 | &
+ CU_8, // 8 | *
+ CU_9, // 9 | (
+ CU_0, // 0 | )
+ CU_EQL, // = | +
+ CU_LBRC, // [ | {
+ CU_RBRC, // ] | }
+ CU_BSLS, // \ | |
+ CU_Z, // Z | Y in conjunction with ctrl
+ CU_Y, // Y | Z in conjunction wiht ctrl
+ CU_ESCT, // Toggle escape of grv and circ on/off
+ // Deadkey Layer
+ CU_AE, // Ä
+ CU_OE, // Ö
+ CU_UE, // Ü
+ CU_SS, // ß
+ CU_DDQ, // "
+ CU_ED, // Escape deadkey layer
+ #endif
+
+ #ifdef RGBLIGHT_ENABLE
+ CU_RGBV, // Cycle through RGB brightness
+ #endif
+
+ NEW_SAFE_RANGE // Use for keymap specific keycodes
+};
+
+#ifdef GERMAN_ENABLE
+extern bool lshift;
+extern bool rshift;
+extern bool lshiftp;
+extern bool rshiftp;
+extern uint16_t lshift_timer;
+extern uint16_t rshift_timer;
+
+extern uint8_t prev_indx;
+extern uint16_t prev_kcs[6];
+void add_to_prev(uint16_t kc);
+void unreg_prev(void);
+
+extern bool esct;
+#endif
+
+extern bool navesc;
+extern uint16_t navesc_timer;
+
+extern bool game;
+
+void timer_timeout(void);
+
+bool process_record_keymap(uint16_t keycode, keyrecord_t *record);
+
+#define CTRLX LCTL(KC_X)
+#define CTRLC LCTL(KC_C)
+#define CTRLV LCTL(KC_V)
+
+#define ALTF4 LALT(KC_F4)
+
+#define GUIU LGUI(KC_UP)
+#define GUID LGUI(KC_DOWN)
+#define GUIL LGUI(KC_LEFT)
+#define GUIR RGUI(KC_RIGHT)
+
+/*
+Templates for Keys, with custom shifted and non shifted Characters
+*/
+
+// Normal shift status
+#define SHIFT_NORM(kc1, kc2) \
+if (record->event.pressed) { \
+ timer_timeout(); \
+ if (lshift || rshift) { \
+ register_code(KC_LSFT); \
+ unregister_code(kc2); \
+ register_code(kc2); \
+ add_to_prev(kc2); \
+ } else { \
+ unregister_code(KC_LSFT); \
+ unregister_code(kc1); \
+ register_code(kc1); \
+ } \
+} else { \
+ unregister_code(kc1); \
+ unregister_code(kc2); \
+} \
+return false;
+
+// Inverted shift status
+#define SHIFT_SWITCH(kc1, kc2) \
+if (record->event.pressed) { \
+ timer_timeout(); \
+ if (lshift || rshift) { \
+ unregister_code(KC_LSFT); \
+ unregister_code(kc2); \
+ register_code(kc2); \
+ add_to_prev(kc2); \
+ } else { \
+ register_code(KC_LSFT); \
+ unregister_code(kc1); \
+ register_code(kc1); \
+ add_to_prev(kc1); \
+ } \
+} else { \
+ unregister_code(kc1); \
+ unregister_code(kc2); \
+ unreg_prev(); \
+ if (lshift || rshift) \
+ register_code(KC_LSFT); \
+ else \
+ unregister_code(KC_LSFT); \
+} \
+return false;
+
+// Always shifted
+#define SHIFT_ALL(kc1, kc2) \
+if (record->event.pressed) { \
+ timer_timeout(); \
+ register_code(KC_LSFT); \
+ if (lshift || rshift) { \
+ unregister_code(kc2); \
+ register_code(kc2); \
+ add_to_prev(kc2); \
+ } else { \
+ unregister_code(kc1); \
+ register_code(kc1); \
+ add_to_prev(kc1); \
+ } \
+} else { \
+ unregister_code(kc1); \
+ unregister_code(kc2); \
+ unreg_prev(); \
+ if (lshift || rshift) \
+ register_code(KC_LSFT); \
+ else \
+ unregister_code(KC_LSFT); \
+} \
+return false;
+
+// Never shifted
+#define SHIFT_NO(kc1, kc2) \
+if (record->event.pressed) { \
+ timer_timeout(); \
+ unregister_code(KC_LSFT); \
+ if (lshift || rshift) { \
+ unregister_code(kc2); \
+ register_code(kc2); \
+ add_to_prev(kc2); \
+ } else { \
+ unregister_code(kc1); \
+ register_code(kc1); \
+ } \
+} else { \
+ unregister_code(kc1); \
+ unregister_code(kc2); \
+ unreg_prev(); \
+ if (lshift || rshift) \
+ register_code(KC_LSFT); \
+ else \
+ unregister_code(KC_LSFT); \
+} \
+return false;
+
+// Always AltGr
+#define SHIFT_ALGR(kc1, kc2) \
+if (record->event.pressed) { \
+ timer_timeout(); \
+ unregister_code(KC_LSFT); \
+ register_code(KC_ALGR); \
+ if (lshift || rshift) { \
+ unregister_code(kc2); \
+ register_code(kc2); \
+ unregister_code(kc2); \
+ register_code(KC_LSFT); \
+ } else { \
+ unregister_code(kc1); \
+ register_code(kc1); \
+ unregister_code(kc1); \
+ } \
+ unregister_code(KC_ALGR); \
+} \
+return false;
+
+// Different keycode when Ctrl is pressed
+#define CTRL(kc1, kc2) \
+if(record->event.pressed) { \
+ timer_timeout(); \
+ if (lshift || rshift) \
+ register_code(KC_LSFT); \
+ else \
+ unregister_code(KC_LSFT); \
+ if (keyboard_report->mods & (MOD_BIT(KC_LCTL) | MOD_BIT(KC_RCTL))){ \
+ register_code(kc2); \
+ } else { \
+ register_code(kc1); \
+ } \
+} else { \
+ unregister_code(kc1); \
+ unregister_code(kc2); \
+} \
+return false;
+
+// Template for keys on deadkey layer (mostly Umlaute)
+#define UML(kc) \
+if(record->event.pressed) { \
+ timer_timeout(); \
+ if (lshift || rshift) \
+ register_code(KC_LSFT); \
+ else \
+ unregister_code(KC_LSFT); \
+ register_code(kc); \
+ unregister_code(kc); \
+ layer_off(_DEADKEY); \
+} \
+return false;
diff --git a/users/talljoe/config.h b/users/talljoe/config.h
index 15bbde6bcd..33374014df 100644
--- a/users/talljoe/config.h
+++ b/users/talljoe/config.h
@@ -1,9 +1,12 @@
#ifndef USERSPACE_CONFIG_H
#define USERSPACE_CONFIG_H
-#define PREVENT_STUCK_MODIFIERS
-#define IGNORE_MOD_TAP_INTERRUPT
+#define PERMISSIVE_HOLD
#define RESET_LAYER 15
+#define BOOTMAGIC_KEY_SALT KC_ESC
+#define BOOTMAGIC_KEY_SKIP KC_I
+#define BOOTMAGIC_KEY_EEPROM_CLEAR KC_E
+
#endif // !USERSPACE_CONFIG_H
diff --git a/users/talljoe/rules.mk b/users/talljoe/rules.mk
index 0f1f6f26a6..e0a71561f4 100644
--- a/users/talljoe/rules.mk
+++ b/users/talljoe/rules.mk
@@ -5,3 +5,5 @@ EXTRAFLAGS+=-flto
TAP_DANCE_ENABLE=yes
CONSOLE_ENABLE=no
COMMAND_ENABLE=no
+DYNAMIC_KEYMAP_ENABLE=no
+BOOTMAGIC_ENABLE=full
diff --git a/users/talljoe/talljoe.c b/users/talljoe/talljoe.c
index e9c69b016a..345b5604bb 100644
--- a/users/talljoe/talljoe.c
+++ b/users/talljoe/talljoe.c
@@ -1,14 +1,17 @@
#include QMK_KEYBOARD_H
#include "talljoe.h"
+#ifdef ZEAL_RGB
+#include "../../../keyboards/zeal60/rgb_backlight.h"
+#endif
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
[_BASE] = TEMPLATE_TKL(
KC_ESC, KC_F1 , KC_F2 , KC_F3 , KC_F4 , KC_F5 , KC_F6 , KC_F7 , KC_F8 , KC_F9 , KC_F10 , KC_F11 , KC_F12 , KC_PSCR, KC_SLCK, MO_ADJ ,
- KC_GRV , KC_1 , KC_2 , KC_3 , KC_4 , KC_5 , KC_6 , KC_7 , KC_8 , KC_9 , KC_0 , KC_MINS, KC_EQL , KC_BSLS, KC_INS , KC_HOME, KC_PGUP,
- KC_TAB , KC_Q, KC_W, KC_E, KC_R, KC_T , KC_Y, KC_U, KC_I, KC_O, KC_P , KC_LBRC, KC_RBRC, KC_BSPC, KC_DEL , KC_END , KC_PGDN,
- US_CAPS, KC_A, KC_S, KC_D, KC_F, KC_G , KC_H, KC_J, KC_K, KC_L, US_SCLN, US_QUOT, US_ENT ,
- KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B , KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_RSFT, KC_UP ,
+ US_GRV , KC_1 , KC_2 , KC_3 , KC_4 , KC_5 , KC_6 , KC_7 , KC_8 , KC_9 , KC_0 , KC_MINS, KC_EQL , US_BSLS, KC_INS , KC_HOME, KC_PGUP,
+ US_TAB , KC_Q, KC_W, KC_E, KC_R, KC_T , KC_Y, KC_U, KC_I, KC_O, KC_P , KC_LBRC, KC_RBRC, KC_BSPC, KC_DEL , KC_END , KC_PGDN,
+ CTL_ESC, KC_A, KC_S, KC_D, KC_F, KC_G , KC_H, KC_J, KC_K, KC_L, US_SCLN, KC_QUOT, US_ENT ,
+ SH_LBRC, KC_Z, KC_X, KC_C, KC_V, KC_B , KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, SH_RBRC, KC_UP ,
KC_LCTL, KC_LGUI, KC_LALT, KC_SPC2, KC_SPC1, KC_SPC3, KC_RALT, KC_RGUI, KC_RCTL, KC_PTT , KC_LEFT, KC_DOWN, KC_RGHT),
[_WORKMAN] = TEMPLATE(
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______,
@@ -34,41 +37,44 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
_______, KC_A, KC_R, KC_S, KC_T, KC_D , KC_H, KC_N, KC_E, KC_I, KC_O , _______, _______,
_______, KC_Z, KC_X, KC_C, KC_V, KC_B , KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, _______, _______,
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______),
-
+#if (SPACE_COUNT > 1)
+ // A tweaked version of the Maltron layout
+ [_MALTROFF] = TEMPLATE(
+ _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______,
+ _______, KC_Q, KC_P, KC_Y, KC_G, KC_B , KC_J, KC_M, KC_U, KC_K, KC_L, _______, _______, _______,
+ _______, KC_A, KC_N, KC_I, KC_S, KC_F , KC_D, KC_T, KC_H, KC_O, KC_R , US_ENT , KC_BSPC,
+ _______, KC_Z, KC_X, KC_C, KC_V, US_QUOT, KC_SCLN, KC_W, KC_COMM, KC_DOT, KC_SLSH, _______, _______,
+ _______, _______, _______, MLT_E , _______, _______, _______, _______, _______, _______),
+#endif
#ifdef ENABLE_GAME_LAYER
[_GAME] = TEMPLATE(
KC_ESC , KC_1 , KC_2 , KC_3 , KC_4 , KC_5 , KC_6 , KC_7 , KC_8 , KC_9 , KC_0 , KC_MINS, KC_EQL , KC_BSLS, KC_GRV,
KC_TAB , KC_Q , KC_W , KC_E , KC_R , KC_T , KC_Y , KC_U , KC_I , KC_O , KC_P , KC_LBRC, KC_RBRC, KC_BSPC,
MO_NAV , KC_A , KC_S , KC_D , KC_F , KC_G , KC_H , KC_J , KC_K , KC_L , KC_SCLN, KC_QUOT, KC_ENT ,
KC_LSFT, KC_Z , KC_X , KC_C , KC_V , KC_B , KC_N , KC_M , KC_COMM, KC_DOT , KC_SLSH, KC_RSFT, MO_ADJ ,
- KC_LCTL, KC_PTT , KC_PGDN, KC_SPC , KC_SPC , KC_SPC , KC_RALT, KC_APP , KC_RCTL, KC_PTT ),
+ KC_LCTL, KC_PTT , KC_PGDN, KC_SPC , KC_SPC , KC_SPC , KC_RALT, KC_APP , KC_RCTL, KC_PTT ),
#endif
- [_NAV] = TEMPLATE(
- KC_GRV , XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX,
- KC_TAB , KC_F1 , KC_F2 , KC_F3 , KC_F4 , KC_VOLU, KC_INS , KC_PGUP, KC_UP , KC_PGDN, KC_BTN1, KC_BTN2, KC_BTN3, KC_DEL ,
- US_CAPS, KC_F5 , KC_F6 , KC_F7 , KC_F8 , KC_MUTE, KC_HOME, KC_LEFT, KC_DOWN, KC_RGHT, KC_END , KC_RCTL, TG_ADJ ,
- KC_LSFT, KC_F9 , KC_F10 , KC_F11 , KC_F12 , KC_VOLD, KC_END , KC_PGDN, KC_WBAK, KC_WFWD, KC_WREF, KC_RSFT, KC_APP ,
+ [_NAV] = TEMPLATE_NAV(
+ KC_GRV , KC_F1 , KC_F2 , KC_F3 , KC_F4 , KC_F5 , KC_F6 , KC_F7 , KC_F8 , KC_F9 , KC_F10 , KC_F11 , KC_F12 , XXXXXXX, XXXXXXX,
+ US_TAB , KC_EXLM, KC_AT , KC_HASH, KC_DLR , KC_PERC, KC_INS , KC_PGUP, KC_UP , KC_PGDN, KC_BTN1, KC_BTN3, KC_BTN2, KC_DEL ,
+ CTL_ESC, KC_LCBR, KC_RCBR, KC_LPRN, KC_RPRN, KC_AMPR, KC_HOME, KC_LEFT, KC_DOWN, KC_RGHT, KC_END , US_QUOT, TG_ADJ ,
+ KC_LSFT, KC_EQL, KC_PLUS, KC_MINS, KC_UNDS, KC_ASTR, KC_CALC, US_GRV , KC_WBAK, KC_WFWD, KC_WREF, KC_RSFT, KC_APP ,
KC_LCTL, KC_LGUI, KC_LALT, NV_SPC2, NV_SPC1, NV_SPC3, KC_RALT, KC_RGUI, KC_RCTL, KC_PTT ),
- [_NUM] = TEMPLATE(
+ [_NUM] = TEMPLATE_NUM(
XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX,
- KC_GRV , KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS, XXXXXXX, KC_DEL ,
- US_CAPS, KC_LCBR, KC_RCBR, KC_LPRN, KC_RPRN, KC_LBRC, KC_RBRC, KC_4, KC_5, KC_6, KC_PPLS, KC_PENT, XXXXXXX,
- KC_LSFT, KC_EQL, KC_PLUS, KC_BSLS, KC_PIPE, KC_SCLN, XXXXXXX, KC_1, KC_2, KC_3, KC_PAST, KC_PSLS, XXXXXXX,
+ KC_GRV , KC_F1 , KC_F2 , KC_F3 , KC_F4 , KC_VOLU, KC_CIRC, KC_7, KC_8, KC_9, KC_PMNS, XXXXXXX, XXXXXXX, KC_DEL ,
+ CTL_ESC, KC_F5 , KC_F6 , KC_F7 , KC_F8 , KC_MUTE, KC_PENT, KC_4, KC_5, KC_6, KC_PPLS, XXXXXXX, KC_ENT ,
+ KC_LSFT, KC_F9 , KC_F10 , KC_F11 , KC_F12 , KC_VOLD, KC_PIPE, KC_1, KC_2, KC_3, KC_PAST, KC_PSLS, TG_NUM ,
KC_LCTL, KC_LGUI, KC_LALT, NM_SPC2, NM_SPC1, NM_SPC3, KC_PDOT, KC_PCMM, KC_RCTL, KC_PTT ),
// Adjust layer is on the split-shift key; or NAV+Enter (for non-split keyboards)
- [_ADJUST] = TEMPLATE(
- MO_RST , FX(1) , FX(2) , FX(3) , FX(4) , FX(5) , FX(6) , FX(7) , FX(8) , FX(9) , FX(10) , BR_DEC , BR_INC , XXXXXXX, MO_RST ,
- XXXXXXX, H1_INC , S1_INC , H2_INC , S2_INC , EF_INC , RGB_HUI, RGB_SAI, RGB_MOD, RGB_M_P, DFAULTS, RGB_VAD, RGB_VAI, KC_DEL ,
+ [_ADJUST] = TEMPLATE_ADJUST(
+ MO_RST , FX(1) , FX(2) , FX(3) , FX(4) , FX(5) , FX(6) , FX(7) , FX(8) , FX(9) , FX(10) , BR_DEC , BR_INC , XXXXXXX, MO_RST ,
+ MO_RST , H1_INC , S1_INC , H2_INC , S2_INC , EF_INC , RGB_HUI, RGB_SAI, RGB_MOD, RGB_M_P, DFAULTS, RGB_VAD, RGB_VAI, MO_RST ,
XXXXXXX, H1_DEC , S1_DEC , H2_DEC , S2_DEC , EF_DEC , RGB_HUD, RGB_SAD, RGB_RMOD,RGB_M_K, RGB_M_B, RGB_M_G, TG_ADJ ,
- TG_NKRO, LY_QWER, LY_WORK, LY_NRMN, LY_DVRK, LY_CLMK, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, KC_MAKE, KC_CAPS, XXXXXXX,
- MO_RST , AG_NORM, AG_SWAP, XXXXXXX, BL_STEP, XXXXXXX, RGB_TOG, XXXXXXX, XXXXXXX, TG_GAME),
+ TG_NKRO, LY_QWER, LY_WORK, LY_NRMN, LY_DVRK, LY_CLMK, XXXXXXX, LY_MALT, XXXXXXX, XXXXXXX, KC_MAKE, KC_CAPS, XXXXXXX,
+ MO_RST , AG_SWAP, AG_NORM, XXXXXXX, BL_TOGG, XXXXXXX, RGB_TOG, XXXXXXX, XXXXXXX, TG_GAME),
// To Reset hit FN + ` + Esc
- [_RESET] = TEMPLATE(
- RESET , XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, RESET ,
- XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX,
- XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX,
- XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX,
- RESET , XXXXXXX, XXXXXXX, XXXXXXX, KC_SLEP, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX),
+ [_RESET] = TEMPLATE_RESET,
};
void matrix_scan_user(void) {
@@ -98,7 +104,13 @@ bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
return true;
}
+#ifdef ZEAL_RGB
+extern backlight_config g_config;
+#endif
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+#ifdef ZEAL_RGB
+ static uint8_t last_effect;
+#endif
#ifdef RGBLIGHT_ENABLE
static uint32_t savedRgbMode;
@@ -141,6 +153,27 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
}
return false;
break;
+#ifdef ZEAL_RGB
+ case BL_TOGG:
+ if (IS_PRESSED(record->event)) {
+ if (g_config.effect) {
+ last_effect = g_config.effect;
+ g_config.effect = 0;
+ } else {
+ g_config.effect = last_effect;
+ }
+ }
+ return false;
+ case EFFECT...EFFECT_END:
+ if (IS_PRESSED(record->event)) {
+ uint8_t effect = keycode - EFFECT;
+ if(effect == g_config.effect)
+ effect = 0; // Toggle effect on second press
+ g_config.effect = effect;
+ backlight_config_save();
+ }
+ return false;
+#endif
}
return process_record_keymap(keycode, record);
}
diff --git a/users/talljoe/talljoe.h b/users/talljoe/talljoe.h
index 7c34cd41ff..4436c0a044 100644
--- a/users/talljoe/talljoe.h
+++ b/users/talljoe/talljoe.h
@@ -8,7 +8,7 @@ enum userspace_custom_keycodes {
DFAULTS,
TOGGLE_BACKLIGHT,
EFFECT,
- EFFECT_END = EFFECT + 10
+ EFFECT_END = EFFECT + 20
};
#ifndef RESET_LAYER
@@ -21,6 +21,7 @@ enum layers {
_NORMAN,
_DVORAK,
_COLMAK,
+ _MALTROFF,
_GAME,
_NAV,
_NUM,
@@ -29,7 +30,9 @@ enum layers {
};
enum tap_dancers {
- TD_SEMICOLON
+ TD_SEMICOLON,
+ TD_GRAVE,
+ TD_QUOTE,
};
#define _______ KC_TRNS
@@ -39,6 +42,7 @@ enum tap_dancers {
#define MO_ADJ MO(_ADJUST)
#define MO_RST MO(_RESET)
#define TG_ADJ TG(_ADJUST)
+#define TG_NUM TG(_NUM)
#ifdef ENABLE_GAME_LAYER
#define TG_GAME TG(_GAME)
#else
@@ -49,16 +53,28 @@ enum tap_dancers {
#define LY_NRMN DF(_NORMAN)
#define LY_DVRK DF(_DVORAK)
#define LY_CLMK DF(_COLMAK)
+#if SPACE_COUNT >= 2
+ #define LY_MALT DF(_MALTROFF)
+#else
+ #define LY_MALT KC_NO
+#endif
#define TG_NKRO MAGIC_TOGGLE_NKRO
#define KC_PTT KC_F24
#define MS_MID KC_MS_BTN3
#define FX(x) (EFFECT + x)
-#define US_CAPS CTL_T(KC_ESC)
-#define US_QUOT RCTL_T(KC_QUOT)
+#define CTL_ESC CTL_T(KC_ESC)
+#define US_ENT RCTL_T(KC_ENT)
#define US_MINS RCTL_T(KC_QUOT)
+#define US_BSLS LCA_T(KC_BSLS)
#define US_SCLN TD(TD_SEMICOLON)
-#define US_ENT LT(_NUM, KC_ENT)
+#define US_GRV TD(TD_GRAVE)
+#define US_QUOT TD(TD_QUOTE)
+#define US_TAB C_S_T(KC_TAB)
+#define SH_LBRC LSFT_T(KC_LBRC)
+#define SH_RBRC RSFT_T(KC_RBRC)
+
+#define MLT_E LT(_NUM, KC_E)
#ifndef SPACE_COUNT
#define SPACE_COUNT 1
@@ -75,17 +91,34 @@ enum tap_dancers {
#define NM_SPC1 _______
#define NM_SPC2 _______
#define NM_SPC3 _______
+#elif (SPACE_COUNT == 2)
+ #define KC_SPC1 LT(_NAV,KC_SPC)
+ #define KC_SPC2 LT(_NUM,KC_ENT)
+
+ #define NV_SPC1 KC_SPC
+ #define NV_SPC2 KC_ENT
+
+ #define NM_SPC1 KC_0
+ #define NM_SPC2 KC_SPC
+
+ #define KC_SPC3 XXXXXXX
+ #define NV_SPC3 XXXXXXX
+ #define NM_SPC3 XXXXXXX
#elif (SPACE_COUNT == 3)
- #define KC_SPC1 KC_BSPC
+ #ifdef SWAP_HANDS_ENABLE
+ #define KC_SPC1 SH_T(KC_BSPC)
+ #else
+ #define KC_SPC1 KC_BSPC
+ #endif
#define KC_SPC2 LT(_NUM,KC_ENT)
#define KC_SPC3 LT(_NAV,KC_SPC)
#define NV_SPC1 KC_SPC
- #define NV_SPC2 C_S_T(KC_ENT)
+ #define NV_SPC2 KC_ENT
#define NV_SPC3 KC_SPC
- #define NM_SPC2 XXXXXXX
#define NM_SPC1 KC_SPC
+ #define NM_SPC2 XXXXXXX
#define NM_SPC3 KC_0
#else
#error "Unsupported space count:" SPACE_COUNT
@@ -110,7 +143,7 @@ enum tap_dancers {
#define FN_MO2 KC_NO
#endif
-#ifdef TEMPLATE_TKL
+#ifndef TEMPLATE
#define _X_ KC_NO
#define TEMPLATE( \
KJ4, KJ7, KI7, KH7, KG7, KG4, KF4, KF7, KE7, KD7, KR7, KR4, KE4, KB2, KJ6, \
@@ -126,7 +159,8 @@ enum tap_dancers {
KN2, KJ1, KI1, KH1, KG1, KG0, KF0, KF1, KE1, KD1, KR0, KN3, _X_, \
KA4, KP2, KC6, KX1, KK6, KX2, KC0, KM3, KD0, KA1, _X_, _X_, _X_ \
)
-#else
+#endif
+#ifndef TEMPLATE_TKL
#define TEMPLATE_TKL( \
KJ6, KI4, KH4, KH2, KH6, KA7, KE6, KD2, KD4, KB4, KB7, KB6, KB0, KC7, KC5, KA5, \
KJ4, KJ7, KI7, KH7, KG7, KG4, KF4, KF7, KE7, KD7, KR7, KR4, KE4, KB2, KL4, KO4, KQ4, \
@@ -143,4 +177,26 @@ enum tap_dancers {
)
#endif
+#ifndef TEMPLATE_ALT
+ #define TEMPLATE_ALT TEMPLATE
+#endif
+#ifndef TEMPLATE_NUM
+ #define TEMPLATE_NUM TEMPLATE_ALT
+#endif
+#ifndef TEMPLATE_NAV
+ #define TEMPLATE_NAV TEMPLATE_ALT
+#endif
+#ifndef TEMPLATE_ADJUST
+ #define TEMPLATE_ADJUST TEMPLATE_ALT
+#endif
+
+#ifndef TEMPLATE_RESET
+ #define TEMPLATE_RESET TEMPLATE_ALT( \
+ RESET , XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, RESET , \
+ RESET , XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, RESET , \
+ XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, \
+ XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, \
+ RESET , XXXXXXX, XXXXXXX, XXXXXXX, RESET , XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX, XXXXXXX)
+#endif
+
#endif
diff --git a/users/talljoe/tapdance.c b/users/talljoe/tapdance.c
index 3198fc67f0..c4d6025f0f 100644
--- a/users/talljoe/tapdance.c
+++ b/users/talljoe/tapdance.c
@@ -1,34 +1,146 @@
//Tap Dance
#include "talljoe.h"
-// Send semin-colon + enter on two taps
-void tap_dance_semicolon(qk_tap_dance_state_t *state, void *user_data) {
+enum {
+ SINGLE_TAP = 1,
+ SINGLE_HOLD = 2,
+ DOUBLE_TAP = 3,
+ DOUBLE_HOLD = 4,
+ DOUBLE_SINGLE_TAP = 5, //send two single taps
+ TRIPLE_TAP = 6,
+ TRIPLE_HOLD = 7,
+ SPECIAL = 8
+};
+
+static struct {
+ int quote;
+ int semicolon;
+} tap_state = {0};
+
+int cur_dance (qk_tap_dance_state_t *state) {
+ if (state->count == 1) {
+ //If count = 1, and it has been interrupted - it doesn't matter if it is pressed or not: Send SINGLE_TAP
+ if (state->interrupted) {
+ // if (!state->pressed) return SINGLE_TAP;
+ //need "permissive hold" here.
+ // else return SINGLE_HOLD;
+ //If the interrupting key is released before the tap-dance key, then it is a single HOLD
+ //However, if the tap-dance key is released first, then it is a single TAP
+ //But how to get access to the state of the interrupting key????
+ return SINGLE_TAP;
+ }
+ else {
+ if (!state->pressed) return SINGLE_TAP;
+ else return SINGLE_HOLD;
+ }
+ }
+ //If count = 2, and it has been interrupted - assume that user is trying to type the letter associated
+ //with single tap.
+ else if (state->count == 2) {
+ if (state->interrupted) return DOUBLE_SINGLE_TAP;
+ else if (state->pressed) return DOUBLE_HOLD;
+ else return DOUBLE_TAP;
+ }
+ else if ((state->count == 3) && ((state->interrupted) || (!state->pressed))) return TRIPLE_TAP;
+ else if (state->count == 3) return TRIPLE_HOLD;
+ else return SPECIAL;
+}
+
+int hold_cur_dance (qk_tap_dance_state_t *state) {
+ if (state->count == 1) {
+ if (state->interrupted) {
+ if (!state->pressed) return SINGLE_TAP;
+ else return SINGLE_HOLD;
+ }
+ else {
+ if (!state->pressed) return SINGLE_TAP;
+ else return SINGLE_HOLD;
+ }
+ }
+ //If count = 2, and it has been interrupted - assume that user is trying to type the letter associated
+ //with single tap.
+ else if (state->count == 2) {
+ if (state->pressed) return DOUBLE_HOLD;
+ else return DOUBLE_TAP;
+ }
+ else if (state->count == 3) {
+ if (!state->pressed) return TRIPLE_TAP;
+ else return TRIPLE_HOLD;
+ }
+ else return SPECIAL;
+}
+
+// Send semi-colon + enter on two taps
+void tap_dance_semicolon_finished(qk_tap_dance_state_t *state, void *user_data) {
+ tap_state.semicolon = hold_cur_dance(state);
+ switch (tap_state.semicolon) {
+ case SINGLE_TAP: case DOUBLE_HOLD: register_code(KC_SCLN); break;
+ case SINGLE_HOLD: layer_on(_NUM); break;
+ }
+}
+
+void tap_dance_semicolon_reset(qk_tap_dance_state_t *state, void *user_data) {
+ switch (tap_state.semicolon) {
+ case SINGLE_TAP: case DOUBLE_HOLD: unregister_code(KC_SCLN); break;
+ case DOUBLE_TAP: {
+ if (get_mods()) {
+ SEND_STRING(";;"); // send normal when mods are pressed
+ }
+ else {
+ SEND_STRING(";\n");
+ }
+ break;
+ }
+ case TRIPLE_TAP: {
+ SEND_STRING(";\n\n");
+ }
+ case SPECIAL: layer_invert(_NUM); break;
+ case SINGLE_HOLD: layer_off(_NUM); break;
+ }
+ tap_state.semicolon = 0;
+}
+
+// Send `. ~. ```
+void tap_dance_grave_finished(qk_tap_dance_state_t *state, void *user_data) {
switch(state->count) {
case 1:
- register_code(KC_SCLN);
- unregister_code(KC_SCLN);
+ SEND_STRING("`");
break;
case 2:
- register_code(KC_SCLN);
- unregister_code(KC_SCLN);
+ SEND_STRING("~");
+ break;
+ }
+}
- uint8_t mods = get_mods();
- if (mods) {
- clear_mods();
- }
+void tap_dance_grave_each(qk_tap_dance_state_t *state, void *user_data) {
+ if(state->count == 3) {
+ SEND_STRING("```");
+ } else if (state->count > 3) {
+ SEND_STRING("`");
+ }
+}
- register_code(KC_ENT);
- unregister_code(KC_ENT);
- if (mods) {
- set_mods(mods);
- }
+void tap_dance_quote_finished(qk_tap_dance_state_t *state, void *user_data) {
+ tap_state.quote = hold_cur_dance(state);
+ switch (tap_state.quote) {
+ case SINGLE_TAP: case DOUBLE_HOLD: register_code(KC_QUOT); break;
+ case SINGLE_HOLD: layer_on(_NAV); break;
+ }
+}
- reset_tap_dance(state);
- break;
+void tap_dance_quote_reset(qk_tap_dance_state_t *state, void *user_data) {
+ switch (tap_state.quote) {
+ case SINGLE_TAP: case DOUBLE_HOLD: unregister_code(KC_QUOTE); break;
+ case DOUBLE_TAP: SEND_STRING("\""); break;
+ case TRIPLE_TAP: layer_invert(_NAV); break;
+ case SINGLE_HOLD: layer_off(_NAV); break;
}
+ tap_state.quote = 0;
}
qk_tap_dance_action_t tap_dance_actions[] = {
- [TD_SEMICOLON] = ACTION_TAP_DANCE_FN(tap_dance_semicolon),
+ [TD_SEMICOLON] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, tap_dance_semicolon_finished, tap_dance_semicolon_reset),
+ [TD_GRAVE] = ACTION_TAP_DANCE_FN_ADVANCED(tap_dance_grave_each, tap_dance_grave_finished, NULL),
+ [TD_QUOTE] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, tap_dance_quote_finished, tap_dance_quote_reset),
};
diff --git a/users/turbomech/backupturbomech.c b/users/turbomech/backupturbomech.c
index 49bcded552..2815aa452f 100644
--- a/users/turbomech/backupturbomech.c
+++ b/users/turbomech/backupturbomech.c
@@ -269,7 +269,6 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
/*case RGB_MOD:
-case RGB_SMOD:
case RGB_HUI:
case RGB_HUD:
case RGB_SAI:
diff --git a/users/wanleg/config.h b/users/wanleg/config.h
new file mode 100644
index 0000000000..0c8b048af7
--- /dev/null
+++ b/users/wanleg/config.h
@@ -0,0 +1,44 @@
+#pragma once
+
+//TAPPING_TERM
+//tapping term short (<100): on multi-purpose keys, slow taps may not register, but "holds" register easier. multi-tap keys may be difficult to activate.
+//tapping term long (>200): holds don't register as easily - noticeable when typing quickly (e.g. shift doesn't want to engage.)
+
+
+//MIGHT HAVE TO SPLIT THIS INTO TWO CONDITIONS
+#if defined(TAP_DANCE_ENABLE) && defined(KEYBOARD_lets_split_rev2) || defined(KEYBOARD_iris_rev2)
+//Kailh Coppers activate quickly and don't need a long tapping term
+#define TAPPING_TERM 100
+
+#elif defined(TAP_DANCE_ENABLE) && defined(KEYBOARD_bigswitch)
+#define TAPPING_TERM 700
+
+#else
+#define TAPPING_TERM 145
+#endif
+
+//Mousekey Settings
+#ifdef MOUSEKEY_ENABLE
+#define MOUSEKEY_INTERVAL 16
+#define MOUSEKEY_DELAY 0
+#define MOUSEKEY_TIME_TO_MAX 60
+#define MOUSEKEY_MAX_SPEED 7
+#define MOUSEKEY_WHEEL_DELAY 0
+#endif
+
+// Disable action_get_macro and fn_actions, since we don't use these
+// and it saves on space in the firmware.
+#ifndef NO_DEBUG
+#define NO_DEBUG
+#endif // !NO_DEBUG
+#if !defined(NO_PRINT) && !defined(CONSOLE_ENABLE)
+#define NO_PRINT
+#endif // !NO_PRINT
+#define NO_ACTION_MACRO
+#define NO_ACTION_FUNCTION
+#define NO_ACTION_ONESHOT
+
+// Disable mod tap interrrupt
+#ifndef IGNORE_MOD_TAP_INTERRUPT
+#define IGNORE_MOD_TAP_INTERRUPT
+#endif // !mod tap interrrupt \ No newline at end of file
diff --git a/users/wanleg/readme.md b/users/wanleg/readme.md
new file mode 100644
index 0000000000..f687b92f48
--- /dev/null
+++ b/users/wanleg/readme.md
@@ -0,0 +1,14 @@
+Copyright 2018 Brian Fong @wanleg
+
+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, either version 2 of the License, or
+(at your option) any later version.
+
+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/>.
diff --git a/users/wanleg/rules.mk b/users/wanleg/rules.mk
new file mode 100644
index 0000000000..b069cd8d38
--- /dev/null
+++ b/users/wanleg/rules.mk
@@ -0,0 +1,39 @@
+SRC += wanleg.c tapdances.c
+
+TAP_DANCE_ENABLE = yes
+MOUSEKEY_ENABLE = yes
+
+#If using a ProMicro and it has the QMK DFU bootloader instead of Caterina,
+#run "make <keyboard>:<keymap> dfu=qmk" when compiling to ensure it is flagged properly after being flashed
+ifeq ($(strip $(dfu)), qmk)
+ BOOTLOADER = qmk-dfu
+endif
+
+#use alternate settings for boards using ProMicro instead of Micro
+#example usage: make 4x4:wanleg PM=yes
+ifeq ($(strip $(PM)), yes)
+ OPT_DEFS += -DPRO_MICRO
+endif
+
+#use alternate settings for boards using "Adafruit Feather 32u4 Bluefruit LE" instead of Micro
+#example usage: make 5x5:wanleg BT=yes
+ifeq ($(strip $(BT)), yes)
+ #opt_defs for alternate pin usage
+ OPT_DEFS += -DBLUEFRUIT
+ #Adafruit Bluefruit controller settings
+ BLUETOOTH = AdafruitBLE
+ BLUETOOTH_ENABLE = yes
+ F_CPU = 8000000
+ CONSOLE_ENABLE = no # Console for debug(+400)
+ COMMAND_ENABLE = no # Commands for debug and configuration
+ RGBLIGHT_ENABLE = no # Enable keyboard RGB underglow
+endif
+
+#move numpad to Left/Centre/Right(default) on 5x15 boards
+#example usage: make 4x4:wanleg padc=yes
+ifeq ($(strip $(padc)), yes)
+ OPT_DEFS += -DPADC
+endif
+ifeq ($(strip $(padl)), yes)
+ OPT_DEFS += -DPADL
+endif \ No newline at end of file
diff --git a/users/wanleg/tapdances.c b/users/wanleg/tapdances.c
new file mode 100644
index 0000000000..1be5636dc7
--- /dev/null
+++ b/users/wanleg/tapdances.c
@@ -0,0 +1,264 @@
+//Tap Dance Settings
+#include "wanleg.h"
+
+//audio settings for one of the tap dances below
+#ifdef AUDIO_ENABLE
+ float lyrup_song[][2] = SONG(MUSIC_ON_SOUND);
+ float lyrdown_song[][2] = SONG(MUSIC_OFF_SOUND);
+#endif
+
+///// QUAD FUNCTION TAP DANCE GENERAL SETUP SECTION START /////
+///// (no need to edit this section) /////
+//Enums used to clearly convey the state of the tap dance
+enum {
+ SINGLE_TAP = 1,
+ SINGLE_HOLD = 2,
+ DOUBLE_TAP = 3,
+ DOUBLE_HOLD = 4,
+ DOUBLE_SINGLE_TAP = 5, //send SINGLE_TAP twice - NOT DOUBLE_TAP
+ TRIPLE_TAP = 6,
+ TRIPLE_HOLD = 7,
+ TRIPLE_SINGLE_TAP = 8
+ // Add more enums here if you want for triple, quadruple, etc.
+};
+
+typedef struct {
+ bool is_press_action;
+ int state;
+} tap;
+
+int cur_dance (qk_tap_dance_state_t *state) {
+ if (state->count == 1) {
+ //If count = 1, and it has been interrupted - it doesn't matter if it is pressed or not: Send SINGLE_TAP
+ if (state->interrupted || !state->pressed) return SINGLE_TAP;
+ if (state->interrupted) return SINGLE_TAP;
+ else return SINGLE_HOLD;
+ }
+ //If count = 2, and it has been interrupted - assume that user is trying to type the letter associated
+ //with single tap.
+ else if (state->count == 2) {
+ if (state->interrupted) return DOUBLE_SINGLE_TAP;
+ else if (state->pressed) return DOUBLE_HOLD;
+ else return DOUBLE_TAP;
+ }
+
+ //If count = 3, and it has been interrupted - assume that user is trying to type the letter associated
+ //with double tap.
+ else if (state->count == 3) {
+ if (state->interrupted) return TRIPLE_SINGLE_TAP;
+ else if (state->pressed) return TRIPLE_HOLD;
+ else return TRIPLE_TAP;
+ }
+ else return 9; //magic number. At some point this method will expand to work for more presses
+}
+///// QUAD FUNCTION TAP DANCE GENERAL SETUP SECTION END /////
+///// QUAD FUNCTION TAP DANCE PERSONALIZATION SECTION START /////
+//instantiate 'tap' for the 'CAD' tap dance.
+static tap CADtap_state = {
+ .is_press_action = true,
+ .state = 0
+};
+
+void CAD_finished (qk_tap_dance_state_t *state, void *user_data) {
+ CADtap_state.state = cur_dance(state);
+ switch (CADtap_state.state) {
+ case SINGLE_TAP:
+ //register_code(KC_SPC);
+ SEND_STRING(SS_LGUI("l"));
+ #ifdef BACKLIGHT_ENABLE
+ backlight_level(3);
+ #endif
+ break;
+ case SINGLE_HOLD:
+ //register_code(KC_NO);
+ //take a screenshot of a single window, open Paint and paste
+ SEND_STRING(SS_LALT(SS_TAP(X_PSCREEN)) SS_LGUI("r"));
+ wait_ms(500);
+ SEND_STRING("mspaint" SS_TAP(X_ENTER));
+ wait_ms(700);
+ SEND_STRING(SS_LCTRL("v"));
+ break; //register this keycode when button is held
+ case DOUBLE_TAP:
+ //register_code(KC_ENT);
+ SEND_STRING(SS_LCTRL(SS_LALT(SS_TAP(X_DELETE))));
+ #ifdef BACKLIGHT_ENABLE
+ backlight_level(0);
+ #endif
+ break;
+ //case DOUBLE_HOLD: register_code(KC_NO); break; //register this keycode when button is tapped and then held
+ case DOUBLE_HOLD:
+ reset_keyboard();
+ break; //register this keycode when button is tapped and then held
+ case TRIPLE_TAP:
+ SEND_STRING("wanleg@github.com");
+ break;
+ case TRIPLE_HOLD:
+ set_single_persistent_default_layer(1);
+ #ifdef AUDIO_ENABLE
+ stop_all_notes();
+ PLAY_SONG(lyrup_song);
+ #endif
+ break;
+ }
+}
+
+void CAD_reset (qk_tap_dance_state_t *state, void *user_data) {
+ switch (CADtap_state.state) {
+//nothing to do
+ }
+ CADtap_state.state = 0;
+}
+
+//instantiate 'tap' for the 'RST' tap dance.
+static tap RSTtap_state = {
+ .is_press_action = true,
+ .state = 0
+};
+
+void RST_finished (qk_tap_dance_state_t *state, void *user_data) {
+ RSTtap_state.state = cur_dance(state);
+ switch (RSTtap_state.state) {
+ case SINGLE_TAP: register_code(KC_LCTL); break;
+ case SINGLE_HOLD: register_code(KC_LCTL); break;
+ case DOUBLE_TAP: reset_keyboard(); break;
+ case DOUBLE_SINGLE_TAP: register_code(KC_LCTL); unregister_code(KC_LCTL); register_code(KC_LCTL); break;
+ }
+}
+
+void RST_reset (qk_tap_dance_state_t *state, void *user_data) {
+ switch (RSTtap_state.state) {
+ case SINGLE_TAP: unregister_code(KC_LCTL); break;
+ case SINGLE_HOLD: unregister_code(KC_LCTL); break;
+ case DOUBLE_SINGLE_TAP: unregister_code(KC_LCTL); break;
+ }
+ RSTtap_state.state = 0;
+}
+
+//instantiate 'tap' for the 'LYR' tap dance.
+static tap LYRtap_state = {
+ .is_press_action = true,
+ .state = 0
+};
+
+void LYR_finished (qk_tap_dance_state_t *state, void *user_data) {
+ LYRtap_state.state = cur_dance(state);
+ switch (LYRtap_state.state) {
+ case SINGLE_TAP: register_code(KC_PSLS); break;
+ case DOUBLE_TAP: set_single_persistent_default_layer(_GK); break;
+ case DOUBLE_SINGLE_TAP: register_code(KC_PSLS); unregister_code(KC_PSLS); register_code(KC_PSLS);
+ }
+}
+
+void LYR_reset (qk_tap_dance_state_t *state, void *user_data) {
+ switch (LYRtap_state.state) {
+ case SINGLE_TAP: unregister_code(KC_PSLS); break;
+ case DOUBLE_TAP: set_single_persistent_default_layer(_GK); break;
+ case DOUBLE_SINGLE_TAP: unregister_code(KC_PSLS);
+ }
+ LYRtap_state.state = 0;
+}
+
+//instantiate 'tap' for the 'LYR75' tap dance.
+static tap LYR75tap_state = {
+ .is_press_action = true,
+ .state = 0
+};
+
+void LYR75_finished (qk_tap_dance_state_t *state, void *user_data) {
+ LYR75tap_state.state = cur_dance(state);
+ switch (LYR75tap_state.state) {
+ case SINGLE_TAP: register_code(KC_PSLS); break;
+ case DOUBLE_TAP: set_single_persistent_default_layer(_GK); break;
+ case DOUBLE_SINGLE_TAP: register_code(KC_PSLS); unregister_code(KC_PSLS); register_code(KC_PSLS);
+ }
+}
+
+void LYR75_reset (qk_tap_dance_state_t *state, void *user_data) {
+ switch (LYR75tap_state.state) {
+ case SINGLE_TAP: unregister_code(KC_PSLS); break;
+ case DOUBLE_TAP: set_single_persistent_default_layer(_GK); break;
+ case DOUBLE_SINGLE_TAP: unregister_code(KC_PSLS);
+ }
+ LYR75tap_state.state = 0;
+}
+
+//instantiate 'tap' for the 'LYR50' tap dance.
+static tap LYR50tap_state = {
+ .is_press_action = true,
+ .state = 0
+};
+
+void LYR50_finished (qk_tap_dance_state_t *state, void *user_data) {
+ LYR50tap_state.state = cur_dance(state);
+ switch (LYR75tap_state.state) {
+ case SINGLE_TAP: register_code(KC_PSLS); break;
+ case DOUBLE_TAP: set_single_persistent_default_layer(GK50); break;
+ case DOUBLE_SINGLE_TAP: register_code(KC_PSLS); unregister_code(KC_PSLS); register_code(KC_PSLS);
+ }
+}
+
+void LYR50_reset (qk_tap_dance_state_t *state, void *user_data) {
+ switch (LYR50tap_state.state) {
+ case SINGLE_TAP: unregister_code(KC_PSLS); break;
+ case DOUBLE_TAP: set_single_persistent_default_layer(GK50); break;
+ case DOUBLE_SINGLE_TAP: unregister_code(KC_PSLS);
+ }
+ LYR50tap_state.state = 0;
+}
+
+//instantiate 'tap' for the 'BSW' tap dance.
+static tap BSWtap_state = {
+ .is_press_action = true,
+ .state = 0
+};
+
+void BSW_finished (qk_tap_dance_state_t *state, void *user_data) {
+ BSWtap_state.state = cur_dance(state);
+ switch (BSWtap_state.state) {
+ case SINGLE_TAP: register_code(KC_ENTER); break;
+ case SINGLE_HOLD:
+ set_single_persistent_default_layer(0);
+ #ifdef AUDIO_ENABLE
+ stop_all_notes();
+ PLAY_SONG(lyrdown_song);
+ #endif
+ break;
+ case DOUBLE_TAP:
+ register_code(KC_LCTRL);
+ register_code(KC_C);
+ break;
+ case DOUBLE_HOLD:
+ reset_keyboard();
+ break; //register this keycode when button is tapped and then held
+ }
+}
+
+void BSW_reset (qk_tap_dance_state_t *state, void *user_data) {
+ switch (BSWtap_state.state) {
+ case SINGLE_TAP: unregister_code(KC_ENTER); break;
+ case DOUBLE_TAP:
+ unregister_code(KC_LCTRL);
+ unregister_code(KC_C);
+ break;
+ }
+ BSWtap_state.state = 0;
+}
+
+///// QUAD FUNCTION TAP DANCE PERSONALIZATION SECTION END /////
+
+//Tap Dance Definitions
+//THIS SECTION HAS TO BE AT THE END OF THE TAP DANCE SECTION
+qk_tap_dance_action_t tap_dance_actions[] = {
+ [TD_SFT_CAPS] = ACTION_TAP_DANCE_DOUBLE(KC_LSFT, KC_CAPS)
+// Other declarations would go here, separated by commas, if you have them
+ ,[TD_Q_ESC] = ACTION_TAP_DANCE_DOUBLE(KC_Q, KC_ESC)
+ ,[RST_TAP_DANCE] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, RST_finished, RST_reset)
+ ,[CAD_TD] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, CAD_finished, CAD_reset)
+ ,[LYR_TAP_DANCE] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, LYR_finished, LYR_reset)
+ ,[LYR75_TAP_DANCE] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, LYR75_finished, LYR75_reset)
+ ,[LYR50_TAP_DANCE] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, LYR50_finished, LYR50_reset)
+ ,[BSW_TAP_DANCE] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, BSW_finished, BSW_reset)
+};
+
+//In Layer declaration, add tap dance item in place of a key code
+//TD(TD_SFT_CAPS)
diff --git a/users/wanleg/wanleg.c b/users/wanleg/wanleg.c
new file mode 100644
index 0000000000..274c74f728
--- /dev/null
+++ b/users/wanleg/wanleg.c
@@ -0,0 +1,139 @@
+#include "wanleg.h"
+
+// Defines actions for my global custom keycodes. Defined in wanleg.h file
+// Then runs the _keymap's record handier if not processed here
+bool process_record_user(uint16_t keycode, keyrecord_t *record) {
+ switch (keycode) {
+ case QWERTY:
+ if (record->event.pressed) {
+ print("mode just switched to qwerty and this is a huge string\n");
+ set_single_persistent_default_layer(_QW);
+ }
+ return false;
+ break;
+ case GHERKIN:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(_GK);
+ }
+ return false;
+ break;
+ case gGHERKIN:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(gGK);
+ }
+ return false;
+ break;
+ case ONEHAND:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(ONE);
+ }
+ return false;
+ break;
+ case NUMPAD:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(PAD);
+ }
+ return false;
+ break;
+ case GHERKIN50:
+ if (record->event.pressed) {
+ set_single_persistent_default_layer(GK50);
+ }
+ return false;
+ break;
+ case SUBTER:
+ if (record->event.pressed) {
+ layer_on(SUB);
+ } else {
+ layer_off(SUB);
+ }
+ return false;
+ break;
+ case SUPRA:
+ if (record->event.pressed) {
+ layer_on(SUP);
+ } else {
+ layer_off(SUP);
+ }
+ return false;
+ break;
+ case NUMBER:
+ if (record->event.pressed) {
+ layer_on(NUM);
+ } else {
+ layer_off(NUM);
+ }
+ return false;
+ break;
+ case DIRECTION:
+ if (record->event.pressed) {
+ layer_on(DIR);
+ } else {
+ layer_off(DIR);
+ }
+ return false;
+ break;
+ case ETCETERA:
+ if (record->event.pressed) {
+ layer_on(ETC);
+ } else {
+ layer_off(ETC);
+ }
+ return false;
+ break;
+ case gNUMBER:
+ if (record->event.pressed) {
+ layer_on(gNUM);
+ } else {
+ layer_off(gNUM);
+ }
+ return false;
+ break;
+ case gDIRECTION:
+ if (record->event.pressed) {
+ layer_on(gDIR);
+ } else {
+ layer_off(gDIR);
+ }
+ return false;
+ break;
+ case gETCETERA:
+ if (record->event.pressed) {
+ layer_on(gETC);
+ } else {
+ layer_off(gETC);
+ }
+ return false;
+ break;
+ case FUNCTION:
+ if (record->event.pressed) {
+ layer_on(_FN);
+ } else {
+ layer_off(_FN);
+ }
+ return false;
+ break;
+ }
+ return true;
+}
+
+/// Turn off LEDs on ProMicros of Let's Split ///
+// LEDs only on by default on Let's Split
+// Add reconfigurable functions here, for keymap customization
+// This allows for a global, userspace functions, and continued
+// customization of the keymap. Use _keymap instead of _user
+// functions in the keymaps
+__attribute__ ((weak))
+void matrix_init_keymap(void) {}
+
+// Call user matrix init, then call the keymap's init function
+void matrix_init_user(void) {
+#if defined(KEYBOARD_lets_split_rev2)
+ DDRD &= ~(1<<5);
+ PORTD &= ~(1<<5);
+
+ DDRB &= ~(1<<0);
+ PORTB &= ~(1<<0);
+#endif
+ matrix_init_keymap();
+} \ No newline at end of file
diff --git a/users/wanleg/wanleg.h b/users/wanleg/wanleg.h
new file mode 100644
index 0000000000..9d07760a7b
--- /dev/null
+++ b/users/wanleg/wanleg.h
@@ -0,0 +1,309 @@
+#pragma once
+
+#include "quantum.h"
+
+// Define layer names and order
+#ifdef KEYBOARD_gherkin
+enum userspace_layers {
+ gGK = 0,
+ gNUM,
+ gDIR,
+ gETC,
+ _GK,
+ _QW,
+ ONE,
+ SUB,
+ SUP,
+ NUM,
+ DIR,
+ ETC,
+ _FN,
+ PAD,
+ GK50,
+};
+#elif KEYBOARD_40percentclub_5x5
+enum userspace_layers {
+ GK50 = 0,
+ _GK,
+ _QW,
+ PAD,
+ gNUM,
+ gDIR,
+ gETC,
+ gGK,
+ ONE,
+ SUB,
+ SUP,
+ NUM,
+ DIR,
+ ETC,
+ _FN,
+};
+#else
+ enum userspace_layers {
+ _GK = 0,
+ _QW,
+ PAD,
+ ONE,
+ SUB,
+ SUP,
+ NUM,
+ DIR,
+ ETC,
+ gGK,
+ gNUM,
+ gDIR,
+ gETC,
+ _FN,
+ GK50,
+};
+#endif
+
+enum userspace_custom_keycodes {
+ gGHERKIN = SAFE_RANGE,
+ GHERKIN,
+ QWERTY,
+ ONEHAND,
+ SUBTER,
+ SUPRA,
+ NUMBER,
+ DIRECTION,
+ ETCETERA,
+ gNUMBER,
+ gDIRECTION,
+ gETCETERA,
+ FUNCTION,
+ NUMPAD,
+ GHERKIN50,
+
+};
+
+//Tap Dance Declarations (list of my tap dance configurations)
+#ifdef TAP_DANCE_ENABLE
+enum {
+ TD_SFT_CAPS = 0
+ ,TD_Q_ESC
+ ,CAD_TD
+ ,RST_TAP_DANCE
+ ,LYR_TAP_DANCE
+ ,LYR50_TAP_DANCE
+ ,LYR75_TAP_DANCE
+ ,BSW_TAP_DANCE
+};
+#endif
+
+// Since our quirky block definitions are basically a list of comma separated
+// arguments, we need a wrapper in order for these definitions to be
+// expanded before being used as arguments to the LAYOUT_xxx macro.
+#if (!defined(LAYOUT) && defined(KEYMAP))
+#define LAYOUT KEYMAP
+#endif
+
+#define KEYMAP_wrapper(...) LAYOUT(__VA_ARGS__)
+#define LAYOUT_wrapper(...) LAYOUT(__VA_ARGS__)
+#define LAYOUT_ortho_3x10_wrapper(...) LAYOUT_ortho_3x10(__VA_ARGS__)
+#define LAYOUT_ortho_4x4_wrapper(...) LAYOUT_ortho_4x4(__VA_ARGS__)
+#define LAYOUT_ortho_4x12_wrapper(...) LAYOUT_ortho_4x12(__VA_ARGS__)
+#define LAYOUT_ortho_5x5_wrapper(...) LAYOUT_ortho_5x5(__VA_ARGS__)
+#define LAYOUT_ortho_5x10_wrapper(...) LAYOUT_ortho_5x10(__VA_ARGS__)
+#define LAYOUT_ortho_5x15_wrapper(...) LAYOUT_ortho_5x15(__VA_ARGS__)
+
+// Blocks for each of the major keyboard layouts
+// Organized so we can quickly adapt and modify all of them
+// at once, rather than for each keyboard, one at a time.
+// And this allows for much cleaner blocks in the keymaps.
+
+// NOTE: These are all the same length. If you do a search/replace
+// then you need to add/remove underscores to keep the
+// lengths consistent.
+
+
+/* Pure Gherkin
+ * .-----------------------------------------------------------------------------------------.
+ * | Q//ESC | W | E | R | T | Y | U | I | O | P |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | A | S | D | F | G | H | J | K | L | SPACE |
+ * | | | | | | | | | |SFThold |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | Z | X | C | V/gNUM | B/gETC | N | M/gDIR | ,/GUI | ./ALT | BSPC |
+ * | SFThold| | | | | | | | |CTRLhold|
+ * '-----------------------------------------------------------------------------------------'
+ */
+#define _______________Gherkin_Row_0_______________ TD(TD_Q_ESC), KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P
+#define _______________Gherkin_Row_1_______________ KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, SFT_T(KC_SPC)
+#define _______________Gherkin_Row_2_______________ SFT_T(KC_Z), KC_X, KC_C, LT(gNUM,KC_V), LT(gETC,KC_B), KC_N, LT(gDIR,KC_M), GUI_T(KC_COMM), ALT_T(KC_DOT), CTL_T(KC_BSPC)
+
+/* Directional Keys
+ * .-----------------------------------------------------------------------------------------.
+ * | TAB | up | | INS | CTRL | SHIFT | PgUp | HOME | - | = |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | left | down | right | PrScr | SHIFT | CTRL | PgDn | END | [ | ] |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | P-Brk | | | | | | | RGUI | ALT | / |
+ * '-----------------------------------------------------------------------------------------'
+ */
+#define _______________Gherkin_DIR_0_______________ KC_TAB, KC_UP, _______, KC_INS, KC_LCTL, KC_RSFT, KC_PGUP, KC_HOME, KC_MINS, KC_EQL
+#define _______________Gherkin_DIR_1_______________ KC_LEFT, KC_DOWN, KC_RGHT, KC_PSCR, KC_LSFT, KC_RCTL, KC_PGDN, KC_END, KC_LBRC, KC_RBRC
+#define _______________Gherkin_DIR_2_______________ KC_PAUS, _______, _______, _______, _______, _______, _______, KC_RGUI, KC_LALT, KC_SLSH
+
+/* Numbers
+ * .-----------------------------------------------------------------------------------------.
+ * | F1 | F2 | F3 | F4 | F5 | F6 | F7 | F8 | F9 | F10 |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | F11 | F12 | | | | ENTER | SHIFT | GUI | ./ALT | BSPC |
+ * | | | | | | | | | |CTRLhold|
+ * '-----------------------------------------------------------------------------------------'
+ */
+#define _______________Gherkin_NUM_0_______________ KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10
+#define _______________Gherkin_NUM_1_______________ KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0
+#define _______________Gherkin_NUM_2_______________ KC_F11, KC_F12, _______,_______, _______, KC_ENT, KC_RSFT, KC_RGUI, ALT_T(KC_DOT), CTL_T(KC_BSPC)
+
+/* Et Cetera
+ * .-----------------------------------------------------------------------------------------.
+ * | ` | mUP | | | RESET | SHIFT | mScrDn | mScrUp | | \ |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | mLeft | mDown | mRight | | SHIFT | mBtn3 | mBtn1 | mBtn2 | ; | ' |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | Sft//Cp| CAPS | | | | C-A-D | mScrL | mScrR | ALT | DEL |
+ * '-----------------------------------------------------------------------------------------'
+ */
+#define _______________Gherkin_ETC_0_______________ KC_GRV, KC_MS_U, _______,_______, RESET, KC_RSFT, KC_WH_D, KC_WH_U, _______, KC_BSLS
+#define _______________Gherkin_ETC_1_______________ KC_MS_L, KC_MS_D, KC_MS_R,_______, KC_LSFT, KC_BTN3, KC_BTN1, KC_BTN2, KC_SCLN, KC_QUOT
+#define _______________Gherkin_ETC_2_______________ TD(TD_SFT_CAPS),KC_CAPS, _______,_______, _______, LALT(LCTL(KC_DEL)), KC_WH_L, KC_WH_R, KC_LALT, KC_DEL
+
+/* Gherkin-Like
+ * .-----------------------------------------------------------------------------------------------------------.
+ * | ESC | Q//ESC | W | E | R | T | Y | U | I | O | P | BSPC |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | TAB | A | S | D | F | G | H | J | K | L | SPACE | ' |
+ * | | | | | | | | | | |SFThold | |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * |SFT/CAPS| Z | X | C | V/NUM | B/ETC | N | M/DIR | ,/GUI | ./ALT | BSPC | ENT/SFT|
+ * | |SFThold | | | | | | | | |CTRLhold| |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | LCTRL | LGUI | ALT | ONEHAND| NUM | ETC | SPACE | DIR | RGUI | ALT | DEL | CTRL |
+ * '-----------------------------------------------------------------------------------------------------------'
+ */
+#define _______________GherkinLike_0_______________ KC_ESC, _______________Gherkin_Row_0_______________, KC_BSPC
+#define _______________GherkinLike_1_______________ KC_TAB, _______________Gherkin_Row_1_______________, KC_QUOT
+#define _______________GherkinLike_2_______________ TD(TD_SFT_CAPS), SFT_T(KC_Z), KC_X, KC_C, LT(NUM, KC_V),LT(ETC, KC_B),KC_N, LT(DIR, KC_M), GUI_T(KC_COMM), ALT_T(KC_DOT), CTL_T(KC_BSPC), SFT_T(KC_ENT)
+#define _______________GherkinLike_3_______________ KC_LCTL, KC_LGUI, KC_LALT, KC_LALT, NUMBER, ETCETERA, KC_SPC,DIRECTION, KC_RGUI, KC_RALT, KC_DEL, KC_RCTL
+#define _______________GherkinLike_3_OneHand_______ KC_LCTL, KC_LGUI, KC_LALT, ONEHAND, NUMBER, ETCETERA, KC_SPC,DIRECTION, KC_RGUI, KC_RALT, ONEHAND, KC_RCTL
+
+/* Qwerty
+ * .-------------------------------------------------------------------------------------.
+ * | Esc | Q | W | E | R | T | Y | U | I | O | P | BSPC |
+ * |-------+------+------+------+------+-------------+------+------+------+------+-------|
+ * | Tab | A | S | D | F | G | H | J | K | L | ; | ' |
+ * |-------+------+------+------+------+------|------+------+------+------+------+-------|
+ * |Sft/Cps| Z | X | C | V | B | N | M | , | . | / |ENT/SFT|
+ * |-------+------+------+------+------+------+------+------+------+------+------+-------|
+ * | LCTRL | LGUI | ALT | ALT | SUB | SHIFT| SPACE| SUP | RGUI | RALT | DEL | CTRL |
+ * '-------------------------------------------------------------------------------------'
+ */
+#define _______________Qwerty_Row__0_______________ KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC
+#define _______________Qwerty_Row__1_______________ KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT
+#define _______________Qwerty_Row__2_______________ TD(TD_SFT_CAPS), KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, SFT_T(KC_ENT)
+#define _______________Qwerty_Row__3_______________ KC_LCTL, KC_LGUI, KC_LALT, KC_LALT, SUBTER, KC_LSFT, KC_SPC, SUPRA, KC_RGUI, KC_RALT, KC_DEL, KC_RCTL
+
+/* SUPRA
+ * .-----------------------------------------------------------------------------------------------------------.
+ * | RESET | TAB | up | | INS | CTRL | SHIFT | PgUp | Home | - | = | DEL |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | left | down | right | PrScr | SHIFT | CTRL | PgDn | End | [ | ] | \ |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | P-Brk | | | | | | | RGUI | ALT | | |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | | | | | | | | | | | |
+ * '-----------------------------------------------------------------------------------------------------------'
+ */
+#define ________________SUPRA_Row_0________________ RESET, KC_TAB, KC_UP, _______, KC_INS, KC_LCTL, KC_RSFT, KC_PGUP, KC_HOME, KC_MINS, KC_EQL, KC_DEL
+#define ________________SUPRA_Row_1________________ _______, KC_LEFT, KC_DOWN, KC_RGHT, KC_PSCR, KC_LSFT, KC_RCTL, KC_PGDN, KC_END, KC_LBRC, KC_RBRC, KC_BSLS
+#define ________________SUPRA_Row_2________________ _______, KC_PAUS, _______, _______, _______, _______, _______, _______, KC_RGUI, KC_RALT, _______, _______
+#define ________________SUPRA_Row_3________________ _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______
+
+/* SUBTER
+ * .-----------------------------------------------------------------------------------------------------------.
+ * | | F1 | F2 | F3 | F4 | F5 | F6 | F7 | F8 | F9 | F10 | DEL |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | F11 | F12 | | | | | | RGUI | ./ALT | BSPC | |
+ * | | | | | | | | | | |CTRLhold| |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | | gherkin| | | | ENTER | SHIFT | | | | |
+ * '-----------------------------------------------------------------------------------------------------------'
+ */
+#define _______________SUBTER_Row__0_______________ _______, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_DEL
+#define _______________SUBTER_Row__1_______________ KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, _______
+#define _______________SUBTER_Row__2_______________ _______, KC_F11, KC_F12, _______, _______, _______, _______, _______, KC_RGUI,ALT_T(KC_DOT), CTL_T(KC_BSPC), _______
+#define _______________SUBTER_Row__3_______________ _______, _______, GHERKIN, _______, _______, _______, KC_ENT, KC_LSFT, _______,_______, _______, _______
+
+/* Gherkin Numbers
+ * .-----------------------------------------------------------------------------------------------------------.
+ * | | F1 | F2 | F3 | F4 | F5 | F6 | F7 | F8 | F9 | F10 | BSPC |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | F11 | F12 | | | | ENTER | SHIFT | RGUI | ./ALT | BSPC | |
+ * | | | | | | | | | | |CTRLhold| |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | | | | | | ENTER | SHIFT | RGUI | | | |
+ * '-----------------------------------------------------------------------------------------------------------'
+ */
+#define _______________NUMBERS_Row_0_______________ _______, _______________Gherkin_NUM_0_______________, KC_BSPC
+#define _______________NUMBERS_Row_1_______________ _______, _______________Gherkin_NUM_1_______________, _______
+#define _______________NUMBERS_Row_2_______________ _______, _______________Gherkin_NUM_2_______________, _______
+#define _______________NUMBERS_Row_3_______________ _______, _______, _______, _______, _______, _______, KC_ENT, KC_RSFT, KC_RGUI, _______, _______, _______
+
+
+/* Gherkin Directional Keys
+ * .-----------------------------------------------------------------------------------------------------------.
+ * | | TAB | up | | INS | CTRL | SHIFT | PgUp | HOME | - | = | DEL |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | left | down | right | PrScr | SHIFT | CTRL | PgDn | END | [ | ] | |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | P-Brk | | | | | | | RGUI | ALT | / | |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | | qwerty | | | | | | | | | |
+ * '-----------------------------------------------------------------------------------------------------------'
+ */
+#define _____________DIRECTIONS_Row__0_____________ _______, _______________Gherkin_DIR_0_______________, KC_DEL
+#define _____________DIRECTIONS_Row__1_____________ _______, _______________Gherkin_DIR_1_______________, _______
+#define _____________DIRECTIONS_Row__2_____________ _______, _______________Gherkin_DIR_2_______________, _______
+#define _____________DIRECTIONS_Row__3_____________ _______, _______, QWERTY, _______, _______, _______, _______, _______, _______, _______, _______, _______
+
+/* Gherkin Et Cetera
+ * .-----------------------------------------------------------------------------------------------------------.
+ * | | ` | mUP | | | RESET | SHIFT | mScrUp |mScrDown| | \ | DEL |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | mLeft | mDown | mRight | | SHIFT | mBtn3 | mBtn1 | mBtn2 | ; | ' | |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | Sft//Cp| | | | | C-A-D |mScrLeft| mScrRt | ALT | DEL | |
+ * |--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------+--------|
+ * | | | | | | | C-A-D | | | | | |
+ * '-----------------------------------------------------------------------------------------------------------'
+ */
+#define ______________ETCETERA_Row__0______________ _______, _______________Gherkin_ETC_0_______________, KC_DEL
+#define ______________ETCETERA_Row__1______________ _______, _______________Gherkin_ETC_1_______________, _______
+#define ______________ETCETERA_Row__2______________ _______, _______________Gherkin_ETC_2_______________, _______
+#define ______________ETCETERA_Row__3______________ _______, _______, _______, _______, _______, _______, LALT(LCTL(KC_DEL)), _______, _______, _______, _______, _______
+
+/* Single 4x4 board only
+ * .-----------------------------------.
+ * | 7 | 8 | 9 | BSPC |
+ * |--------+--------+--------+--------|
+ * | 4 | 5 | 6 | SPACE |
+ * |--------+--------+--------+--------|
+ * | 1 | 2 | 3 | ENTER |
+ * |--------+--------+--------+--------|
+ * | 0 |/ //_GK | . | - |
+ * '-----------------------------------'
+ */
+
+#define _______________NUMPAD_Row__0_______________ KC_KP_7, KC_KP_8, KC_KP_9, KC_BSPC
+#define _______________NUMPAD_Row__1_______________ KC_KP_4, KC_KP_5, KC_KP_6, KC_SPC
+#define _______________NUMPAD_Row__2_______________ KC_KP_1, KC_KP_2, KC_KP_3, KC_PENT
+#define _______________NUMPAD_Row__3_______________ KC_KP_0, TD(LYR_TAP_DANCE), KC_KP_DOT, KC_PMNS
diff --git a/users/xtonhasvim/fancylighting.c b/users/xtonhasvim/fancylighting.c
new file mode 100644
index 0000000000..a88ca4beb3
--- /dev/null
+++ b/users/xtonhasvim/fancylighting.c
@@ -0,0 +1,172 @@
+ /* Copyright 2015-2017 Christon DeWan
+ *
+ * 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, either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 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/>.
+ */
+
+#ifdef RGBLIGHT_ENABLE
+
+#include <math.h>
+
+#include "rgblight.h"
+#include "color.h"
+#include "fancylighting.h"
+
+
+__attribute__ ((weak))
+void matrix_scan_keymap(void) {
+ // override me, if you want.
+ return;
+}
+
+#define ABSDIFF(a,b) ((a)>(b)?(a)-(b):(b)-(a))
+
+#define FADE_BACK_TIME 500
+#define BREATH_FIRE_TIME 1000
+#define ANIMATION_STEP_INTERVAL 20
+
+#if RGBLED_NUM >= 2
+#define POWER_KEY_OFFSET (RGBLED_NUM / 2)
+#define SPACE_OFFSET_MAX (RGBLED_NUM / 2)
+#else
+#define POWER_KEY_OFFSET 1
+#define SPACE_OFFSET_MAX 1
+#endif
+
+uint16_t effect_start_timer = 0;
+uint8_t user_rgb_mode = 0;
+LED_TYPE shadowed_led[RGBLED_NUM] = {{0}};
+
+void start_firey_return(void) {
+ user_rgb_mode = BREATH_FIRE;
+ effect_start_timer = timer_read();
+ for(uint8_t i = 0; i < RGBLED_NUM; i++) {
+ shadowed_led[i] = led[i];
+ }
+}
+
+/** 0---max
+ * [___]
+ * [__/]
+ * [_/\]
+ * [/\_]
+ * [\__]
+ * [___]
+ **/
+
+void set_color_for_offsets(uint16_t time_offset, uint16_t space_offset, uint8_t idx) {
+ float time_progress = (float)time_offset / BREATH_FIRE_TIME;
+ float space_progress = (float)space_offset / SPACE_OFFSET_MAX;
+ float progress = time_progress * 5.0 - space_progress;
+ if(progress > 1.0) {
+ progress -= 1.0;
+ progress /= 4.0;
+ progress = 1.0 - progress;
+ }
+ progress = fmax(0.0,progress);
+ progress *= progress; // squared!
+
+ float alpha = (time_progress + 0.1) * 7.0 - space_progress;
+ alpha = fmin(1.0, alpha*alpha);
+
+ LED_TYPE px[1] = {{0}};
+ sethsv((uint16_t)(fmod(time_progress * 1.5 + space_progress,1.0)*360), 255, (uint8_t)(progress*255),&px[0]);
+ led[idx].r = alpha * px[0].r + ( 1.0 - alpha) * shadowed_led[idx].r;
+ led[idx].g = alpha * px[0].g + ( 1.0 - alpha) * shadowed_led[idx].g;
+ led[idx].b = alpha * px[0].b + ( 1.0 - alpha) * shadowed_led[idx].b;
+}
+
+/**
+ * It's actually a rainbow: a fire curve didn't really look right.
+ * it's still cool, though!
+ */
+void rgb_mode_breath_fire(void) {
+ static uint16_t last_timer = 0;
+ if(!last_timer) last_timer = timer_read();
+ uint16_t this_timer = timer_read();
+
+ // too soon. don't spam updates
+ if(this_timer - last_timer < ANIMATION_STEP_INTERVAL) return;
+
+ uint16_t elapsed = this_timer - effect_start_timer;
+
+ last_timer = this_timer;
+ if(elapsed >= BREATH_FIRE_TIME) {
+ // complete
+ user_rgb_mode = FADE_BACK;
+ effect_start_timer = this_timer;
+ } else {
+ // linear fade
+ for(uint16_t i = 0; i < RGBLED_NUM; i++) {
+ uint16_t space_offset = ABSDIFF(i,POWER_KEY_OFFSET);
+ if(space_offset > SPACE_OFFSET_MAX) space_offset = RGBLED_NUM - space_offset;
+
+ set_color_for_offsets(elapsed, space_offset, i);
+ }
+ rgblight_set();
+ }
+}
+
+void rgb_mode_fade_back(void) {
+ static uint16_t last_timer = 0;
+ if(!last_timer) last_timer = timer_read();
+ uint16_t this_timer = timer_read();
+
+ // too soon. don't spam updates
+ if(this_timer - last_timer < ANIMATION_STEP_INTERVAL) return;
+
+ uint16_t elapsed = this_timer - effect_start_timer;
+
+ last_timer = this_timer;
+ float progress = (float)elapsed / FADE_BACK_TIME;
+ progress = fmin(1.0,progress);
+
+ for(uint8_t i = 0; i < RGBLED_NUM; i++) {
+ led[i].r = shadowed_led[i].r * progress;
+ led[i].g = shadowed_led[i].g * progress;
+ led[i].b = shadowed_led[i].b * progress;
+ }
+ rgblight_set();
+
+ if(elapsed >= FADE_BACK_TIME) user_rgb_mode = 0;
+}
+
+/** called when layer state or vstate has changed */
+__attribute__ ((weak))
+void set_state_leds(void) {
+ return;
+}
+
+void matrix_scan_user(void) {
+ static uint32_t last_layer = 0;
+ static uint32_t last_vstate = 0;
+ if(last_layer != layer_state || last_vstate != vstate) set_state_leds();
+ last_layer = layer_state;
+ last_vstate = vstate;
+
+ switch (user_rgb_mode) {
+ case BREATH_FIRE:
+ rgb_mode_breath_fire();
+ break;
+ case FADE_BACK:
+ rgb_mode_fade_back();
+ break;
+ }
+ matrix_scan_keymap();
+}
+
+#else
+
+void start_firey_return(void) {}
+
+#endif
diff --git a/users/xtonhasvim/fancylighting.h b/users/xtonhasvim/fancylighting.h
new file mode 100644
index 0000000000..02fb58b84a
--- /dev/null
+++ b/users/xtonhasvim/fancylighting.h
@@ -0,0 +1,36 @@
+/* Copyright 2015-2017 Christon DeWan
+ *
+ * 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, either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 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/>.
+ */
+
+#ifndef _fancy_lighting_h
+#define _fancy_lighting_h
+#ifdef RGBLIGHT_ENABLE
+
+#include "xtonhasvim.h"
+
+
+extern uint8_t user_rgb_mode;
+extern LED_TYPE shadowed_led[];
+
+
+#endif //RGBLIGHT_ENABLE
+void start_firey_return(void);
+
+enum xtonhasvim_rgbmodes {
+ BREATH_FIRE = 1,
+ FADE_BACK
+};
+
+#endif //_fancy_lighting_h
diff --git a/users/xtonhasvim/rules.mk b/users/xtonhasvim/rules.mk
index 3777917f8f..a901bfcf67 100644
--- a/users/xtonhasvim/rules.mk
+++ b/users/xtonhasvim/rules.mk
@@ -1 +1,2 @@
SRC += xtonhasvim.c
+SRC += fancylighting.c
diff --git a/users/xtonhasvim/xtonhasvim.c b/users/xtonhasvim/xtonhasvim.c
index a2ff2fa31c..5f6701830f 100644
--- a/users/xtonhasvim/xtonhasvim.c
+++ b/users/xtonhasvim/xtonhasvim.c
@@ -15,6 +15,7 @@
*/
#include "xtonhasvim.h"
+#include "fancylighting.h"
/************************************
* helper foo
@@ -53,13 +54,13 @@ static void ALT(uint16_t keycode) {
}
-static uint16_t vstate = VIM_START;
+uint16_t vstate = VIM_START;
static bool yank_was_lines = false;
static bool SHIFTED = false;
static uint32_t mod_override_layer_state = 0;
static uint16_t mod_override_triggering_key = 0;
-static void edit(void) { vstate = VIM_START; layer_on(_EDIT); layer_off(_CMD); }
+static void edit(void) { vstate = VIM_START; layer_clear(); }
#define EDIT edit()
@@ -102,25 +103,54 @@ static void simple_movement(uint16_t keycode) {
}
}
+static void comma_period(uint16_t keycode) {
+ switch (keycode) {
+ case VIM_COMMA:
+ if (SHIFTED) {
+ // indent
+ CMD(KC_LBRACKET);
+ } else {
+ // toggle comment
+ CMD(KC_SLASH);
+ }
+ break;
+ case VIM_PERIOD:
+ if (SHIFTED) {
+ // outdent
+ CMD(KC_RBRACKET);
+ }
+ break;
+ }
+}
+
__attribute__ ((weak))
bool process_record_keymap(uint16_t keycode, keyrecord_t *record) {
return true;
}
-#define PASS_THRU process_record_keymap(keycode, record)
-
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
- if(record->event.pressed && layer_state_is(_CMD) && IS_MOD(keycode)) {
+ /* keymap gets first whack */
+ if(!process_record_keymap(keycode, record)) return false;
+
+ /****** FIREY_RETURN *****/
+ if(record->event.pressed && keycode == FIREY_RETURN) {
+ start_firey_return();
+ TAP(KC_ENT);
+ }
+
+ /****** mod passthru *****/
+ if(record->event.pressed && layer_state_is(vim_cmd_layer()) && (IS_MOD(keycode) || keycode == LSFT(KC_LALT))) {
mod_override_layer_state = layer_state;
mod_override_triggering_key = keycode;
+ // TODO: change this to track key location instead
layer_clear();
- return PASS_THRU; // let the event fall through...
+ return true; // let the event fall through...
}
if(mod_override_layer_state && !record->event.pressed && keycode == mod_override_triggering_key) {
layer_state_set(mod_override_layer_state);
mod_override_layer_state = 0;
mod_override_triggering_key = 0;
- return PASS_THRU;
+ return true;
}
if (VIM_START <= keycode && keycode <= VIM_ESC) {
@@ -132,7 +162,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
if (record->event.pressed) {
if(keycode == VIM_START) {
// entry from anywhere
- layer_on(_CMD);
+ layer_on(vim_cmd_layer());
vstate = VIM_START;
// reset state
@@ -176,7 +206,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
break;
case VIM_D:
if(SHIFTED) {
- TAP(KC_K);
+ CTRL(KC_K);
} else {
vstate = VIM_D;
}
@@ -300,19 +330,8 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
}
break;
case VIM_COMMA:
- if(SHIFTED) {
- // indent
- CMD(KC_LBRACKET);
- } else {
- // toggle comment
- CMD(KC_SLASH);
- }
- break;
case VIM_PERIOD:
- if(SHIFTED) {
- // outdent
- CMD(KC_RBRACKET);
- }
+ comma_period(keycode);
break;
}
break;
@@ -483,6 +502,10 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
TAP(KC_RIGHT);
vstate = VIM_START;
break;
+ case VIM_COMMA:
+ case VIM_PERIOD:
+ comma_period(keycode);
+ break;
default:
// do nothing
break;
@@ -539,6 +562,10 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
TAP(KC_RIGHT);
vstate = VIM_START;
break;
+ case VIM_COMMA:
+ case VIM_PERIOD:
+ comma_period(keycode);
+ break;
default:
// do nothing
break;
@@ -610,6 +637,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
}
return false;
} else {
- return PASS_THRU;
+ return true;
}
}
+
diff --git a/users/xtonhasvim/xtonhasvim.h b/users/xtonhasvim/xtonhasvim.h
index 21b794c033..2d6670a5e6 100644
--- a/users/xtonhasvim/xtonhasvim.h
+++ b/users/xtonhasvim/xtonhasvim.h
@@ -22,10 +22,9 @@
#define X_____X KC_NO
-bool process_record_xtonhasvim(uint16_t keycode, keyrecord_t *record);
-
enum xtonhasvim_keycodes {
- DUMMY = SAFE_RANGE,
+ // 20: give keyboard-specific codes some room
+ FIREY_RETURN = SAFE_RANGE + 20, // kick off special effects
VIM_START, // bookend for vim states
VIM_A,
VIM_B,
@@ -57,10 +56,10 @@ enum xtonhasvim_keycodes {
VIM_SAFE_RANGE // start other keycodes here.
};
-enum xtonhasvim_layers {
- _EDIT = 12,
- _CMD
-};
+// NOTE: YOU MUST DEFINE THIS
+extern uint8_t vim_cmd_layer(void);
+
+extern uint16_t vstate;
#endif
diff --git a/users/zer09/config.h b/users/zer09/config.h
index 7668064622..c5ab32f8d4 100644
--- a/users/zer09/config.h
+++ b/users/zer09/config.h
@@ -11,18 +11,18 @@
// actually sends Ctrl-x. That's bad.)
#define IGNORE_MOD_TAP_INTERRUPT
#undef PERMISSIVE_HOLD
-#undef PREVENT_STUCK_MODIFIERS
+#define STRICT_LAYER_RELEASE
#define FORCE_NKRO
#ifndef TAPPING_TOGGLE
-#define TAPPING_TOGGLE 1
+#define TAPPING_TOGGLE 1
#endif
#ifdef TAPPING_TERM
#undef TAPPING_TERM
#endif
-#define TAPPING_TERM 120
+#define TAPPING_TERM 95
// Disable action_get_macro and fn_actions, since we don't use these
// and it saves on space in the firmware.
diff --git a/users/zer09/tap_dance.c b/users/zer09/tap_dance.c
index a23705ad8b..e99b26cca0 100644
--- a/users/zer09/tap_dance.c
+++ b/users/zer09/tap_dance.c
@@ -17,15 +17,27 @@ qk_tap_dance_action_t tap_dance_actions[] = {
};
volatile uint8_t active_layer = _BL;
+volatile uint8_t gm_layer_act = false;
static tap upltap_state = {.state = 0};
static tap dwltap_state = {.state = 0};
static tap lsprtap_state = {.state = 0};
static tap ralttap_state = {.state = 0};
void layer_switcher_tap(uint8_t new_layer) {
- layer_off(active_layer);
- layer_on(new_layer);
- active_layer = new_layer;
+ if (gm_layer_act == true) {
+ layer_off(active_layer);
+ if (new_layer == _BL) {
+ layer_on(_GM);
+ active_layer = _GM;
+ } else {
+ layer_on(new_layer);
+ active_layer = new_layer;
+ }
+ } else {
+ layer_off(active_layer);
+ layer_on(new_layer);
+ active_layer = new_layer;
+ }
}
int cur_dance(qk_tap_dance_state_t *state) {
@@ -162,6 +174,14 @@ void dance_dwly_finished(qk_tap_dance_state_t *state, void *user_data) {
case DOUBLE_HOLD:
layer_switcher_tap(_AL);
break;
+ case TRIPLE_TAP:
+ if (gm_layer_act == true) {
+ gm_layer_act = false;
+ layer_switcher_tap(_BL);
+ } else {
+ gm_layer_act = true;
+ layer_switcher_tap(_GM);
+ }
default:
layer_switcher_tap(_BL);
break;
@@ -174,6 +194,7 @@ void dance_dwly_reset(qk_tap_dance_state_t *state, void *user_data) {
break;
case SINGLE_HOLD:
case DOUBLE_HOLD:
+ case TRIPLE_TAP:
default:
layer_switcher_tap(_BL);
break;
diff --git a/users/zer09/zer09.h b/users/zer09/zer09.h
index 75c1d3cad4..acac8ab09f 100644
--- a/users/zer09/zer09.h
+++ b/users/zer09/zer09.h
@@ -3,16 +3,24 @@
#include "quantum.h"
-enum custom_keycodes { CK_SAFE = SAFE_RANGE, RGUP, RGDWN, NEWPLACEHOLDER };
+enum custom_keycodes {
+ CK_SAFE = SAFE_RANGE,
+ RGUP,
+ RGDWN,
+ YREG,
+ NEW_SAFE_RANGE
+};
#define _______ KC_TRNS
#define KC_RGUP RGUP
#define KC_RGDWN RGDWN
+#define KC_YREG YREG
#define _BL 0 // The base layer
#define _UL 1 // The up layer
#define _DL 2 // The down layer
#define _VL 3 // The shifted up layer
#define _AL 4 // The assorted layer
+#define _GM 5
#endif