From daa8a008db52ca5c4985db57075a55a9732721a1 Mon Sep 17 00:00:00 2001 From: Gabriel Diegel Date: Tue, 15 Dec 2015 21:36:01 +0100 Subject: [PATCH 01/12] Fix typos and add comments, swap plus with equals, swap pipe with backslash, move slash, change cursor keys to make the classic shape --- keyboard/planck/keymaps/keymap_gabriel.c | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/keyboard/planck/keymaps/keymap_gabriel.c b/keyboard/planck/keymaps/keymap_gabriel.c index 3620c75a75..b933d7d110 100644 --- a/keyboard/planck/keymaps/keymap_gabriel.c +++ b/keyboard/planck/keymaps/keymap_gabriel.c @@ -9,9 +9,9 @@ #define _RS 2 #define _FN 3 -// This a slightly adapted 'default' keymap. I like the position of 'esc' and 'tab' better this way. -// I also git rid of the backlighting control key and the dvorak and colemak layers. I added a 'fn' -// layer that makes the 'bspc' a forward delete (like on OSX). +// This a slightly modified 'default' keymap that's closer to the Mac keyboard layout. I like the position +// of 'esc' and 'tab' better this way. I also got rid of the backlighting control key and the dvorak and +// colemak layers. I added a 'fn' layer that makes the 'bspc' a forward delete (like on OSX). const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { /* MIT Layout (QWERTY layer) * @@ -20,23 +20,23 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { * |-----------------------------------------------------------------------| * | tab | a | s | d | f | g | h | j | k | l | ; | ' | * |-----------------------------------------------------------------------| - * |shift| z | x | c | v | b | n | m | , | . | / |enter| + * |shift| z | x | c | v | b | n | m | , | . | up |enter| * |-----------------------------------------------------------------------| - * | fn | ctl | alt | cmd |lower| spc |raise| left| down| up |right| + * | fn | ctl | alt | cmd |lower| spc |raise| / | left|down |right| * `-----------------------------------------------------------------------' */ [_QW] = { /* QWERTY */ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC}, {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT}, - {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT }, - {MO(_FN), KC_LCTL, KC_LALT, KC_LGUI, MO(_LW), KC_SPC, KC_SPC, MO(_RS), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT} + {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_UP, KC_ENT }, + {MO(_FN), KC_LCTL, KC_LALT, KC_LGUI, MO(_LW), KC_SPC, KC_SPC, MO(_RS), KC_SLSH, KC_LEFT, KC_DOWN, KC_RGHT} }, /* MIT Layout (Raised layer) * * ,-----------------------------------------------------------------------. * | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | | * |-----------------------------------------------------------------------| - * | | F1 | F2 | F3 | F4 | F5 | F6 | - | = | [ | ] | \ | + * | | F1 | F2 | F3 | F4 | F5 | F6 | - | + | [ | ] | | | * |-----------------------------------------------------------------------| * | | F7 | F8 | F9 | F10 | F11 | F12 | | | | | | * |-----------------------------------------------------------------------| @@ -45,7 +45,7 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { */ [_RS] = { /* RAISE */ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC}, - {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS}, + {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_MINS, KC_PLUS, KC_LBRC, KC_RBRC, KC_PIPE}, {KC_TRNS, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}, {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS} }, @@ -54,7 +54,7 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { * ,-----------------------------------------------------------------------. * | ~ | ! | @ | # | $ | % | ^ | & | * | ( | ) | | * |-----------------------------------------------------------------------| - * | | F1 | F2 | F3 | F4 | F5 | F6 | _ | + | { | } | | | + * | | F1 | F2 | F3 | F4 | F5 | F6 | _ | = | { | } | \ | * |-----------------------------------------------------------------------| * | | F7 | F8 | F9 | F10 | F11 | F12 | | | | | | * |-----------------------------------------------------------------------| @@ -63,7 +63,7 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { */ [_LW] = { /* LOWER */ {KC_TILD, KC_EXLM, KC_AT, KC_HASH, KC_DLR, KC_PERC, KC_CIRC, KC_AMPR, KC_ASTR, KC_LPRN, KC_RPRN, KC_BSPC}, - {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_UNDS, KC_PLUS, KC_LCBR, KC_RCBR, KC_PIPE}, + {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_UNDS, KC_EQL, KC_LCBR, KC_RCBR, KC_BSLS}, {KC_TRNS, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}, {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS} }, From 190562288c1522b1fe8c7bc7e4cfdfa1ab98ff65 Mon Sep 17 00:00:00 2001 From: Piet Nutbey Date: Sat, 19 Dec 2015 21:38:56 -0500 Subject: [PATCH 02/12] OSX Kinesis-like Mapping OS X Kinesis Like key mapping. Only the default layer was changed into a more Kinesis-like mapping. Hopefully useful as a starting point. --- keyboard/ergodox_ez/keymap_osx_kinesis_pnut.c | 191 ++++++++++++++++++ 1 file changed, 191 insertions(+) create mode 100644 keyboard/ergodox_ez/keymap_osx_kinesis_pnut.c diff --git a/keyboard/ergodox_ez/keymap_osx_kinesis_pnut.c b/keyboard/ergodox_ez/keymap_osx_kinesis_pnut.c new file mode 100644 index 0000000000..4f36c1b762 --- /dev/null +++ b/keyboard/ergodox_ez/keymap_osx_kinesis_pnut.c @@ -0,0 +1,191 @@ +// Netable differences vs. the default firmware for the ErgoDox EZ: +// 1. The Cmd key is now on the right side, making Cmd+Space easier. +// 2. The media keys work on OSX (But not on Windows). +// Wanted to map default layer of my EZ to my existing Kinesis Mapping. +// Only default layer was remapped all others layers are standard Ergodox EZ +// Very personal mapping of-course, but who knows a starting point for others. + +#include "ergodox_ez.h" +#include "debug.h" +#include "action_layer.h" + +#define BASE 0 // default layer +#define SYMB 1 // symbols +#define MDIA 2 // media keys + +const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { +/* Keymap 0: Basic layer + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | CapsL | 1 | 2 | 3 | 4 | 5 | LEFT | | RIGHT| 6 | 7 | 8 | 9 | 0 | - | + * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------| + * | TAB | Q | W | E | R | T | L1 | | L1 | Y | U | I | O | P | \ | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | ESC | A | S | D | F | G |------| |------| H | J | K | L |; / L2| '" | + * |--------+------+------+------+------+------| Hyper| | Meh |------+------+------+------+------+--------| + * | LShift |Z/Ctrl| X | C | V | B | | | | N | M | , | . |//Ctrl| RShift | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * |Grv/L1| '" |AltShf| Left | Right| | Up | Down | [ | ] | ~L1 | + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | LGui | App | | Ctrl/Esc | RGui | + * ,------|------|------| |------+--------+------. + * | | | Home | | = | | | + * | Backs|Delete|------| |------| Enter |Space | + * | pace | | End | | TAB | | | + * `--------------------' `----------------------' + */ +// If it accepts an argument (i.e, is a function), it doesn't need KC_. +// Otherwise, it needs KC_* +[BASE] = KEYMAP( // layer 0 : default + // left hand + KC_CAPSLOCK, KC_1, KC_2, KC_3, KC_4, KC_5, KC_LEFT, + KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, TG(1), + KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, + KC_LSFT, CTL_T(KC_Z), KC_X, KC_C, KC_V, KC_B, ALL_T(KC_NO), + LALT(KC_LSFT), LT(SYMB,KC_GRV),KC_QUOT,KC_LEFT,KC_RGHT, + KC_LGUI, ALT_T(KC_APP), + KC_HOME, + KC_BSPC,KC_DELT,KC_END, + // right hand + KC_RGHT, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS, + TG(1), KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSLS, + KC_H, KC_J, KC_K, KC_L, LT(MDIA, KC_SCLN),KC_QUOTE, + MEH_T(KC_NO),KC_N, KC_M, KC_COMM,KC_DOT, CTL_T(KC_SLSH), KC_RSFT, + KC_UP, KC_DOWN,KC_LBRC,KC_RBRC, KC_FN1, + CTL_T(KC_ESC), KC_LGUI, + KC_EQL, + KC_TAB, KC_ENT, KC_SPC + ), +/* Keymap 1: Symbol Layer + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | | F1 | F2 | F3 | F4 | F5 | | | | F6 | F7 | F8 | F9 | F10 | F11 | + * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------| + * | | ! | @ | { | } | | | | | | Up | 7 | 8 | 9 | * | F12 | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | # | $ | ( | ) | ` |------| |------| Down | 4 | 5 | 6 | + | | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | % | ^ | [ | ] | ~ | | | | & | 1 | 2 | 3 | \ | | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * | | | | | | | | . | 0 | = | | + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | | | | | | + * ,------|------|------| |------+------+------. + * | | | | | | | | + * | | |------| |------| | | + * | | | | | | | | + * `--------------------' `--------------------' + */ +// SYMBOLS +[SYMB] = KEYMAP( + // left hand + KC_TRNS,KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_TRNS, + KC_TRNS,KC_EXLM,KC_AT, KC_LCBR,KC_RCBR,KC_PIPE,KC_TRNS, + KC_TRNS,KC_HASH,KC_DLR, KC_LPRN,KC_RPRN,KC_GRV, + KC_TRNS,KC_PERC,KC_CIRC,KC_LBRC,KC_RBRC,KC_TILD,KC_TRNS, + KC_TRNS,KC_TRNS,KC_TRNS,KC_TRNS,KC_TRNS, + KC_TRNS,KC_TRNS, + KC_TRNS, + KC_TRNS,KC_TRNS,KC_TRNS, + // right hand + KC_TRNS, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, + KC_TRNS, KC_UP, KC_7, KC_8, KC_9, KC_ASTR, KC_F12, + KC_DOWN, KC_4, KC_5, KC_6, KC_PLUS, KC_TRNS, + KC_TRNS, KC_AMPR, KC_1, KC_2, KC_3, KC_BSLS, KC_TRNS, + KC_TRNS,KC_DOT, KC_0, KC_EQL, KC_TRNS, + KC_TRNS, KC_TRNS, + KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS +), +/* Keymap 2: Media and mouse keys + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | | | | | | | | | | | | | | | | + * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------| + * | | | | MsUp | | | | | | | | | | | | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | |MsLeft|MsDown|MsRght| |------| |------| | | | | | Play | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | | | | | | | | | | | Prev | Next | | | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * | | | | Lclk | Rclk | |VolUp |VolDn | Mute | | | + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | | | | | | + * ,------|------|------| |------+------+------. + * | | | | | | |Brwser| + * | | |------| |------| |Back | + * | | | | | | | | + * `--------------------' `--------------------' + */ +// MEDIA AND MOUSE +KEYMAP( + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_MS_U, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_MS_L, KC_MS_D, KC_MS_R, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_BTN1, KC_BTN2, + KC_TRNS, KC_TRNS, + KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, + // right hand + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_MPLY, + KC_TRNS, KC_TRNS, KC_TRNS, KC_MPRV, KC_MNXT, KC_TRNS, KC_TRNS, + KC_VOLU, KC_VOLD, KC_MUTE, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, + KC_TRNS, + KC_TRNS, KC_TRNS, KC_WBAK +), +}; + +const uint16_t PROGMEM fn_actions[] = { + [1] = ACTION_LAYER_TAP_TOGGLE(SYMB) // FN1 - Momentary Layer 1 (Symbols) +}; + +const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt) +{ + // MACRODOWN only works in this function + switch(id) { + case 0: + if (record->event.pressed) { + register_code(KC_RSFT); + } else { + unregister_code(KC_RSFT); + } + break; + } + return MACRO_NONE; +}; + +// Runs just one time when the keyboard initializes. +void * matrix_init_user(void) { + +}; + +// Runs constantly in the background, in a loop. +void * matrix_scan_user(void) { + + uint8_t layer = biton32(layer_state); + + ergodox_board_led_off(); + ergodox_right_led_1_off(); + ergodox_right_led_2_off(); + ergodox_right_led_3_off(); + switch (layer) { + // TODO: Make this relevant to the ErgoDox EZ. + case 1: + ergodox_right_led_1_on(); + break; + case 2: + ergodox_right_led_2_on(); + break; + default: + // none + break; + } + +}; From ac3513b79fc171a8efc92a94641e0b88dd43bd4f Mon Sep 17 00:00:00 2001 From: Piet Nutbey Date: Sat, 19 Dec 2015 22:50:48 -0500 Subject: [PATCH 03/12] corrected folder --- keyboard/ergodox_ez/{ => keymaps}/keymap_osx_kinesis_pnut.c | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename keyboard/ergodox_ez/{ => keymaps}/keymap_osx_kinesis_pnut.c (100%) diff --git a/keyboard/ergodox_ez/keymap_osx_kinesis_pnut.c b/keyboard/ergodox_ez/keymaps/keymap_osx_kinesis_pnut.c similarity index 100% rename from keyboard/ergodox_ez/keymap_osx_kinesis_pnut.c rename to keyboard/ergodox_ez/keymaps/keymap_osx_kinesis_pnut.c From cc79f1742472f16199a138e9cefd8fd5ed1bde0e Mon Sep 17 00:00:00 2001 From: Piet Nutbey Date: Sat, 19 Dec 2015 23:24:59 -0500 Subject: [PATCH 04/12] Fixed keymap "graphic" --- keyboard/ergodox_ez/keymaps/keymap_osx_kinesis_pnut.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/keyboard/ergodox_ez/keymaps/keymap_osx_kinesis_pnut.c b/keyboard/ergodox_ez/keymaps/keymap_osx_kinesis_pnut.c index 4f36c1b762..f71ca28ceb 100644 --- a/keyboard/ergodox_ez/keymaps/keymap_osx_kinesis_pnut.c +++ b/keyboard/ergodox_ez/keymaps/keymap_osx_kinesis_pnut.c @@ -25,7 +25,7 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { * |--------+------+------+------+------+------| Hyper| | Meh |------+------+------+------+------+--------| * | LShift |Z/Ctrl| X | C | V | B | | | | N | M | , | . |//Ctrl| RShift | * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' - * |Grv/L1| '" |AltShf| Left | Right| | Up | Down | [ | ] | ~L1 | + * |AltShf|Grv/L1| '" | Left | Right| | Up | Down | [ | ] | ~L1 | * `----------------------------------' `----------------------------------' * ,-------------. ,-------------. * | LGui | App | | Ctrl/Esc | RGui | From d7d092de5f6d09d6d56d7dc0dea5f63d1d212b58 Mon Sep 17 00:00:00 2001 From: Gabriel Diegel Date: Sun, 20 Dec 2015 23:05:15 +0100 Subject: [PATCH 05/12] Use planck-style arrow keys --- keyboard/planck/keymaps/keymap_gabriel.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/keyboard/planck/keymaps/keymap_gabriel.c b/keyboard/planck/keymaps/keymap_gabriel.c index b933d7d110..b84ecd76c3 100644 --- a/keyboard/planck/keymaps/keymap_gabriel.c +++ b/keyboard/planck/keymaps/keymap_gabriel.c @@ -20,16 +20,16 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { * |-----------------------------------------------------------------------| * | tab | a | s | d | f | g | h | j | k | l | ; | ' | * |-----------------------------------------------------------------------| - * |shift| z | x | c | v | b | n | m | , | . | up |enter| + * |shift| z | x | c | v | b | n | m | , | . | / |enter| * |-----------------------------------------------------------------------| - * | fn | ctl | alt | cmd |lower| spc |raise| / | left|down |right| + * | fn | ctl | alt | cmd |lower| spc |raise|left |down | up |right| * `-----------------------------------------------------------------------' */ [_QW] = { /* QWERTY */ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC}, {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT}, - {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_UP, KC_ENT }, - {MO(_FN), KC_LCTL, KC_LALT, KC_LGUI, MO(_LW), KC_SPC, KC_SPC, MO(_RS), KC_SLSH, KC_LEFT, KC_DOWN, KC_RGHT} + {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT }, + {MO(_FN), KC_LCTL, KC_LALT, KC_LGUI, MO(_LW), KC_SPC, KC_SPC, MO(_RS), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT} }, /* MIT Layout (Raised layer) * From a67ef035b88015ae43c045c1f8b0b982e0dc9151 Mon Sep 17 00:00:00 2001 From: Technovangelist Date: Mon, 21 Dec 2015 09:52:10 -0500 Subject: [PATCH 06/12] first attempt at a working workman layout for the ergodoxez --- .../keymaps/keymap_workman_osx_mdw.c | 366 ++++++++++++++++++ 1 file changed, 366 insertions(+) create mode 100644 keyboard/ergodox_ez/keymaps/keymap_workman_osx_mdw.c diff --git a/keyboard/ergodox_ez/keymaps/keymap_workman_osx_mdw.c b/keyboard/ergodox_ez/keymaps/keymap_workman_osx_mdw.c new file mode 100644 index 0000000000..d0195faf34 --- /dev/null +++ b/keyboard/ergodox_ez/keymaps/keymap_workman_osx_mdw.c @@ -0,0 +1,366 @@ +#include "ergodox_ez.h" +#include "debug.h" +#include "action_layer.h" +// README +// This keyboard layout is based on the [Workman Dead layout](https://github.com/ojbucao/Workman/tree/master/mac#workman-dead-for-programmers), which uses the comma as a dead key to trigger a second layer. +// Since I have more keys at my disposal on the ErgoDox, I moved the dead key to the bottom right. There are still a lot of +// blanks so still discovering what I like. +// If you aren't familiar with a dead key, the idea is that you tap the dead key which switches the layout. the next key you hit +// triggers the key you pressed AND switches the layout back to the original. For now I do this with a super kludgey macro and I +// look forward to learning about a more elegant way to do the same thing. Until then, this will have to do. + + +// TODO: Define layer names that make sense for the ErgoDox EZ. +#define BASE 0 // default layer +#define SYMB 1 // symbols +#define MDIA 2 // media keys +#define DEAD 3 // dead version of the symbols layer + +const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { +/* Keymap 0: Basic layer + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | ` | 1 | 2 | 3 | 4 | 5 | LEFT | | RIGHT| 6 | 7 | 8 | 9 | 0 | - | + * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------| + * | Tab | Q | D | R | W | B | L1 | | L1 | J | F | U | P | ; | | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | Hyper | A | S | H | T | G |------| |------| Y | N | E | O | I | ' | + * |--------+------+------+------+------+------| | | Meh |------+------+------+------+------+--------| + * | LShift | Z | X | M | C | V | | | | K | L | , | . |//Ctrl| RShift | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * | | | CTRL | OPT | CMD | | Left | Down | Up | Right| L3 | + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | | | | | | + * ,------|------|------| |------+--------+------. + * | | | Home | | PgUp | | | + * | Space|Backsp|------| |------| Enter |Space | + * | |ace | End | | PgDn | | | + * `--------------------' `----------------------' + */ +// If it accepts an argument (i.e, is a function), it doesn't need KC_. +// Otherwise, it needs KC_* +[BASE] = KEYMAP( // layer 0 : default + // left hand + KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_LEFT, + KC_TAB, KC_Q, KC_D, KC_R, KC_W, KC_B, TG(1), + ALL_T(KC_ESC), KC_A, KC_S, KC_H, KC_T, KC_G, + KC_LSFT, KC_Z, KC_X, KC_M, KC_C, KC_V, KC_NO, + KC_NO, KC_NO, KC_LCTL,KC_LALT,KC_LGUI, + KC_NO, KC_NO, + KC_HOME, + KC_SPC,KC_BSPC,KC_END, + // right hand + KC_RGHT, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS, + TG(1), KC_J, KC_F, KC_U, KC_P, KC_SCLN, KC_BSLS, + KC_Y, KC_N, KC_E, KC_O, KC_I, KC_QUOT, + MEH_T(KC_NO),KC_K, KC_L, KC_COMM,KC_DOT, CTL_T(KC_SLSH), KC_RSFT, + KC_LEFT,KC_DOWN,KC_UP, KC_RGHT, KC_FN4, + KC_NO, KC_NO, + KC_PGUP, + KC_PGDN,KC_ENT, KC_SPC + ), +/* Keymap 1: Symbol Layer + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | | F1 | F2 | F3 | F4 | F5 | | | | F6 | F7 | F8 | F9 | F10 | F11 | + * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------| + * | | % | & | ? | + | @ | | | | $ | _ | [ | ] | ! | F12 | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | / | ( | = | 0 | { |------| |------| } | 1 | * | ) | - | " | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | 6 | 7 | 8 | 9 | | | | | | \ | 2 | 3 | 4 | 5 | | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * | | | | | | | | | | | | + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | | | | | | + * ,------|------|------| |------+------+------. + * | | | | | | | | + * | | |------| |------| | | + * | | | | | | | | + * `--------------------' `--------------------' + */ +// SYMBOLS +[SYMB] = KEYMAP( + // left hand + KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_TRNS, + KC_TRNS, KC_PERC, KC_AMPR, LSFT(KC_SLSH), LSFT(KC_EQL), KC_AT, KC_TRNS, + KC_TRNS, KC_SLSH, KC_LPRN, KC_EQL, KC_0, LSFT(KC_LBRC), + KC_TRNS, KC_6, KC_7, KC_8, KC_9, KC_PIPE, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS,KC_TRNS, + KC_TRNS, + KC_TRNS,KC_TRNS,KC_TRNS, + // right hand + KC_TRNS, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, + KC_TRNS, KC_DLR, KC_UNDERSCORE, KC_LBRC, KC_RBRC, KC_EXLM, KC_F12, + KC_RCBR, KC_1, KC_ASTR, KC_RPRN, KC_MINS, KC_QUOT, + KC_TRNS, KC_SLSH, KC_2, KC_3, KC_4, KC_5, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, + KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS +), +/* Keymap 2: Media and mouse keys + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | | | | | | | | | | | | | | | | + * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------| + * | | | | MsUp | | | | | | | | | | | | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | |MsLeft|MsDown|MsRght| |------| |------| | | | | | Play | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | | | | | | | | | | | Prev | Next | | | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * | | | | Lclk | Rclk | |VolUp |VolDn | Mute | | | + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | | | | | | + * ,------|------|------| |------+------+------. + * | | | | | | |Brwser| + * | | |------| |------| |Back | + * | | | | | | | | + * `--------------------' `--------------------' + */ +// MEDIA AND MOUSE +[MDIA] = KEYMAP( + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_MS_U, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_MS_L, KC_MS_D, KC_MS_R, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_BTN1, KC_BTN2, + KC_TRNS, KC_TRNS, + KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, + // right hand + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_MPLY, + KC_TRNS, KC_TRNS, KC_TRNS, KC_MPRV, KC_MNXT, KC_TRNS, KC_TRNS, + KC_VOLU, KC_VOLD, KC_MUTE, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, + KC_TRNS, + KC_TRNS, KC_TRNS, KC_WBAK +), +/* Keymap 4: Dead Symbol Layer + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | | F1 | F2 | F3 | F4 | F5 | | | | F6 | F7 | F8 | F9 | F10 | F11 | + * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------| + * | | % | & | ? | + | @ | | | | $ | _ | [ | ] | ! | F12 | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | / | ( | = | 0 | { |------| |------| } | 1 | * | ) | - | " | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | 6 | 7 | 8 | 9 | | | | | | \ | 2 | 3 | 4 | 5 | | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * | | | | | | | | | | | | + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | | | | | | + * ,------|------|------| |------+------+------. + * | | | | | | | | + * | | |------| |------| | | + * | | | | | | | | + * `--------------------' `--------------------' + */ +// SYMBOLS +[DEAD] = KEYMAP( + // left hand + KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_TRNS, + KC_TRNS, M(100), M(101), M(102), M(103), M(104), KC_TRNS, + KC_TRNS, M(109), M(110), M(111), M(112), M(113), + KC_TRNS, M(120), M(121), M(122), M(123), M(124), KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS,KC_TRNS, + KC_TRNS, + KC_TRNS,KC_TRNS,KC_TRNS, + // right hand + KC_TRNS, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, + KC_TRNS, M(105), M(106), M(107), M(108), M(130), KC_F12, + M(114), M(115), M(116), M(117), M(118), M(119), + KC_TRNS, M(125), M(126), M(127), M(128), M(129), KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, + KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS +), +}; + +const uint16_t PROGMEM fn_actions[] = { + [1] = ACTION_LAYER_TAP_TOGGLE(SYMB), // FN1 - Momentary Layer 1 (Symbols) + [2] = ACTION_LAYER_ON(BASE,0), // FN2 - Go back to the base layer + [3] = ACTION_LAYER_ON(DEAD,0), + [4] = ACTION_LAYER_TOGGLE(DEAD), +}; + +const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt) +{ + // MACRODOWN only works in this function + switch(id) { + case 0: + if (record->event.pressed) { + register_code(KC_RSFT); + } else { + unregister_code(KC_RSFT); + } + break; + case 100: + layer_clear(); + return MACRODOWN(D(LSFT), T(5), U(LSFT), T(FN4), END); + break; + case 101: + layer_clear(); + return MACRODOWN(D(LSFT), T(7), U(LSFT), T(FN4), END); + break; + case 102: + layer_clear(); + return MACRODOWN(D(LSFT), T(SLSH), U(LSFT), T(FN4), END); + break; + case 103: + layer_clear(); + return MACRODOWN(D(LSFT), T(EQL), U(LSFT), T(FN4), END); + break; + case 104: + layer_clear(); + return MACRODOWN(D(LSFT), T(2), U(LSFT), T(FN4), END); + break; + case 105: + layer_clear(); + return MACRODOWN(D(LSFT), T(4), U(LSFT), T(FN4), END); + break; + case 106: + layer_clear(); + return MACRODOWN(D(LSFT), T(MINS), U(LSFT), T(FN4), END); + break; + case 107: + layer_clear(); + return MACRODOWN(T(LBRC), T(FN4), END); + break; + case 108: + layer_clear(); + return MACRODOWN(T(RBRC), T(FN4), END); + break; + case 130: + layer_clear(); + return MACRODOWN(D(LSFT), T(1), U(LSFT), T(FN4), END); + break; + case 109: + layer_clear(); + return MACRODOWN(T(SLSH), T(FN4), END); + break; + case 110: + layer_clear(); + return MACRODOWN(D(LSFT), T(9), U(LSFT), T(FN4), END); + break; + case 111: + layer_clear(); + return MACRODOWN(T(EQL), T(FN4), END); + break; + case 112: + layer_clear(); + return MACRODOWN(T(0), T(FN4), END); + break; + case 113: + layer_clear(); + return MACRODOWN(D(LSFT), T(LBRC), U(LSFT), T(FN4), END); + break; + case 114: + layer_clear(); + return MACRODOWN(D(LSFT), T(RBRC), U(LSFT), T(FN4), END); + break; + case 115: + layer_clear(); + return MACRODOWN(T(1), T(FN4), END); + break; + case 116: + layer_clear(); + return MACRODOWN(D(LSFT), T(8), U(LSFT), T(FN4), END); + break; + case 117: + layer_clear(); + return MACRODOWN(D(LSFT), T(0), U(LSFT), T(FN4), END); + break; + case 118: + layer_clear(); + return MACRODOWN(T(MINS), T(FN4), END); + break; + case 119: + layer_clear(); + return MACRODOWN(D(LSFT), T(QUOT), U(LSFT), T(FN4), END); + break; + case 120: + layer_clear(); + return MACRODOWN(T(6), T(FN4), END); + break; + case 121: + layer_clear(); + return MACRODOWN(T(7), T(FN4), END); + break; + case 122: + layer_clear(); + return MACRODOWN(T(8), T(FN4), END); + break; + case 123: + layer_clear(); + return MACRODOWN(T(9), T(FN4), END); + break; + case 124: + layer_clear(); + return MACRODOWN(D(LSFT), T(BSLS), U(LSFT), T(FN4), END); + break; + case 125: + layer_clear(); + return MACRODOWN(T(BSLS), T(FN4), END); + break; + case 126: + layer_clear(); + return MACRODOWN(T(2), T(FN4), END); + break; + case 127: + layer_clear(); + return MACRODOWN(T(3), T(FN4), END); + break; + case 128: + layer_clear(); + return MACRODOWN(T(4), T(FN4), END); + break; + case 129: + layer_clear(); + return MACRODOWN(T(5), T(FN4), END); + break; + + default: + return MACRO_NONE; + } + +}; + +// Runs just one time when the keyboard initializes. +void * matrix_init_user(void) { + +}; + +// Runs constantly in the background, in a loop. +void * matrix_scan_user(void) { + + uint8_t layer = biton32(layer_state); + + ergodox_board_led_off(); + ergodox_right_led_1_off(); + ergodox_right_led_2_off(); + ergodox_right_led_3_off(); + switch (layer) { + // TODO: Make this relevant to the ErgoDox EZ. + case 1: + ergodox_right_led_1_on(); + break; + case 2: + ergodox_right_led_2_on(); + break; + default: + // none + break; + } + +}; From 42ca2e6684b7656a5715ccd88d982e6df04eb6d6 Mon Sep 17 00:00:00 2001 From: Technovangelist Date: Mon, 21 Dec 2015 10:20:02 -0500 Subject: [PATCH 07/12] swapped the space and enter to get the space under where the thumb is. --- keyboard/ergodox_ez/keymaps/keymap_workman_osx_mdw.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/keyboard/ergodox_ez/keymaps/keymap_workman_osx_mdw.c b/keyboard/ergodox_ez/keymaps/keymap_workman_osx_mdw.c index d0195faf34..14bbe010d5 100644 --- a/keyboard/ergodox_ez/keymaps/keymap_workman_osx_mdw.c +++ b/keyboard/ergodox_ez/keymaps/keymap_workman_osx_mdw.c @@ -34,8 +34,8 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { * | | | | | | * ,------|------|------| |------+--------+------. * | | | Home | | PgUp | | | - * | Space|Backsp|------| |------| Enter |Space | - * | |ace | End | | PgDn | | | + * |Bckspc| Space|------| |------| Space |Enter | + * | | | End | | PgDn | | | * `--------------------' `----------------------' */ // If it accepts an argument (i.e, is a function), it doesn't need KC_. @@ -49,7 +49,7 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { KC_NO, KC_NO, KC_LCTL,KC_LALT,KC_LGUI, KC_NO, KC_NO, KC_HOME, - KC_SPC,KC_BSPC,KC_END, + KC_BSPC,KC_SPC,KC_END, // right hand KC_RGHT, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS, TG(1), KC_J, KC_F, KC_U, KC_P, KC_SCLN, KC_BSLS, @@ -58,7 +58,7 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { KC_LEFT,KC_DOWN,KC_UP, KC_RGHT, KC_FN4, KC_NO, KC_NO, KC_PGUP, - KC_PGDN,KC_ENT, KC_SPC + KC_PGDN,KC_SPC,KC_ENT ), /* Keymap 1: Symbol Layer * From 58e237d2dc77450b5831701ad2a93de305c044ca Mon Sep 17 00:00:00 2001 From: Erez Zukerman Date: Wed, 23 Dec 2015 15:28:13 +0200 Subject: [PATCH 08/12] Updates readme --- keyboard/ergodox_ez/README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/keyboard/ergodox_ez/README.md b/keyboard/ergodox_ez/README.md index de6b8edf90..8085e5cd87 100644 --- a/keyboard/ergodox_ez/README.md +++ b/keyboard/ergodox_ez/README.md @@ -16,9 +16,9 @@ This requires a little bit of familiarity with coding. 1. Go to https://github.com/jackhumbert/qmk_firmware and read the Readme at the base of this repository, top to bottom. Then come back here :) 2. Clone the repository (download it) 3. Set up a build environment as per https://www.pjrc.com/teensy/gcc.html -4. Copy keymaps/keymap_default.c into keymaps/your_keymap_name.c +4. Copy `keymaps/keymap_default.c` into `keymaps/keymaps_your_name.c` (for example, `keymaps/keymap_german.c`) 5. Edit this file, changing keycodes to your liking (see "Finding the keycodes you need" below). Try to edit the comments as well, so the "text graphics" represent your layout correctly. -6. Compile your firmware by running `make clean` followed by `make KEYMAP=your_keymap_name`. This will result in a hex file. +6. Compile your firmware by running `make clean` followed by `make KEYMAP=your_name`. Note that you must omit the `keymap_` prefix for your filename in this command -- for example, `make KEYMAP=german`. This will result in a hex file, which will always be called `ergodox_ez.hex`, regardless of your keymap name. 6. Flash this hex file using the [Teensy loader](https://www.pjrc.com/teensy/loader.html) as described in step 4 in the "Easy Way" above. 7. Submit your work as a pull request to this repository, so others can also use it. :) From f1dea975d2bcafaebbdbc3a6520b538adb4ce7d7 Mon Sep 17 00:00:00 2001 From: MattLeBeauViewpoint Date: Thu, 31 Dec 2015 10:16:51 -0800 Subject: [PATCH 09/12] Small change to filename spelling in README Edited filename to remove plural case in example so that prefix is correctly parsed in step 6. --- keyboard/ergodox_ez/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/keyboard/ergodox_ez/README.md b/keyboard/ergodox_ez/README.md index 8085e5cd87..27568323b9 100644 --- a/keyboard/ergodox_ez/README.md +++ b/keyboard/ergodox_ez/README.md @@ -16,7 +16,7 @@ This requires a little bit of familiarity with coding. 1. Go to https://github.com/jackhumbert/qmk_firmware and read the Readme at the base of this repository, top to bottom. Then come back here :) 2. Clone the repository (download it) 3. Set up a build environment as per https://www.pjrc.com/teensy/gcc.html -4. Copy `keymaps/keymap_default.c` into `keymaps/keymaps_your_name.c` (for example, `keymaps/keymap_german.c`) +4. Copy `keymaps/keymap_default.c` into `keymaps/keymap_your_name.c` (for example, `keymaps/keymap_german.c`) 5. Edit this file, changing keycodes to your liking (see "Finding the keycodes you need" below). Try to edit the comments as well, so the "text graphics" represent your layout correctly. 6. Compile your firmware by running `make clean` followed by `make KEYMAP=your_name`. Note that you must omit the `keymap_` prefix for your filename in this command -- for example, `make KEYMAP=german`. This will result in a hex file, which will always be called `ergodox_ez.hex`, regardless of your keymap name. 6. Flash this hex file using the [Teensy loader](https://www.pjrc.com/teensy/loader.html) as described in step 4 in the "Easy Way" above. From 1cdcbc9865bd9628f0da4f1f947dd56d100cc327 Mon Sep 17 00:00:00 2001 From: Gabriel Diegel Date: Sat, 2 Jan 2016 10:31:47 +0100 Subject: [PATCH 10/12] Fix incorrect number of rows on fn layer. Add additional navigation keys to fn layer --- keyboard/planck/keymaps/keymap_gabriel.c | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/keyboard/planck/keymaps/keymap_gabriel.c b/keyboard/planck/keymaps/keymap_gabriel.c index b84ecd76c3..805484488b 100644 --- a/keyboard/planck/keymaps/keymap_gabriel.c +++ b/keyboard/planck/keymaps/keymap_gabriel.c @@ -11,7 +11,7 @@ // This a slightly modified 'default' keymap that's closer to the Mac keyboard layout. I like the position // of 'esc' and 'tab' better this way. I also got rid of the backlighting control key and the dvorak and -// colemak layers. I added a 'fn' layer that makes the 'bspc' a forward delete (like on OSX). +// colemak layers. I added an 'fn' layer that makes the 'bspc' a forward delete (like on OSX). const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { /* MIT Layout (QWERTY layer) * @@ -76,15 +76,14 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { * |-----------------------------------------------------------------------| * | | | | | | | | | | | | | * |-----------------------------------------------------------------------| - * | | | | | | | | | | | | + * | | | | | | | |home |pgdn |pgup | end | * `-----------------------------------------------------------------------' */ [_FN] = { /* FUNCTION */ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_DELT}, {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}, {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}, - {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}, - {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS} + {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_HOME, KC_PGDN, KC_PGUP, KC_END} } }; From 7ba06c9e0dbc17cc46794b9961ff9290694d93df Mon Sep 17 00:00:00 2001 From: Dave Jones Date: Sat, 19 Dec 2015 22:18:58 +0000 Subject: [PATCH 11/12] Dave's custom keymap This moves the keys closer to a traditional layout with some redundancy around the middle to compensate for fast non-traditional typists like myself who tend to wander from the home row a fair bit. Navigation keys are provided in layer 2 (accessed by left thumb button), programming symbols and classic numeric keypad in layer 1 (accessed by right thumb button). Permanent layer switching is provided with a smaller thumb button. Ctrl provided in place of caps lock (because no-one needs caps/num lock), space, backspace, enter, shift all in traditional positions with layer 1 providing things like equals, tilde and apostrophe (an attempt to re-use existing muscle memory). LEDs are pimped to the point of being silly (fading in/out on layer switch, rolling on reboot ... because I can). Power and reset keys provided on left thumb pad in layer 2. No meh or hyper as I haven't found a burning need for them yet. --- .gitignore | 1 + keyboard/ergodox_ez/ergodox_ez.c | 35 +++-- keyboard/ergodox_ez/ergodox_ez.h | 9 +- keyboard/ergodox_ez/keymaps/keymap_dave.c | 183 ++++++++++++++++++++++ 4 files changed, 217 insertions(+), 11 deletions(-) create mode 100644 keyboard/ergodox_ez/keymaps/keymap_dave.c diff --git a/.gitignore b/.gitignore index f3f46872a0..bae2658b00 100644 --- a/.gitignore +++ b/.gitignore @@ -7,6 +7,7 @@ *.lst *.map *.sym +*.swp tags *~ build/ diff --git a/keyboard/ergodox_ez/ergodox_ez.c b/keyboard/ergodox_ez/ergodox_ez.c index 78e956a042..d0eaf33923 100644 --- a/keyboard/ergodox_ez/ergodox_ez.c +++ b/keyboard/ergodox_ez/ergodox_ez.c @@ -6,12 +6,12 @@ uint8_t mcp23018_status = 0x20; __attribute__ ((weak)) void * matrix_init_user(void) { - + return NULL; }; __attribute__ ((weak)) void * matrix_scan_user(void) { - + return NULL; }; void * matrix_init_kb(void) { @@ -34,16 +34,20 @@ void * matrix_init_kb(void) { ergodox_blink_all_leds(); - if (matrix_init_user) { - (*matrix_init_user)(); - } + if (matrix_init_user) { + (*matrix_init_user)(); + } + + return NULL; }; void * matrix_scan_kb(void) { - if (matrix_scan_user) { - (*matrix_scan_user)(); - } + if (matrix_scan_user) { + (*matrix_scan_user)(); + } + + return NULL; }; @@ -51,8 +55,19 @@ void ergodox_blink_all_leds(void) { ergodox_led_all_off(); ergodox_led_all_set(LED_BRIGHTNESS_HI); - ergodox_led_all_on(); - _delay_ms(333); + ergodox_right_led_1_on(); + _delay_ms(50); + ergodox_right_led_2_on(); + _delay_ms(50); + ergodox_right_led_3_on(); + _delay_ms(50); + ergodox_right_led_1_off(); + _delay_ms(50); + ergodox_right_led_2_off(); + _delay_ms(50); + ergodox_right_led_3_off(); + //ergodox_led_all_on(); + //_delay_ms(333); ergodox_led_all_off(); } diff --git a/keyboard/ergodox_ez/ergodox_ez.h b/keyboard/ergodox_ez/ergodox_ez.h index 3989a2f3ac..aceb7ed9c3 100644 --- a/keyboard/ergodox_ez/ergodox_ez.h +++ b/keyboard/ergodox_ez/ergodox_ez.h @@ -34,7 +34,7 @@ void ergodox_blink_all_leds(void); uint8_t init_mcp23018(void); uint8_t ergodox_left_leds_update(void); -#define LED_BRIGHTNESS_LO 31 +#define LED_BRIGHTNESS_LO 15 #define LED_BRIGHTNESS_HI 255 @@ -42,11 +42,13 @@ inline void ergodox_board_led_on(void) { DDRD |= (1<<6); PORTD |= (1<<6); inline void ergodox_right_led_1_on(void) { DDRB |= (1<<5); PORTB |= (1<<5); } inline void ergodox_right_led_2_on(void) { DDRB |= (1<<6); PORTB |= (1<<6); } inline void ergodox_right_led_3_on(void) { DDRB |= (1<<7); PORTB |= (1<<7); } +inline void ergodox_right_led_on(uint8_t led) { DDRB |= (1<<(led+4)); PORTB |= (1<<(led+4)); } inline void ergodox_board_led_off(void) { DDRD &= ~(1<<6); PORTD &= ~(1<<6); } inline void ergodox_right_led_1_off(void) { DDRB &= ~(1<<5); PORTB &= ~(1<<5); } inline void ergodox_right_led_2_off(void) { DDRB &= ~(1<<6); PORTB &= ~(1<<6); } inline void ergodox_right_led_3_off(void) { DDRB &= ~(1<<7); PORTB &= ~(1<<7); } +inline void ergodox_right_led_off(uint8_t led) { DDRB &= ~(1<<(led+4)); PORTB &= ~(1<<(led+4)); } inline void ergodox_led_all_on(void) { @@ -67,6 +69,11 @@ inline void ergodox_led_all_off(void) inline void ergodox_right_led_1_set(uint8_t n) { OCR1A = n; } inline void ergodox_right_led_2_set(uint8_t n) { OCR1B = n; } inline void ergodox_right_led_3_set(uint8_t n) { OCR1C = n; } +inline void ergodox_right_led_set(uint8_t led, uint8_t n) { + (led == 1) ? (OCR1A = n) : + (led == 2) ? (OCR1B = n) : + (OCR1C = n); +} inline void ergodox_led_all_set(uint8_t n) { diff --git a/keyboard/ergodox_ez/keymaps/keymap_dave.c b/keyboard/ergodox_ez/keymaps/keymap_dave.c new file mode 100644 index 0000000000..b53aed9222 --- /dev/null +++ b/keyboard/ergodox_ez/keymaps/keymap_dave.c @@ -0,0 +1,183 @@ +#include "ergodox_ez.h" +#include "debug.h" +#include "action_layer.h" + +#define BASE 0 // default layer +#define PROG 1 // symbols +#define NAVI 2 // navigation keys + +const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { +/* Keymap 0: Basic layer + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | Esc | 1 | 2 | 3 | 4 | 5 | 6 | | 6 | 7 | 8 | 9 | 0 | - | BkSpce | + * |--------+------+------+------+------+------+------| |------+------+------+------+------+------+--------| + * | Tab | Q | W | E | R | T | Y | | G | Y | U | I | O | P | Enter | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | LCtrl | A | S | D | F | G |------| |------| H | J | K | L | ; | Enter | + * |--------+------+------+------+------+------| H | | B |------+------+------+------+------+--------| + * | LShift | Z | X | C | V | B | | | | N | M | , | . | / | RShift | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * |`/Ctrl| \ | | | LAlt | | RAlt | | [ | ] |'/Ctrl| + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | PrtS | Apps | | Paus | CtAl | + * ,------+------+------| |------+------+------. + * | | | L1 | | L1 | | | + * | Spce | ~L2 +------| |------+ ~L1 | Spce | + * | | | LGui | | RGui | | | + * `--------------------' `--------------------' + */ +[BASE] = KEYMAP( // layer 0 : default + // left hand + KC_ESC, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, + KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, + KC_LCTRL, KC_A, KC_S, KC_D, KC_F, KC_G, + KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_H, + CTL_T(KC_GRV),KC_NUBS,KC_NO, KC_NO, KC_LALT, + KC_PSCREEN, KC_APP, + TO(PROG, ON_PRESS), + KC_SPC, MO(NAVI), KC_LGUI, + // right hand + KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS, KC_BSPC, + KC_G, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_ENTER, + KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_ENTER, + KC_B, KC_N, KC_M, KC_COMM,KC_DOT, KC_SLSH, KC_RSFT, + KC_RALT,KC_NO, KC_LBRC,KC_RBRC, CTL_T(KC_QUOT), + KC_PAUS, MT(0x5, KC_NO), + TO(PROG, ON_PRESS), + KC_RGUI, MO(PROG), KC_SPC + ), + +/* Keymap 1: Symbol Layer + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | | | | | | | | | | | | K/ | K* | K- | = | + * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------| + * | | ! | @ | ( | ) | | | | | | | K7 | K8 | K9 | K+ | # | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | # | $ | { | } | ` |------| |------| | K4 | K5 | K6 | K+ | ' | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | % | ^ | [ | ] | ~ | | | | | K1 | K2 | K3 | K= | | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * | | | | | | | K0 | K0 | K. | K= | | + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | | | | | | + * ,------|------|------| |------+------+------. + * | | | L2 | | L2 | | | + * | | |------| |------| | | + * | | | | | | | | + * `--------------------' `--------------------' + */ +[PROG] = KEYMAP( + // left hand + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_EXLM, KC_AT, KC_LCBR, KC_RCBR, KC_PIPE, KC_TRNS, + KC_TRNS, KC_HASH, KC_DLR, KC_LPRN, KC_RPRN, KC_GRV, + KC_TRNS, KC_PERC, KC_CIRC, KC_LBRC, KC_RBRC, KC_TILD, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, + TO(NAVI, ON_PRESS), + KC_TRNS, KC_TRNS, KC_TRNS, + // right hand + KC_TRNS, KC_TRNS, KC_NO, KC_PSLS, KC_PAST, KC_PMNS, KC_EQUAL, + KC_TRNS, KC_TRNS, KC_P7, KC_P8, KC_P9, KC_PPLS, KC_NUHS, + KC_TRNS, KC_P4, KC_P5, KC_P6, KC_PPLS, KC_QUOT, + KC_TRNS, KC_TRNS, KC_P1, KC_P2, KC_P3, KC_PENT, KC_TRNS, + KC_P0, KC_P0, KC_PDOT, KC_PENT, KC_TRNS, + KC_TRNS, KC_TRNS, + TO(NAVI, ON_PRESS), + KC_TRNS, KC_TRNS, KC_TRNS +), + +/* Keymap 2: Navigation and system keys + * + * ,--------------------------------------------------. ,--------------------------------------------------. + * | | F1 | F2 | F3 | F4 | F5 | F6 | | F7 | F8 | F9 | F10 | F11 | F12 | | + * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------| + * | | Home | Up | End | Ins | PgUp | | | | | | Ins | | | | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | Left | Down | Rght | Del | PgDn |------| |------| | Back | Del | Fwrd | | | + * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------| + * | | Lclk | MsUp | Rclk | | | | | | | Prev | Play | Next | | | + * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------' + * | | MsLt | MsDn | MsRt | | |VolDn | Mute |VolUp | | | + * `----------------------------------' `----------------------------------' + * ,-------------. ,-------------. + * | Powr | Log | | | | + * ,------|------|------| |------+------+------. + * | | | L0 | | L0 | | | + * | | |------| |------| | | + * | | | | | | | | + * `--------------------' `--------------------' + */ +[NAVI] = KEYMAP( + KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, + KC_TRNS, KC_HOME, KC_UP, KC_END, KC_INS, KC_PGUP, KC_TRNS, + KC_TRNS, KC_LEFT, KC_DOWN, KC_RGHT, KC_DELT, KC_PGDN, + KC_TRNS, KC_BTN1, KC_MS_U, KC_BTN2, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_MS_L, KC_MS_D, KC_MS_R, KC_TRNS, + KC_PWR, LCTL(LALT(KC_DELT)), + TO(BASE, ON_PRESS), + KC_TRNS, KC_TRNS, KC_TRNS, + // right hand + KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, KC_TRNS, + KC_TRNS, KC_TRNS, KC_TRNS, KC_INS, KC_TRNS, KC_TRNS, KC_TRNS, + KC_TRNS, KC_WBAK, KC_DELT, KC_WFWD, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, KC_MPRV, KC_MPLY, KC_MNXT, KC_TRNS, KC_TRNS, + KC_VOLD, KC_MUTE, KC_VOLU, KC_TRNS, KC_TRNS, + KC_TRNS, KC_TRNS, + TO(BASE, ON_PRESS), + KC_TRNS, KC_TRNS, KC_TRNS +), +}; + +const uint16_t PROGMEM fn_actions[] = { + //[1] = ACTION_LAYER_TAP_TOGGLE(PROG), // FN1 - Momentary Layer 1 (Symbols) + //[2] = ACTION_LAYER_TAP_TOGGLE(NAVI) // FN2 - Momentary Layer 2 (Navigation) +}; + +const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt) +{ + // MACRODOWN only works in this function + switch(id) { + case 0: + if (record->event.pressed) { + register_code(KC_RSFT); + } else { + unregister_code(KC_RSFT); + } + break; + } + return MACRO_NONE; +}; + +// Runs just one time when the keyboard initializes. +void * matrix_init_user(void) { + return NULL; +}; + +// Runs constantly in the background, in a loop. +void * matrix_scan_user(void) { + static uint8_t leds[4]; // Yes, I'm wasting a byte. Sue me. + uint8_t led; + uint8_t layer = biton32(layer_state); + + ergodox_board_led_off(); + + for (led = 1; led <= 3; ++led) { + leds[led] += (layer == led) ? + (leds[led] < 255 ? 1 : 0): + (leds[led] > 0 ? -1 : 0); + if (leds[led]) { + ergodox_right_led_on(led); + ergodox_right_led_set(led, leds[led]); + } + else { + ergodox_right_led_off(led); + } + } + + return NULL; +}; From dcc9948fae588daa0649a94ae342a4b13e631eba Mon Sep 17 00:00:00 2001 From: Dave Jones Date: Sat, 2 Jan 2016 18:23:49 +0000 Subject: [PATCH 12/12] Added comments to LED stuff and included .hex file --- keyboard/ergodox_ez/keymaps/keymap_dave.c | 14 +++++++++++++- keyboard/ergodox_ez/keymaps/keymap_dave.hex | Bin 0 -> 66667 bytes 2 files changed, 13 insertions(+), 1 deletion(-) create mode 100644 keyboard/ergodox_ez/keymaps/keymap_dave.hex diff --git a/keyboard/ergodox_ez/keymaps/keymap_dave.c b/keyboard/ergodox_ez/keymaps/keymap_dave.c index b53aed9222..a0c74ad805 100644 --- a/keyboard/ergodox_ez/keymaps/keymap_dave.c +++ b/keyboard/ergodox_ez/keymaps/keymap_dave.c @@ -160,16 +160,28 @@ void * matrix_init_user(void) { // Runs constantly in the background, in a loop. void * matrix_scan_user(void) { - static uint8_t leds[4]; // Yes, I'm wasting a byte. Sue me. + /* leds is a static array holding the current brightness of each of the + * three keyboard LEDs. It's 4 long simply to avoid the ugliness of +1s and + * -1s in the code below, and because wasting a byte really doesn't matter + * that much (no, it *doesn't*, stop whinging!). Note that because it's + * static it'll maintain state across invocations of this routine. + */ + static uint8_t leds[4]; uint8_t led; uint8_t layer = biton32(layer_state); ergodox_board_led_off(); + /* Loop over each LED/layer */ for (led = 1; led <= 3; ++led) { + /* If the current layer matches the current LED, increment its + * brightness by 1 up to a maximum of 255. If the current layer doesn't + * match, decrement its brightness by 1 down to a minimum of zero. + */ leds[led] += (layer == led) ? (leds[led] < 255 ? 1 : 0): (leds[led] > 0 ? -1 : 0); + /* Set LED state according to the new brightness */ if (leds[led]) { ergodox_right_led_on(led); ergodox_right_led_set(led, leds[led]); diff --git a/keyboard/ergodox_ez/keymaps/keymap_dave.hex b/keyboard/ergodox_ez/keymaps/keymap_dave.hex new file mode 100644 index 0000000000000000000000000000000000000000..767a9ca1171e7243060ca15cbeefcd04fe56e74b GIT binary patch literal 66667 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