1
0
Fork 0

Merge remote-tracking branch 'origin/master' into develop

This commit is contained in:
QMK Bot 2021-01-11 09:21:49 +00:00
commit 120c87b630
15 changed files with 1168 additions and 23 deletions

View file

@ -0,0 +1,17 @@
/* Copyright 2020 Vinam Arora <vinam@posteo.de>
*
* 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 "0_sixty.h"

View file

@ -0,0 +1,97 @@
/* Copyright 2020 Vinam Arora <vinam@posteo.de>
*
* 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"
// This a shortcut to help you visually see your layout.
// The first section contains all of the arguements
// The second converts the arguments into a two-dimensional array
#define LAYOUT_ortho_5x12( \
k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b, \
k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b, \
k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b, \
k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b, \
k40, k41, k42, k43, k44, k45, k46, k47, k48, k49, k4a, k4b \
) \
{ \
{ k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b }, \
{ k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b }, \
{ k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b }, \
{ k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b }, \
{ k40, k41, k42, k43, k44, k45, k46, k47, k48, k49, k4a, k4b } \
}
#define LAYOUT_1x2uL( \
k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b, \
k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b, \
k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b, \
k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b, \
k40, k41, k42, k43, k45, k46, k47, k48, k49, k4a, k4b \
) \
{ \
{ k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b }, \
{ k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b }, \
{ k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b }, \
{ k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b }, \
{ k40, k41, k42, k43, k45, k45, k46, k47, k48, k49, k4a, k4b } \
}
#define LAYOUT_1x2uC( \
k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b, \
k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b, \
k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b, \
k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b, \
k40, k41, k42, k43, k44, k46, k47, k48, k49, k4a, k4b \
) \
{ \
{ k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b }, \
{ k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b }, \
{ k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b }, \
{ k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b }, \
{ k40, k41, k42, k43, k44, k46, k46, k47, k48, k49, k4a, k4b } \
}
#define LAYOUT_1x2uR( \
k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b, \
k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b, \
k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b, \
k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b, \
k40, k41, k42, k43, k44, k45, k46, k48, k49, k4a, k4b \
) \
{ \
{ k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b }, \
{ k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b }, \
{ k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b }, \
{ k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b }, \
{ k40, k41, k42, k43, k44, k45, k46, k46, k48, k49, k4a, k4b } \
}
#define LAYOUT_2x2uC( \
k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b, \
k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b, \
k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b, \
k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b, \
k40, k41, k42, k43, k45, k46, k48, k49, k4a, k4b \
) \
{ \
{ k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b }, \
{ k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b }, \
{ k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b }, \
{ k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b }, \
{ k40, k41, k42, k43, k45, k45, k46, k46, k48, k49, k4a, k4b } \
}

View file

@ -0,0 +1,68 @@
/* Copyright 2020 Vinam Arora <vinam@posteo.de>
*
* 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 "config_common.h"
/* USB Device descriptor parameter */
#define VENDOR_ID 0x7654
#define PRODUCT_ID 0x0060
#define DEVICE_VER 0x0001
#define MANUFACTURER ven0mtr0n
#define PRODUCT 0-Sixty
/* key matrix size */
// Rows are doubled-up
#define MATRIX_ROWS 5
#define MATRIX_COLS 12
#define MATRIX_ROW_PINS { B1, F7, F6, F5, F4 }
#define MATRIX_COL_PINS { D3, D2, D1, D0, D4, C6, D7, E6, B4, B5, B3, B2 }
#define UNUSED_PINS
/* COL2ROW or ROW2COL */
#define DIODE_DIRECTION COL2ROW
/* Set 0 if debouncing isn't needed */
#define DEBOUNCE 5
/* indicator leds */
#define LED_CAPS_LOCK_PIN B6
/* Mechanical locking support. Use KC_LCAP, KC_LNUM or KC_LSCR instead in keymap */
#define LOCKING_SUPPORT_ENABLE
/* Locking resynchronize hack */
#define LOCKING_RESYNC_ENABLE
/*
* Feature disable options
* These options are also useful to firmware size reduction.
*/
/* disable debug print */
// #define NO_DEBUG
/* disable print */
// #define NO_PRINT
/* disable action features */
//#define NO_ACTION_LAYER
//#define NO_ACTION_TAPPING
//#define NO_ACTION_ONESHOT
//#define NO_ACTION_MACRO
//#define NO_ACTION_FUNCTION

344
keyboards/0_sixty/info.json Normal file
View file

@ -0,0 +1,344 @@
{
"keyboard_name": "0-Sixty",
"url": "",
"maintainer": "vinamarora8",
"width": 12,
"height": 5,
"layouts": {
"LAYOUT_1x2uC": {
"layout": [
{"x": 0, "y": 0},
{"x": 1, "y": 0},
{"x": 2, "y": 0},
{"x": 3, "y": 0},
{"x": 4, "y": 0},
{"x": 5, "y": 0},
{"x": 6, "y": 0},
{"x": 7, "y": 0},
{"x": 8, "y": 0},
{"x": 9, "y": 0},
{"x": 10, "y": 0},
{"x": 11, "y": 0},
{"x": 0, "y": 1},
{"x": 1, "y": 1},
{"x": 2, "y": 1},
{"x": 3, "y": 1},
{"x": 4, "y": 1},
{"x": 5, "y": 1},
{"x": 6, "y": 1},
{"x": 7, "y": 1},
{"x": 8, "y": 1},
{"x": 9, "y": 1},
{"x": 10, "y": 1},
{"x": 11, "y": 1},
{"x": 0, "y": 2},
{"x": 1, "y": 2},
{"x": 2, "y": 2},
{"x": 3, "y": 2},
{"x": 4, "y": 2},
{"x": 5, "y": 2},
{"x": 6, "y": 2},
{"x": 7, "y": 2},
{"x": 8, "y": 2},
{"x": 9, "y": 2},
{"x": 10, "y": 2},
{"x": 11, "y": 2},
{"x": 0, "y": 3},
{"x": 1, "y": 3},
{"x": 2, "y": 3},
{"x": 3, "y": 3},
{"x": 4, "y": 3},
{"x": 5, "y": 3},
{"x": 6, "y": 3},
{"x": 7, "y": 3},
{"x": 8, "y": 3},
{"x": 9, "y": 3},
{"x": 10, "y": 3},
{"x": 11, "y": 3},
{"x": 0, "y": 4},
{"x": 1, "y": 4},
{"x": 2, "y": 4},
{"x": 3, "y": 4},
{"x": 4, "y": 4},
{"x": 5, "y": 4, "w": 2},
{"x": 7, "y": 4},
{"x": 8, "y": 4},
{"x": 9, "y": 4},
{"x": 10, "y": 4},
{"x": 11, "y": 4}
]
},
"LAYOUT_2x2uC": {
"layout": [
{"x": 0, "y": 0},
{"x": 1, "y": 0},
{"x": 2, "y": 0},
{"x": 3, "y": 0},
{"x": 4, "y": 0},
{"x": 5, "y": 0},
{"x": 6, "y": 0},
{"x": 7, "y": 0},
{"x": 8, "y": 0},
{"x": 9, "y": 0},
{"x": 10, "y": 0},
{"x": 11, "y": 0},
{"x": 0, "y": 1},
{"x": 1, "y": 1},
{"x": 2, "y": 1},
{"x": 3, "y": 1},
{"x": 4, "y": 1},
{"x": 5, "y": 1},
{"x": 6, "y": 1},
{"x": 7, "y": 1},
{"x": 8, "y": 1},
{"x": 9, "y": 1},
{"x": 10, "y": 1},
{"x": 11, "y": 1},
{"x": 0, "y": 2},
{"x": 1, "y": 2},
{"x": 2, "y": 2},
{"x": 3, "y": 2},
{"x": 4, "y": 2},
{"x": 5, "y": 2},
{"x": 6, "y": 2},
{"x": 7, "y": 2},
{"x": 8, "y": 2},
{"x": 9, "y": 2},
{"x": 10, "y": 2},
{"x": 11, "y": 2},
{"x": 0, "y": 3},
{"x": 1, "y": 3},
{"x": 2, "y": 3},
{"x": 3, "y": 3},
{"x": 4, "y": 3},
{"x": 5, "y": 3},
{"x": 6, "y": 3},
{"x": 7, "y": 3},
{"x": 8, "y": 3},
{"x": 9, "y": 3},
{"x": 10, "y": 3},
{"x": 11, "y": 3},
{"x": 0, "y": 4},
{"x": 1, "y": 4},
{"x": 2, "y": 4},
{"x": 3, "y": 4},
{"x": 4, "y": 4, "w": 2},
{"x": 6, "y": 4, "w": 2},
{"x": 8, "y": 4},
{"x": 9, "y": 4},
{"x": 10, "y": 4},
{"x": 11, "y": 4}
]
},
"LAYOUT_ortho_5x12": {
"layout": [
{"x": 0, "y": 0},
{"x": 1, "y": 0},
{"x": 2, "y": 0},
{"x": 3, "y": 0},
{"x": 4, "y": 0},
{"x": 5, "y": 0},
{"x": 6, "y": 0},
{"x": 7, "y": 0},
{"x": 8, "y": 0},
{"x": 9, "y": 0},
{"x": 10, "y": 0},
{"x": 11, "y": 0},
{"x": 0, "y": 1},
{"x": 1, "y": 1},
{"x": 2, "y": 1},
{"x": 3, "y": 1},
{"x": 4, "y": 1},
{"x": 5, "y": 1},
{"x": 6, "y": 1},
{"x": 7, "y": 1},
{"x": 8, "y": 1},
{"x": 9, "y": 1},
{"x": 10, "y": 1},
{"x": 11, "y": 1},
{"x": 0, "y": 2},
{"x": 1, "y": 2},
{"x": 2, "y": 2},
{"x": 3, "y": 2},
{"x": 4, "y": 2},
{"x": 5, "y": 2},
{"x": 6, "y": 2},
{"x": 7, "y": 2},
{"x": 8, "y": 2},
{"x": 9, "y": 2},
{"x": 10, "y": 2},
{"x": 11, "y": 2},
{"x": 0, "y": 3},
{"x": 1, "y": 3},
{"x": 2, "y": 3},
{"x": 3, "y": 3},
{"x": 4, "y": 3},
{"x": 5, "y": 3},
{"x": 6, "y": 3},
{"x": 7, "y": 3},
{"x": 8, "y": 3},
{"x": 9, "y": 3},
{"x": 10, "y": 3},
{"x": 11, "y": 3},
{"x": 0, "y": 4},
{"x": 1, "y": 4},
{"x": 2, "y": 4},
{"x": 3, "y": 4},
{"x": 4, "y": 4},
{"x": 5, "y": 4},
{"x": 6, "y": 4},
{"x": 7, "y": 4},
{"x": 8, "y": 4},
{"x": 9, "y": 4},
{"x": 10, "y": 4},
{"x": 11, "y": 4}
]
},
"LAYOUT_1x2uR": {
"layout": [
{"x": 0, "y": 0},
{"x": 1, "y": 0},
{"x": 2, "y": 0},
{"x": 3, "y": 0},
{"x": 4, "y": 0},
{"x": 5, "y": 0},
{"x": 6, "y": 0},
{"x": 7, "y": 0},
{"x": 8, "y": 0},
{"x": 9, "y": 0},
{"x": 10, "y": 0},
{"x": 11, "y": 0},
{"x": 0, "y": 1},
{"x": 1, "y": 1},
{"x": 2, "y": 1},
{"x": 3, "y": 1},
{"x": 4, "y": 1},
{"x": 5, "y": 1},
{"x": 6, "y": 1},
{"x": 7, "y": 1},
{"x": 8, "y": 1},
{"x": 9, "y": 1},
{"x": 10, "y": 1},
{"x": 11, "y": 1},
{"x": 0, "y": 2},
{"x": 1, "y": 2},
{"x": 2, "y": 2},
{"x": 3, "y": 2},
{"x": 4, "y": 2},
{"x": 5, "y": 2},
{"x": 6, "y": 2},
{"x": 7, "y": 2},
{"x": 8, "y": 2},
{"x": 9, "y": 2},
{"x": 10, "y": 2},
{"x": 11, "y": 2},
{"x": 0, "y": 3},
{"x": 1, "y": 3},
{"x": 2, "y": 3},
{"x": 3, "y": 3},
{"x": 4, "y": 3},
{"x": 5, "y": 3},
{"x": 6, "y": 3},
{"x": 7, "y": 3},
{"x": 8, "y": 3},
{"x": 9, "y": 3},
{"x": 10, "y": 3},
{"x": 11, "y": 3},
{"x": 0, "y": 4},
{"x": 1, "y": 4},
{"x": 2, "y": 4},
{"x": 3, "y": 4},
{"x": 4, "y": 4},
{"x": 5, "y": 4},
{"x": 6, "y": 4, "w": 2},
{"x": 8, "y": 4},
{"x": 9, "y": 4},
{"x": 10, "y": 4},
{"x": 11, "y": 4}
]
},
"LAYOUT_1x2uL": {
"layout": [
{"x": 0, "y": 0},
{"x": 1, "y": 0},
{"x": 2, "y": 0},
{"x": 3, "y": 0},
{"x": 4, "y": 0},
{"x": 5, "y": 0},
{"x": 6, "y": 0},
{"x": 7, "y": 0},
{"x": 8, "y": 0},
{"x": 9, "y": 0},
{"x": 10, "y": 0},
{"x": 11, "y": 0},
{"x": 0, "y": 1},
{"x": 1, "y": 1},
{"x": 2, "y": 1},
{"x": 3, "y": 1},
{"x": 4, "y": 1},
{"x": 5, "y": 1},
{"x": 6, "y": 1},
{"x": 7, "y": 1},
{"x": 8, "y": 1},
{"x": 9, "y": 1},
{"x": 10, "y": 1},
{"x": 11, "y": 1},
{"x": 0, "y": 2},
{"x": 1, "y": 2},
{"x": 2, "y": 2},
{"x": 3, "y": 2},
{"x": 4, "y": 2},
{"x": 5, "y": 2},
{"x": 6, "y": 2},
{"x": 7, "y": 2},
{"x": 8, "y": 2},
{"x": 9, "y": 2},
{"x": 10, "y": 2},
{"x": 11, "y": 2},
{"x": 0, "y": 3},
{"x": 1, "y": 3},
{"x": 2, "y": 3},
{"x": 3, "y": 3},
{"x": 4, "y": 3},
{"x": 5, "y": 3},
{"x": 6, "y": 3},
{"x": 7, "y": 3},
{"x": 8, "y": 3},
{"x": 9, "y": 3},
{"x": 10, "y": 3},
{"x": 11, "y": 3},
{"x": 0, "y": 4},
{"x": 1, "y": 4},
{"x": 2, "y": 4},
{"x": 3, "y": 4},
{"x": 4, "y": 4, "w": 2},
{"x": 6, "y": 4},
{"x": 7, "y": 4},
{"x": 8, "y": 4},
{"x": 9, "y": 4},
{"x": 10, "y": 4},
{"x": 11, "y": 4}
]
}
}
}

View file

@ -0,0 +1,168 @@
/* Copyright 2020 Vinam Arora <vinam@posteo.de>
*
* 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 QMK_KEYBOARD_H
enum zero_sixty_layers {
_QWERTY,
_COLEMAK,
_DVORAK,
_LOWER,
_RAISE,
_ADJUST
};
#define QWERTY DF(_QWERTY)
#define COLEMAK DF(_COLEMAK)
#define DVORAK DF(_DVORAK)
#define LOWER MO(_LOWER)
#define RAISE MO(_RAISE)
#define ADJUST MO(_ADJUST)
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
/* Qwerty
* ,-----------------------------------------------------------------------------------.
* | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | Bksp |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | Tab | Q | W | E | R | T | Y | U | I | O | P | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | Esc | A | S | D | F | G | H | J | K | L | ; | " |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | Shift| Z | X | C | V | B | N | M | , | . | / |Enter |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | Caps | Ctrl | Alt | GUI |Lower | Space |Raise | Left | Down | Up |Right |
* `-----------------------------------------------------------------------------------'
*/
[_QWERTY] = LAYOUT_ortho_5x12(
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_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_DEL,
KC_ESC, 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,
KC_CAPS, KC_LCTL, KC_LALT, KC_LGUI, LOWER, KC_SPC, KC_SPC, RAISE, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT
),
/* Colemak
* ,-----------------------------------------------------------------------------------.
* | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | Bksp |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | Tab | Q | W | F | P | G | J | L | U | Y | ; | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | Esc | A | R | S | T | D | H | N | E | I | O | " |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | Shift| Z | X | C | V | B | K | M | , | . | / |Enter |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | Caps | Ctrl | Alt | GUI |Lower | Space |Raise | Left | Down | Up |Right |
* `-----------------------------------------------------------------------------------'
*/
[_COLEMAK] = LAYOUT_ortho_5x12(
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_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_DEL,
KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT,
KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT,
KC_CAPS, KC_LCTL, KC_LALT, KC_LGUI, LOWER, KC_SPC, KC_SPC, RAISE, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT
),
/* Dvorak
* ,-----------------------------------------------------------------------------------.
* | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | Bksp |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | Tab | " | , | . | P | Y | F | G | C | R | L | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | Esc | A | O | E | U | I | D | H | T | N | S | / |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | Shift| ; | Q | J | K | X | B | M | W | V | Z |Enter |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | Caps | Ctrl | Alt | GUI |Lower | Space |Raise | Left | Down | Up |Right |
* `-----------------------------------------------------------------------------------'
*/
[_DVORAK] = LAYOUT_ortho_5x12(
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_TAB, KC_QUOT, KC_COMM, KC_DOT, KC_P, KC_Y, KC_F, KC_G, KC_C, KC_R, KC_L, KC_DEL,
KC_ESC, KC_A, KC_O, KC_E, KC_U, KC_I, KC_D, KC_H, KC_T, KC_N, KC_S, KC_SLSH,
KC_LSFT, KC_SCLN, KC_Q, KC_J, KC_K, KC_X, KC_B, KC_M, KC_W, KC_V, KC_Z, KC_ENT,
KC_CAPS, KC_LCTL, KC_LALT, KC_LGUI, LOWER, KC_SPC, KC_SPC, RAISE, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT
),
/* Lower
* ,-----------------------------------------------------------------------------------.
* | ~ | ! | @ | # | $ | % | ^ | & | * | ( | ) | Bksp |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | ~ | ! | @ | # | $ | % | ^ | & | * | ( | ) | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | Del | F1 | F2 | F3 | F4 | F5 | F6 | _ | + | { | } | | |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | | F7 | F8 | F9 | F10 | F11 | F12 |ISO ~ |ISO | | | | |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | | | | | | | | Next | Vol- | Vol+ | Play |
* `-----------------------------------------------------------------------------------'
*/
[_LOWER] = LAYOUT_ortho_5x12(
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_TILD, KC_EXLM, KC_AT, KC_HASH, KC_DLR, KC_PERC, KC_CIRC, KC_AMPR, KC_ASTR, KC_LPRN, KC_RPRN, KC_DEL,
KC_DEL, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_UNDS, KC_PLUS, KC_LCBR, KC_RCBR, KC_PIPE,
_______, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12,S(KC_NUHS),S(KC_NUBS),KC_HOME, KC_END, _______,
_______, _______, _______, _______, _______, _______, _______, _______, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY
),
/* Raise
* ,-----------------------------------------------------------------------------------.
* | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | Bksp |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | Del | F1 | F2 | F3 | F4 | F5 | F6 | - | = | [ | ] | \ |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | | F7 | F8 | F9 | F10 | F11 | F12 |ISO # |ISO / | | | |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | | | | | | | | Next | Vol- | Vol+ | Play |
* `-----------------------------------------------------------------------------------'
*/
[_RAISE] = LAYOUT_ortho_5x12(
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_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_DEL,
KC_DEL, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS,
_______, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, KC_NUHS, KC_NUBS, KC_PGUP, KC_PGDN, _______,
_______, _______, _______, _______, _______, _______, _______, _______, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY
),
/* Adjust
* ,-----------------------------------------------------------------------------------.
* | F1 | F2 | F3 | F4 | F5 | F6 | F7 | F8 | F9 | F10 | F11 | F12 |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | | Reset| | | | | | | | | | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | | | | | | | |Qwerty|Colemk|Dvorak| | |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | | | | | | | | | | | | |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | | | | | | | | | | | |
* `-----------------------------------------------------------------------------------'
*/
[_ADJUST] = LAYOUT_ortho_5x12(
KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12,
_______, RESET, _______, _______, _______, _______, _______, _______, _______, _______, _______, KC_DEL,
_______, _______, _______, _______, _______, _______, _______, QWERTY, COLEMAK, DVORAK, _______, _______,
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______,
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______
)
};
layer_state_t layer_state_set_user(layer_state_t state) {
return update_tri_layer_state(state, _LOWER, _RAISE, _ADJUST);
}

View file

@ -0,0 +1 @@
# The default 0-Sixty layout - largely based on the Preonic's and Planck's

View file

@ -0,0 +1,59 @@
/* Copyright 2020 Vinam Arora <vinam@posteo.de>
*
* 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 QMK_KEYBOARD_H
enum zero_sixty_layers {
_DEFAULT,
_L1,
_L2,
_L3,
};
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
[_DEFAULT] = LAYOUT_1x2uC( /* qwerty */
KC_ESC, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC ,
KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_ENT ,
KC_LCTL, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_RCTL ,
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_LGUI, MO(_L3), MO(_L2), KC_LALT, MO(_L1), KC_SPC, MO(_L1), KC_RALT, MO(_L2), MO(_L3), KC_RGUI
),
[_L1] = LAYOUT_1x2uC(
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______ ,
_______, KC_LBRC, KC_LT, KC_GT, KC_RBRC, KC_TILD, KC_PIPE, KC_GRV, KC_QUOT, KC_DQUO, KC_PGUP, _______ ,
_______, KC_LCBR, KC_LPRN, KC_RPRN, KC_RCBR, KC_DEL, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT, KC_PGDN, _______ ,
_______, KC_APP, _______, _______, _______, _______, KC_EQL, KC_UNDS, KC_MINS, KC_PLUS, KC_BSLS, _______ ,
_______, _______, _______, _______, _______, KC_CAPS, _______, _______, _______, _______, _______
),
[_L2] = LAYOUT_1x2uC(
_______, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, _______ ,
_______, _______, _______, _______, _______, KC_VOLU, _______, KC_7, KC_8, KC_9, KC_F11, _______ ,
_______, _______, _______, _______, KC_MPRV, KC_MPLY, KC_MNXT, KC_4, KC_5, KC_6, KC_F12, _______ ,
_______, _______, _______, _______, KC_MUTE, KC_VOLD, KC_MUTE, KC_1, KC_2, KC_3, KC_PSCR, _______ ,
_______, _______, KC_CAPS, _______, _______, _______, KC_0, _______, KC_CAPS, _______, _______
),
[_L3] = LAYOUT_1x2uC(
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______ ,
_______, _______, _______, _______, _______, _______, _______, KC_WH_U, KC_MS_U, KC_WH_D, _______, _______ ,
_______, _______, KC_ACL2, KC_ACL1, KC_ACL0, _______, _______, KC_MS_L, KC_MS_D, KC_MS_R, _______, _______ ,
_______, _______, _______, _______, _______, _______, _______, KC_BTN1, KC_BTN3, KC_BTN2, _______, _______ ,
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______
),
};

View file

@ -0,0 +1 @@
# Keymap used by vinam. Keeps changing ofcourse :3

View file

@ -0,0 +1 @@
MOUSEKEY_ENABLE = yes

View file

@ -0,0 +1,116 @@
/* Copyright 2020 Vinam Arora <vinam@posteo.de>
*
* 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 QMK_KEYBOARD_H
// 4 layers, because that is what VIA can support by default
enum zero_sixty_layers {
_QWERTY,
_LOWER,
_RAISE,
_ADJUST,
};
#define LOWER MO(_LOWER)
#define RAISE MO(_RAISE)
#define ADJUST MO(_ADJUST)
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
/* Qwerty
* ,-----------------------------------------------------------------------------------.
* | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | Bksp |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | Tab | Q | W | E | R | T | Y | U | I | O | P | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | Esc | A | S | D | F | G | H | J | K | L | ; | " |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | Shift| Z | X | C | V | B | N | M | , | . | / |Enter |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | Caps | Ctrl | Alt | GUI |Lower | Space |Raise | Left | Down | Up |Right |
* `-----------------------------------------------------------------------------------'
*/
[_QWERTY] = LAYOUT_ortho_5x12(
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_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_DEL,
KC_ESC, 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,
KC_CAPS, KC_LCTL, KC_LALT, KC_LGUI, LOWER, KC_SPC, KC_SPC, RAISE, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT
),
/* Lower
* ,-----------------------------------------------------------------------------------.
* | ~ | ! | @ | # | $ | % | ^ | & | * | ( | ) | Bksp |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | ~ | ! | @ | # | $ | % | ^ | & | * | ( | ) | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | Del | F1 | F2 | F3 | F4 | F5 | F6 | _ | + | { | } | | |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | | F7 | F8 | F9 | F10 | F11 | F12 |ISO ~ |ISO | | | | |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | | | | | | | | Next | Vol- | Vol+ | Play |
* `-----------------------------------------------------------------------------------'
*/
[_LOWER] = LAYOUT_ortho_5x12(
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_TILD, KC_EXLM, KC_AT, KC_HASH, KC_DLR, KC_PERC, KC_CIRC, KC_AMPR, KC_ASTR, KC_LPRN, KC_RPRN, KC_DEL,
KC_DEL, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_UNDS, KC_PLUS, KC_LCBR, KC_RCBR, KC_PIPE,
_______, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12,S(KC_NUHS),S(KC_NUBS),KC_HOME, KC_END, _______,
_______, _______, _______, _______, _______, _______, _______, ADJUST, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY
),
/* Raise
* ,-----------------------------------------------------------------------------------.
* | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | Bksp |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | ` | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 0 | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | Del | F1 | F2 | F3 | F4 | F5 | F6 | - | = | [ | ] | \ |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | | F7 | F8 | F9 | F10 | F11 | F12 |ISO # |ISO / | | | |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | | | | | | | | Next | Vol- | Vol+ | Play |
* `-----------------------------------------------------------------------------------'
*/
[_RAISE] = LAYOUT_ortho_5x12(
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_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_DEL,
KC_DEL, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS,
_______, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, KC_NUHS, KC_NUBS, KC_PGUP, KC_PGDN, _______,
_______, _______, _______, _______, ADJUST, _______, _______, _______, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY
),
/* Adjust
* ,-----------------------------------------------------------------------------------.
* | F1 | F2 | F3 | F4 | F5 | F6 | F7 | F8 | F9 | F10 | F11 | F12 |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | | Reset| | | | | | | | | | Del |
* |------+------+------+------+------+-------------+------+------+------+------+------|
* | | | | | | | | | | | | |
* |------+------+------+------+------+------|------+------+------+------+------+------|
* | | | | | | | | | | | | |
* |------+------+------+------+------+------+------+------+------+------+------+------|
* | | | | | | | | | | | |
* `-----------------------------------------------------------------------------------'
*/
[_ADJUST] = LAYOUT_ortho_5x12(
KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12,
_______, RESET, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______,
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______,
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______,
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______
),
};

View file

@ -0,0 +1 @@
# The default via-supported 0-Sixty layout - largely based on the Preonic's and Planck's

View file

@ -0,0 +1,2 @@
VIA_ENABLE = yes
MOUSEKEY_ENABLE = yes

View file

@ -0,0 +1,27 @@
# 0-Sixty
![0-Sixty](https://imgur.com/azmMb6Rl.jpg)
![0-Sixty PCB](https://i.imgur.com/I0TkQ0Rl.jpg)
0-Sixty (pronounced "zero to sixty") is a 60 key ortholinear keyboard inspired by the [Discipline](https://github.com/coseyfannitutti/discipline) and the [Preonic](https://drop.com/buy/preonic-mechanical-keyboard). It is designed as a DIY through-hole kit and uses the ProMicro as its controller.
[More images here](https://imgur.com/a/b0JINqX)
* Keyboard Maintainer: [vinamarora8](https://github.com/vinamarora8)
* Hardware Supported: 0-Sixty PCB
* Hardware Availability: Private Group-Buy
Getting the board into bootloader mode:
To be able to flash firmware onto this board, you'll need to bring the ProMicro into bootloader mode. Simply tap the small reset button twice. The button is placed to the right of the ProMicro.
Make example for this keyboard (after setting up your build environment):
make 0_sixty:default
Flashing example for this keyboard:
make 0_sixty:default:flash
See the [build environment setup](https://docs.qmk.fm/#/getting_started_build_tools) and the [make instructions](https://docs.qmk.fm/#/getting_started_make_guide) for more information. Brand new to QMK? Start with our [Complete Newbs Guide](https://docs.qmk.fm/#/newbs).

View file

@ -0,0 +1,21 @@
# MCU name
MCU = atmega32u4
# Bootloader selection
BOOTLOADER = caterina
# Build Options
# change yes to no to disable
#
BOOTMAGIC_ENABLE = no # Virtual DIP switch configuration
EXTRAKEY_ENABLE = yes # Audio control and System control
CONSOLE_ENABLE = yes # Console for debug
COMMAND_ENABLE = yes # Commands for debug and configuration
# Do not enable SLEEP_LED_ENABLE. it uses the same timer as BACKLIGHT_ENABLE
SLEEP_LED_ENABLE = no # Breathing sleep LED during USB suspend
# if this doesn't work, see here: https://github.com/tmk/tmk_keyboard/wiki/FAQ#nkro-doesnt-work
NKRO_ENABLE = yes # USB Nkey Rollover
BACKLIGHT_ENABLE = no # Enable keyboard backlight functionality
RGBLIGHT_ENABLE = no # Enable keyboard RGB underglow
BLUETOOTH_ENABLE = no # Enable Bluetooth
AUDIO_ENABLE = no # Audio output

View file

@ -14,6 +14,83 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>. * along with this program. If not, see <http://www.gnu.org/licenses/>.
*/ */
#include QMK_KEYBOARD_H #include QMK_KEYBOARD_H
#include <assert.h>
// This keymap is designed to make it easy to type in a wide variety of languages, as well as
// generate mathematical symbols (à la Space Cadet).
//
// LAYER MAGIC (aka, typing in many alphabets)
// This keyboard has three "base" layers: QWERTY, GREEK, and CADET. The GREEK and CADET layers
// are actually full of Unicode points, and so which point they generate depends on things like
// whether the shift key is down. To handle this, each of those layers is actually *two* layers, one
// with and one without shift. In our main loop, we manage modifier state detection, as well as
// layer switch detection, and pick the right layer on the fly.
// Layers are selected with a combination of three keys. The "Greek" and "Cadet" keys act like
// modifiers: When held down, they transiently select the indicated base layer. The "Layer Lock" key
// locks the value of the base layer at whatever is currently held; so e.g., if you hold Greek +
// Layer Lock, you'll stay in Greek mode until you hit Layer Lock again without any of the mods
// held.
// TODO: This system of layer selection is nice for math, but it's not very nice for actually
// typing in multiple languages. It seems like a better plan will be to reserve one key for each
// base layer -- maybe fn + F(n) -- which can either be held as a modifier or tapped to switch
// layers. That will open up adding some more languages, like Yiddish, but to do this effectively
// we'll need to find a good UI with which to show the currently selected layer. Need to check what
// the melody96 has in the way of outputs (LEDs, sound, etc).
//
// ACCENT MAGIC (aka, typing conveniently in Romance languages)
// We want to support easy typing of diacritical marks. We can't rely on the host OS for this,
// because (e.g.) on MacOS, to make any of the other stuff work, we need to be using the Unicode
// input method at the OS level, which breaks all the normal accent stuff on that end. So we do it
// ourselves. Accents can actually be invoked in two different ways: one fast and very compatible,
// one very versatile but with occasional compatibility problems.
//
// THE MAIN WAY: You can hit one of the "accent request" key patterns immediately *before* typing
// a letter to be accented. It will emit the corresponding accented Unicode. For example, you can
// hit fn-e to request an acute accent, followed by i, and it will output í, U+00ED LATIN SMALL
// LETTER I WITH ACUTE. These "combined characters" are in Unicode normal form C (NFKC), which is
// important because many European websites and apps, in particular, tend to behave very badly
// (misunderstanding and/or crashing) when presented with characters in other forms! The catch is
// that this only works for the various combinations of letters and accents found in the Latin-1
// supplement block of Unicode -- basically, things you need for Western European languages.
//
// (NB: If you make an accent request followed by a letter which can't take the corresponding
// accent, it will output the uncombined form of the accent followed by whatever you typed; so
// e.g., if you hit fn-e followed by f, it will output ´f, U+00B4 ACUTE ACCENT followed by an
// ordinary f. This is very similar to the default behavior of MacOS.)
//
// THE FLEXIBLE WAY: If you hit the accent request with a shift -- e.g., fn-shift-e -- it will
// instead immediately output the corresponding *combining* Unicode accent mark, which will modify
// the *previous* character you typed. For example, if you type i followed by fn-shift-e, it will
// generate í. But don't be fooled by visual similarity: unlike the previous example, this one is
// an ordinary i followed by U+0301 COMBINING ACUTE ACCENT. It's actually *two symbols*, and this
// is Unicode normal form D (NFKD). Unlike NFKC, there are NFKD representations of far more
// combinations of letters and accents, and it's easy to add more of these if you need. (The NFKC
// representation of such combinations is identical to their NFKD representation)
//
// Programs that try to compare Unicode strings *should* first normalize them by converting them
// all into one normal form or another, and there are functions in every programming language to
// do this -- e.g., JavaScript's string.normalize() -- but lots of programmers fail to understand
// this, and so write code that massively freaks out when it encounters the wrong form.
//
// The current accent request codes are modeled on the ones in MacOS.
//
// fn+` Grave accent (`)
// fn+e Acute accent (´)
// fn+i Circumflex (^)
// fn+u Diaresis / umlaut / trema (¨)
// fn+c Cedilla (¸)
// fn+n Tilde (˜)
//
// Together, these functions make for a nice "polyglot" keyboard: one that can easily type in a wide
// variety of languages, which is very useful for people who, well, need to type in a bunch of
// languages.
//
// The major TODOs are:
// - Update the layer selection logic (and add visible layer cues);
// - Factor the code below so that the data layers are more clearly separated from the code logic,
// so that other users of this keymap can easily add whichever alphabets they need without
// having to deeply understand the implementation.
enum custom_keycodes { enum custom_keycodes {
// We provide special layer management keys: // We provide special layer management keys:
@ -32,6 +109,16 @@ enum custom_keycodes {
KC_GREEK = SAFE_RANGE, KC_GREEK = SAFE_RANGE,
KC_CADET, KC_CADET,
KC_LAYER_LOCK, KC_LAYER_LOCK,
// These are the keycodes generated by the various "accent request" keystrokes.
KC_ACCENT_START,
KC_CGRV = KC_ACCENT_START, // Grave accent
KC_CAGU, // Acute accent
KC_CDIA, // Diaresis / umlaut / trema
KC_CCIR, // Circumflex
KC_CCED, // Cedilla
KC_CTIL, // Tilde
KC_ACCENT_END,
}; };
enum layers_keymap { enum layers_keymap {
@ -49,21 +136,6 @@ enum layers_keymap {
#define MO_FN MO(_FUNCTION) #define MO_FN MO(_FUNCTION)
#define KC_LLCK KC_LAYER_LOCK #define KC_LLCK KC_LAYER_LOCK
// TODO: To generalize this, we want some #defines that let us specify how each key on the base
// layer should map to the four special layers, and then use that plus the base layer definition to
// autogenerate the keymaps for the other layers.
// TODO: It would also be nice to be able to put the actual code points in here, rather than
// numbers.
// Accent marks
#define CMB_GRV H(0300)
#define CMB_AGU H(0301)
#define CMB_DIA H(0308)
#define CMB_CIR H(0302)
#define CMB_MAC H(0304)
#define CMB_CED H(0327)
#define CMB_TIL H(0303)
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
// NB: Using GESC for escape in the QWERTY layer as a temporary hack because I messed up the // NB: Using GESC for escape in the QWERTY layer as a temporary hack because I messed up the
@ -164,14 +236,119 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
// Function layer is mostly for keyboard meta-control operations, but also contains the combining // Function layer is mostly for keyboard meta-control operations, but also contains the combining
// accent marks. These are deliberately placed to match where the analogous controls go on Mac OS. // accent marks. These are deliberately placed to match where the analogous controls go on Mac OS.
[_FUNCTION] = LAYOUT_hotswap( [_FUNCTION] = LAYOUT_hotswap(
CMB_GRV, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, KC_MUTE, KC_VOLD, KC_VOLU, _______, _______, RESET, KC_CGRV, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, KC_MUTE, KC_VOLD, KC_VOLU, _______, _______, RESET,
CMB_GRV, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, KC_CGRV, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______,
_______, _______, _______, CMB_AGU, _______, _______, _______, CMB_DIA, CMB_CIR, CMB_MAC, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, KC_CAGU, _______, _______, _______, KC_CDIA, KC_CCIR, _______, _______, _______, _______, _______, _______, _______, _______,
_______, _______, _______, UC_M_OS, UC_M_LN, UC_M_WI, UC_M_BS, UC_M_WC, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, UC_M_OS, UC_M_LN, UC_M_WI, UC_M_BS, UC_M_WC, _______, _______, _______, _______, _______, _______, _______, _______, _______,
_______, _______, _______, CMB_CED, _______, _______, CMB_TIL, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, KC_CCED, _______, _______, KC_CTIL, _______, _______, _______, _______, _______, _______, _______, _______, _______,
_______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______), _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______, _______),
}; };
////////////////////////////////////////////////////////////////////////////////////////////////////
// Accent implementation
//
// In the body of process_record_user, we store an "accent_request", which is the accent keycode if
// one was just selected, or zero otherwise. When the *next* key is hit, we look up whether the
// accent request plus that next keycode (plus the state of the shift key) together amount to an
// interesting combined (NFKC) character, and if so, emit it; otherwise, we emit the accent as a
// separate character and then process the next key normally. The resulting UI behavior is similar
// to that of the combining accent keys in MacOS.
//
// We store two arrays, depending on whether shift is or isn't held. Each is two-dimensional, with
// its outer key by the next keycode struck, and the inner key by the accent requested. The outer
// array has KC_Z + 1 as its upper bound, so that we can save memory by only coding alphabetic keys.
// The contents are either Unicode code points, or zero to indicate that we don't have a point for
// this combination.
#define KC_NUM_ACCENTS (KC_ACCENT_END - KC_ACCENT_START)
#define KC_NUM_SLOTS (KC_Z + 1)
const uint16_t PROGMEM unshifted_accents[KC_NUM_SLOTS][KC_NUM_ACCENTS] = {
// KC_CGRV, KC_CAGU, KC_CDIA, KC_CCIR, KC_CCED, KC_CTIL
[KC_A] = { 0x00e0, 0x00e1, 0x00e4, 0x00e2, 0, 0x00e3 },
[KC_E] = { 0x00e8, 0x00e9, 0x00eb, 0x00ea, 0, 0 },
[KC_I] = { 0x00ec, 0x00ed, 0x00ef, 0x00ee, 0, 0 },
[KC_O] = { 0x00f2, 0x00f3, 0x00f6, 0x00f4, 0, 0x00f5 },
[KC_U] = { 0x00f9, 0x00fa, 0x00fc, 0x00fb, 0, 0 },
[KC_Y] = { 0, 0, 0x00ff, 0, 0, 0 },
[KC_N] = { 0, 0, 0, 0, 0, 0x00f1 },
[KC_C] = { 0, 0, 0, 0, 0x00e7, 0 },
};
const uint16_t PROGMEM shifted_accents[KC_NUM_SLOTS][KC_NUM_ACCENTS] = {
// KC_CGRV, KC_CAGU, KC_CDIA, KC_CCIR, KC_CCED, KC_CTIL
[KC_A] = { 0x00c0, 0x00c1, 0x00c4, 0x00c2, 0, 0x00c3 },
[KC_E] = { 0x00c8, 0x00c9, 0x00cb, 0x00ca, 0, 0 },
[KC_I] = { 0x00cc, 0x00cd, 0x00cf, 0x00ce, 0, 0 },
[KC_O] = { 0x00d2, 0x00d3, 0x00d6, 0x00d4, 0, 0x00d5 },
[KC_U] = { 0x00d9, 0x00da, 0x00dc, 0x00db, 0, 0 },
[KC_Y] = { 0, 0, 0x00df, 0, 0, 0 },
[KC_N] = { 0, 0, 0, 0, 0, 0x00d1 },
[KC_C] = { 0, 0, 0, 0, 0x00c7, 0 },
};
// The uncombined and combined forms of the accents, for when we want to emit them as single
// characters.
const uint16_t PROGMEM uncombined_accents[KC_NUM_ACCENTS] = {
[KC_CGRV - KC_ACCENT_START] = 0x0060,
[KC_CAGU - KC_ACCENT_START] = 0x00b4,
[KC_CDIA - KC_ACCENT_START] = 0x00a8,
[KC_CCIR - KC_ACCENT_START] = 0x005e,
[KC_CCED - KC_ACCENT_START] = 0x00b8,
[KC_CTIL - KC_ACCENT_START] = 0x02dc,
};
const uint16_t PROGMEM combined_accents[KC_NUM_ACCENTS] = {
[KC_CGRV - KC_ACCENT_START] = 0x0300,
[KC_CAGU - KC_ACCENT_START] = 0x0301,
[KC_CDIA - KC_ACCENT_START] = 0x0308,
[KC_CCIR - KC_ACCENT_START] = 0x0302,
[KC_CCED - KC_ACCENT_START] = 0x0327,
[KC_CTIL - KC_ACCENT_START] = 0x0303,
};
// This function manages keypresses that happen after an accent has been selected by an earlier
// keypress.
// Args:
// accent_key: The accent key which was earlier selected. This must be in the range
// [KC_ACCENT_START, KC_ACCENT_END).
// keycode: The keycode which was just pressed.
// is_shifted: The current shift state (as set by a combination of shift and caps lock)
// force_no_accent: If true, we're in a situation where we want to force there to be no
// accent combination -- if e.g. we're in a non-QWERTY layer, or if other modifier keys
// are held.
//
// Returns true if the keycode has been completely handled by this function (and so should not be
// processed further by process_record_user) or false otherwise.
bool process_key_after_accent(
uint16_t accent_key,
uint16_t keycode,
bool is_shifted,
bool force_no_accent
) {
assert(accent_key >= KC_ACCENT_START);
assert(accent_key < KC_ACCENT_END);
const int accent_index = accent_key - KC_ACCENT_START;
// If the keycode is outside A..Z, or force_no_accent is set, we know we shouldn't even bother
// with a table lookup.
if (keycode <= KC_Z && !force_no_accent) {
// Pick the correct array. Because this is progmem, we're going to need to do the
// two-dimensional array indexing by hand, and so we just cast it to a single-dimensional array.
const uint16_t *points = (const uint16_t*)(is_shifted ? shifted_accents : unshifted_accents);
const uint16_t code_point = pgm_read_word_near(points + KC_NUM_ACCENTS * keycode + accent_index);
if (code_point) {
register_unicode(code_point);
return true;
}
}
// If we get here, there was no accent match. Emit the accent as its own character, and then let
// the caller figure out what to do next.
register_unicode(pgm_read_word_near(uncombined_accents + accent_index));
return false;
}
// Layer bitfields. // Layer bitfields.
#define GREEK_LAYER (1UL << _GREEK) #define GREEK_LAYER (1UL << _GREEK)
#define SHIFTGREEK_LAYER (1UL << _SHIFTGREEK) #define SHIFTGREEK_LAYER (1UL << _SHIFTGREEK)
@ -185,6 +362,8 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
// get_mods or the like, because this function is called *before* that's updated! // get_mods or the like, because this function is called *before* that's updated!
static bool shift_held = false; static bool shift_held = false;
static bool alt_held = false; static bool alt_held = false;
static bool ctrl_held = false;
static bool super_held = false;
static bool greek_held = false; static bool greek_held = false;
static bool cadet_held = false; static bool cadet_held = false;
@ -192,18 +371,36 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
static bool shift_lock = false; static bool shift_lock = false;
static int layer_lock = _QWERTY; static int layer_lock = _QWERTY;
// Process any modifier key presses. // The accent request, or zero if there isn't one.
static uint16_t accent_request = 0;
// If this is set to true, don't trigger any handling of pending accent requests. That's what we
// want to do if e.g. the user just hit the shift key or something.
bool ignore_accent_change = !record->event.pressed;
// Step 1: Process any modifier key state changes, so we can maintain that state.
if (keycode == KC_LSHIFT || keycode == KC_RSHIFT) { if (keycode == KC_LSHIFT || keycode == KC_RSHIFT) {
shift_held = record->event.pressed; shift_held = record->event.pressed;
ignore_accent_change = true;
} else if (keycode == KC_LALT || keycode == KC_RALT) { } else if (keycode == KC_LALT || keycode == KC_RALT) {
alt_held = record->event.pressed; alt_held = record->event.pressed;
ignore_accent_change = true;
} else if (keycode == KC_LCTRL || keycode == KC_RCTRL) {
ctrl_held = record->event.pressed;
ignore_accent_change = true;
} else if (keycode == KC_LGUI || keycode == KC_RGUI) {
super_held = record->event.pressed;
ignore_accent_change = true;
} else if (keycode == KC_GREEK) { } else if (keycode == KC_GREEK) {
greek_held = record->event.pressed; greek_held = record->event.pressed;
ignore_accent_change = true;
} else if (keycode == KC_CADET) { } else if (keycode == KC_CADET) {
cadet_held = record->event.pressed; cadet_held = record->event.pressed;
ignore_accent_change = true;
} }
// Now let's transform these into the "cadet request" and "greek request." // Step 2: Figure out which layer we're supposed to be in, by transforming all the prior stuff
// into layer requests.
const bool greek_request = (greek_held && !alt_held); const bool greek_request = (greek_held && !alt_held);
const bool cadet_request = (cadet_held || (greek_held && alt_held)); const bool cadet_request = (cadet_held || (greek_held && alt_held));
@ -260,8 +457,33 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
layer_state_set(new_layer_state); layer_state_set(new_layer_state);
} }
// TODO: We can update LED states based on shift_lock (caps), layer_lock (layer lock), and // Step 3: Handle accents. If there's a pending accent request, process it. If what the user just
// base_layer (base layer). // hit creates a new accent request, update the pending state for the next keypress.
if (!ignore_accent_change && accent_request && record->event.pressed) {
// Only do the accent stuff if we're in the QWERTY layer and we aren't modifying something.
const bool force_no_accent = (
actual_layer != _QWERTY ||
ctrl_held ||
super_held ||
alt_held
);
const uint16_t old_accent = accent_request;
accent_request = 0;
if (process_key_after_accent(old_accent, keycode, shifted, force_no_accent)) {
return false;
}
}
// And if a new accent request just arrived, update accent_request.
if (keycode >= KC_ACCENT_START && keycode < KC_ACCENT_END && record->event.pressed) {
if (shifted) {
// Shift + accent request generates the combining accent key, and leaves accent_request alone.
register_unicode(pgm_read_word_near(combined_accents + keycode - KC_ACCENT_START));
return false;
} else {
accent_request = keycode;
}
}
return true; return true;
} }