]> git.donarmstrong.com Git - qmk_firmware.git/blob - keyboard/ergodox_ez/keymaps/bepo/keymap.c
BÉPO over CSA: GR2A-shifted characters in AltGr layer
[qmk_firmware.git] / keyboard / ergodox_ez / keymaps / bepo / keymap.c
1 /* TypeMatrix-2030-like keymap  */
2 #include "ergodox_ez.h"
3 #include "debug.h"
4 #include "action_layer.h"
5 #include "action_util.h"
6 #include "led.h"
7 #include "keymap_extras/keymap_bepo.h"
8 #include "keymap_extras/keymap_canadian_multilingual.h"
9
10 enum layers {
11     LR_BASE, // default layer
12     LR_CSA, // BÉPO over Canadian Multilingual (CSA)
13     LR_CSA_SFT, // shifted BÉPO over CSA
14     LR_CSA_AGR, // altgr-ed BÉPO over CSA
15     LR_CSA_AGR_SFT, // altgr-shifted BÉPO over CSA
16     LR_NUMR, // numeric layer
17     LR_FN, // fn layer
18 };
19
20 #define IS_CA_MULT_ENABLED()    (default_layer_state & (1 << LR_CSA))
21
22 enum macros {
23     // Characters that do not exist in CSA and must be implemented based on unicode support
24     // Note: these are intentionally declared first to be used as indexes in spec_chars below
25     UC_NDSH, // –
26     UC_MDSH, // —
27     UC_ELPS, // …
28     END_UC, // indicates the last unicode character macro
29     // other macros
30     M_TGCM, // toggle CA-mult
31     M_CMSFT, // toggle shift on CA-mult
32     // macros for characters that need to be un-shifted in LR_CA_MULT_SHIFT
33     M_1,
34     M_2,
35     M_3,
36     M_4,
37     M_5,
38     M_6,
39     M_7,
40     M_8,
41     M_9,
42     M_0,
43     M_DEGR,
44     M_SCLN,
45     M_GRV,
46     M_NBSP,
47     // macros for characters that don't have a simple key combination in LR_CA_MULT_ALTGR
48     M_CRC,
49     // other layer macros
50     M_DBL0,
51     M_FNLR,
52 };
53
54 const uint16_t unicode_chars[] = {
55         [UC_NDSH] = L'–',
56         [UC_MDSH] = L'—',
57         [UC_ELPS] = L'…',
58 };
59
60 /* shortcut for unicod character macros */
61 #define MUC(name)   M(UC_##name)
62
63 const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
64 /* Basic layer
65  *
66  * ,--------------------------------------------------.           ,--------------------------------------------------.
67  * |   $    |   "  |   «  |   »  |   (  |   )  | Del  |           | Del  |   @  |   +  |   -  |   /  |   *  |   W    |
68  * |--------+------+------+------+------+-------------|           |------+------+------+------+------+------+--------|
69  * | Tab    |   B  |   É  |   P  |   O  |   È  |Backsp|           |Backsp|   ^  |   V  |   D  |   L  |   J  |   Z    |
70  * |--------+------+------+------+------+------|ace   |           |ace   |------+------+------+------+------+--------|
71  * |   =    |   A  |   U  |   I  |   E  |   ,  |------|           |------|   C  |   T  |   S  |   R  |   N  |   M    |
72  * |--------+------+------+------+------+------|Enter |           |Enter |------+------+------+------+------+--------|
73  * | LShift |   À  |   Y  |   X  |   .  |   K  |      |           |      |   '  |   Q  |   G  |   H  |   F  | RShift |
74  * `--------+------+------+------+------+-------------'           `-------------+------+------+------+------+--------'
75  *   |LCtrl |  fn  | LGui | Play |App/Alt|                                      |Alt Gr|   %  | Home |   Ç  |End/Ctl|
76  *   `-----------------------------------'                                      `-----------------------------------'
77  *                                       ,--------------.       ,-------------.
78  *                                       |Esc/Alt| num  |       | Left |Right |
79  *                                ,------+-------+------|       |------+------+------.
80  *                                |      |       | PgUp |       |  Up  |      |      |
81  *                                |Space |LShift |------|       |------|RShift|Space |
82  *                                |      |       | PgDn |       | Down |      |      |
83  *                                `---------------------'       `--------------------'
84  */
85 // If it accepts an argument (i.e, is a function), it doesn't need KC_.
86 // Otherwise, it needs KC_*
87 [LR_BASE] = KEYMAP(  // layer 0 : default
88         // left hand
89         BP_DLR,     KC_1,      KC_2,    KC_3,    KC_4,          KC_5,    KC_DELT,
90         KC_TAB,     BP_B,      BP_ECUT, BP_P,    BP_O,          BP_EGRV, KC_BSPC,
91         BP_EQL,     BP_A,      BP_U,    BP_I,    BP_E,          BP_COMM,
92         KC_LSFT,    BP_AGRV,   BP_Y,    BP_X,    BP_DOT,        BP_K,    KC_ENT,
93         KC_LCTL,    M(M_FNLR), KC_LGUI, KC_MPLY, ALT_T(KC_APP),
94
95                                               ALT_T(KC_ESC),  TG(LR_NUMR),
96                                                               KC_PGUP,
97                                             KC_SPC, KC_LSFT,  KC_PGDN,
98
99         // right hand
100         KC_DELT,   KC_6,     KC_7,    KC_8,    KC_9,    KC_0,     BP_W,
101         KC_BSPC,   BP_DCRC,  BP_V,    BP_D,    BP_L,    BP_J,     BP_Z,
102                    BP_C,     BP_T,    BP_S,    BP_R,    BP_N,     BP_M,
103         KC_ENT,    BP_APOS,  BP_Q,    BP_G,    BP_H,    BP_F,     KC_RSFT,
104                              BP_ALGR, BP_PERC, KC_HOME, BP_CCED,  CTL_T(KC_END),
105
106         KC_LEFT, KC_RGHT,
107         KC_UP,
108         KC_DOWN, KC_RSFT,  KC_SPC
109     ),
110 /**
111  * Same as default but for use with Canadian Multilingual on OS side
112  */
113 [LR_CSA] = KEYMAP(
114         // left hand
115         KC_DLR,      CSA_DQOT,   CSA_LGIL,  CSA_RGIL,  KC_LPRN,       KC_RPRN,   KC_DELT,
116         KC_TAB,      KC_B,       CSA_ECUT,  KC_P,      KC_O,          CSA_EGRV,  KC_BSPC,
117         KC_EQL,      KC_A,       KC_U,      KC_I,      KC_E,          KC_COMM,
118         M(M_CMSFT),  CSA_AGRV,   KC_Y,      KC_X,      KC_DOT,        KC_K,      KC_ENT,
119         KC_LCTL,     M(M_FNLR),  KC_LGUI,   KC_MPLY,   ALT_T(KC_APP),
120
121                                               ALT_T(KC_ESC),  TG(LR_NUMR),
122                                                               KC_PGUP,
123                                             KC_SPC, KC_LSFT,  KC_PGDN,
124
125         // right hand
126         KC_DELT,   KC_AT,     KC_PLUS,  KC_MINS,  CSA_SLSH,  KC_ASTR,   KC_W,
127         KC_BSPC,   CSA_DCRC,  KC_V,     KC_D,     KC_L,      KC_J,      KC_Z,
128                    KC_C,      KC_T,     KC_S,     KC_R,      KC_N,      KC_M,
129         KC_ENT,    CSA_APOS,  KC_Q,     KC_G,     KC_H,      KC_F,      M(M_CMSFT),
130                        MO(LR_CSA_AGR),  KC_PERC,  KC_HOME,   CSA_CCED,  CTL_T(KC_END),
131
132         KC_LEFT, KC_RGHT,
133         KC_UP,
134         KC_DOWN, KC_RSFT,  KC_SPC
135     ),
136 /* Shifted BÉPO over Canadian Multilingual
137  *
138  * ,--------------------------------------------------.           ,--------------------------------------------------.
139  * |   #    |   1  |   2  |   3  |   4  |   5  |      |           |      |   6  |   7  |   8  |   9  |   0  |        |
140  * |--------+------+------+------+------+-------------|           |------+------+------+------+------+------+--------|
141  * |        |      |      |      |      |      |      |           |      |   !  |      |      |      |      |        |
142  * |--------+------+------+------+------+------|      |           |      |------+------+------+------+------+--------|
143  * |   °    |      |      |      |      |   ;  |------|           |------|      |      |      |      |      |        |
144  * |--------+------+------+------+------+------|      |           |      |------+------+------+------+------+--------|
145  * |        |      |      |      |   :  |      |      |           |      |   ?  |      |      |      |      |        |
146  * `--------+------+------+------+------+-------------'           `-------------+------+------+------+------+--------'
147  *   |      |      |      |      |      |                                       |      |   `  |      |      |       |
148  *   `----------------------------------'                                       `-----------------------------------'
149  *                                        ,-------------.       ,-------------.
150  *                                        |      |      |       |      |      |
151  *                                 ,------|------|------|       |------+------+------.
152  *                                 |      |      |      |       |      |      |      |
153  *                                 |      |      |------|       |------|      |      |
154  *                                 |      |      |      |       |      |      |      |
155  *                                 `--------------------'       `--------------------'
156  */
157 [LR_CSA_SFT] = KEYMAP(
158         // left hand
159         KC_HASH,  M(M_1),   M(M_2),   M(M_3),  M(M_4),   M(M_5),   KC_TRNS,
160         KC_TRNS,  KC_TRNS,  KC_TRNS,  KC_TRNS, KC_TRNS,  KC_TRNS,  KC_TRNS,
161         M(M_DEGR),KC_TRNS,  KC_TRNS,  KC_TRNS, KC_TRNS,  M(M_SCLN),
162         KC_TRNS,  KC_TRNS,  KC_TRNS,  KC_TRNS, KC_COLN,  KC_TRNS,  KC_TRNS,
163         KC_TRNS,  KC_TRNS,  KC_TRNS,  KC_TRNS, KC_TRNS,
164
165                                                       KC_TRNS,  KC_TRNS,
166                                                                 KC_TRNS,
167                                           M(M_NBSP),  KC_TRNS,  KC_TRNS,
168
169         // right hand
170         KC_TRNS,  M(M_6),    M(M_7),   M(M_8),   M(M_9),   M(M_0),   KC_TRNS,
171         KC_TRNS,  KC_EXLM,   KC_TRNS,  KC_TRNS,  KC_TRNS,  KC_TRNS,  KC_TRNS,
172                   KC_TRNS,   KC_TRNS,  KC_TRNS,  KC_TRNS,  KC_TRNS,  KC_TRNS,
173         KC_TRNS,  CSA_QEST,  KC_TRNS,  KC_TRNS,  KC_TRNS,  KC_TRNS,  KC_TRNS,
174                              KC_TRNS,  M(M_GRV), KC_TRNS,  KC_TRNS,  KC_TRNS,
175
176         KC_TRNS,  KC_TRNS,
177         KC_TRNS,
178         KC_TRNS,  KC_TRNS,  M(M_NBSP)
179     ),
180 /* AltGr-ed BÉPO over Canadian Multilingual
181  * "////" indicates that the key is disabled (unsupported bépo character)
182  *
183  * ,--------------------------------------------------.           ,--------------------------------------------------.
184  * |    –   |   —  |   <  |   >  |   [  |   ]  |      |           |      |   ^  |   ±  | //// |   ÷  |   ×  | dead ˘ |
185  * |--------+------+------+------+------+-------------|           |------+------+------+------+------+------+--------|
186  * |        |   |  |dead '|   &  |   œ  |dead `|      |           |      |   ¡  |dead ˇ|   ð  | //// |   ij  | ////// |
187  * |--------+------+------+------+------+------|      |           |      |------+------+------+------+------+--------|
188  * | ////// |   æ  |   ù  |dead "|   €  |   ̛’  |------|           |------|   ©  |   þ  |   ß  |   ®  |dead ~| dead ¯ |
189  * |--------+------+------+------+------+------|      |           |      |------+------+------+------+------+--------|
190  * |        |   \  |   {  |   }  |   …  |   ~  |      |           |      |   ¿  |dead °|   μ  | //// |dead ˛|        |
191  * `--------+------+------+------+------+-------------'           `-------------+------+------+------+------+--------'
192  *   |      |      |      |      |      |                                       |      | //// |      |dead ¸|       |
193  *   `----------------------------------'                                       `-----------------------------------'
194  *                                        ,-------------.       ,-------------.
195  *                                        |      |      |       |      |      |
196  *                                 ,------|------|------|       |------+------+------.
197  *                                 |      |      |      |       |      |      |      |
198  *                                 |   _  |      |------|       |------|      |  _   |
199  *                                 |      |      |      |       |      |      |      |
200  *                                 `--------------------'       `--------------------'
201  */
202 [LR_CSA_AGR] = KEYMAP(
203         // left hand
204         MUC(NDSH),  MUC(MDSH),  CSA_LESS,  CSA_GRTR,  CSA_LBRC,   CSA_RBRC,  KC_TRNS,
205         KC_TRNS,    CSA_PIPE,   CSA_DACT,  KC_AMPR,   CSA_OE,     CSA_DGRV,  KC_TRNS,
206         KC_NO,      CSA_AE,     CSA_UGRV,  CSA_DTRM,  CSA_EURO,   CSA_RQOT,
207         KC_TRNS,    CSA_BSLS,   CSA_LCBR,  CSA_RCBR,  MUC(ELPS),  CSA_TILD,  KC_TRNS,
208         KC_TRNS,    KC_TRNS,    KC_TRNS,   KC_TRNS,   KC_TRNS,
209
210                                                       KC_TRNS,  KC_TRNS,
211                                                                 KC_TRNS,
212                                             KC_UNDS,  KC_TRNS,  KC_TRNS,
213
214         // right hand
215         KC_TRNS,  M(M_CRC),  CSA_PSMS,  KC_NO,     CSA_DVSN, CSA_TIMS,  CSA_DBRV,
216         KC_TRNS,  CSA_IXLM,  CSA_DCAR,  CSA_ETH,   KC_NO,    CSA_IJ,    KC_NO,
217                   CSA_CPRT,  CSA_THRN,  CSA_SRPS,  CSA_RTM,  CSA_DTLD,  CSA_DMCR,
218         KC_TRNS,  CSA_IQST,  CSA_DRNG,  CSA_MU,    KC_NO,    CSA_DOGO,  KC_TRNS,
219                              KC_TRNS,   KC_NO,     KC_TRNS,  CSA_DCED,  KC_TRNS,
220
221         KC_TRNS,  KC_TRNS,
222         KC_TRNS,
223         KC_TRNS,  KC_TRNS,  KC_UNDS
224     ),
225 /* Numeric Layer
226  *
227  * ,--------------------------------------------------.           ,--------------------------------------------------.
228  * |        |  F1  |  F2  |  F3  |  F4  |  F5  |      |           |      |      |      |  Tab |   /  |   *  |   -    |
229  * |--------+------+------+------+------+-------------|           |------+------+------+------+------+------+--------|
230  * |        |  F6  |  F7  |  F8  |  F9  |  F10 |      |           |      |      | Home |   7  |   8  |   9  |   +    |
231  * |--------+------+------+------+------+------|      |           |      |------+------+------+------+------+--------|
232  * |        |  F11 |  F12 |      |      |      |------|           |------|  Up  | End  |   4  |   5  |   6  |   +    |
233  * |--------+------+------+------+------+------|      |           |      |------+------+------+------+------+--------|
234  * |        |      |      |      |      |      |      |           | Left | Down | Right|   1  |   2  |   3  |KpEnter |
235  * `--------+------+------+------+------+-------------'           `-------------+------+------+------+------+--------'
236  *   |      |      |      |      |      |                                       |      |   0  |  00  |   .  |Etr/Ctl|
237  *   `----------------------------------'                                       `-----------------------------------'
238  *                                        ,-------------.       ,-------------.
239  *                                        |      |      |       |n.lock|c.lock|
240  *                                 ,------|------|------|       |------+------+------.
241  *                                 |      |      |      |       |      |      |      |
242  *                                 |      |      |------|       |------|      |      |
243  *                                 |      |      |      |       |      |      |      |
244  *                                 `--------------------'       `--------------------'
245  */
246 // SYMBOLS
247 [LR_NUMR] = KEYMAP(
248        // left hand
249        KC_TRNS, KC_F1,   KC_F2,   KC_F3,   KC_F4,   KC_F5,   KC_TRNS,
250        KC_TRNS, KC_F6,   KC_F7,   KC_F8,   KC_F9,   KC_F10,  KC_TRNS,
251        KC_TRNS, KC_F11,  KC_F12,  KC_TRNS, KC_TRNS, KC_TRNS,
252        KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
253        KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
254
255                                        KC_TRNS,KC_TRNS,
256                                                KC_TRNS,
257                               KC_TRNS, KC_TRNS,KC_TRNS,
258        // right hand
259        KC_TRNS, KC_F6,   KC_F7,   KC_TAB,  KC_PSLS,  KC_PAST, KC_PMNS,
260        KC_TRNS, KC_TRNS, KC_HOME, KC_P7,   KC_P8,    KC_P9,   KC_PPLS,
261                 KC_UP,   KC_END,  KC_P4,   KC_P5,    KC_P6,   KC_PPLS,
262        KC_LEFT, KC_DOWN, KC_RGHT, KC_P1,   KC_P2,    KC_P3,   KC_PENT,
263                          KC_TRNS, KC_P0,   M(M_DBL0),KC_PDOT, CTL_T(KC_PENT),
264
265        KC_NLCK, KC_CAPS,
266        KC_TRNS,
267        KC_TRNS, KC_TRNS, KC_TRNS
268 ),
269 /* fn layer
270  *
271  * ,--------------------------------------------------.           ,--------------------------------------------------.
272  * |~CA-mult|      |      |      |      |      |Insert|           |Insert|Eject |Power |Sleep | Wake |PrtScr|ScrollLk|
273  * |--------+------+------+------+------+-------------|           |------+------+------+------+------+------+--------|
274  * |        |      |      |      |      |      |VolUp |           |      |      |      |      |      |      | Pause  |
275  * |--------+------+------+------+------+------|      |           |      |------+------+------+------+------+--------|
276  * |  RESET |      |      | Calc | Mail |Browsr|------|           |------|      |      |      |      |      |        |
277  * |--------+------+------+------+------+------|      |           |      |------+------+------+------+------+--------|
278  * |        |      | cut  | copy |paste | Mute |VolDn |           |      |      |      |      |      |      |        |
279  * `--------+------+------+------+------+-------------'           `-------------+------+------+------+------+--------'
280  *   |      |      |      |      |      |                                       |      |      |      |      |      |
281  *   `----------------------------------'                                       `----------------------------------'
282  *                                        ,-------------.       ,-------------.
283  *                                        |      |      |       |      |      |
284  *                                 ,------|------|------|       |------+------+------.
285  *                                 |      |      |      |       | Next |      |      |
286  *                                 | Mute |      |------|       |------|      |      |
287  *                                 |      |      |      |       | Prev |      |      |
288  *                                 `--------------------'       `--------------------'
289  */
290 // MEDIA AND MOUSE
291 [LR_FN] = KEYMAP(
292        M(M_TGCM), KC_TRNS, KC_TRNS,      KC_TRNS,     KC_TRNS,      KC_TRNS, KC_INS,
293        KC_TRNS,   KC_TRNS, KC_TRNS,      KC_TRNS,     KC_TRNS,      KC_TRNS, KC_VOLU,
294        RESET,     KC_TRNS, KC_TRNS,      KC_CALC,     KC_MAIL,      KC_WHOM,
295        KC_TRNS,   KC_TRNS, LSFT(KC_DELT),LCTL(KC_INS),LSFT(KC_INS), KC_MUTE, KC_VOLD,
296        KC_TRNS,   KC_TRNS, KC_TRNS,      KC_TRNS,     KC_TRNS,
297
298                                            KC_TRNS, KC_TRNS,
299                                                     KC_TRNS,
300                                   KC_MUTE, KC_TRNS, KC_TRNS,
301     // right hand
302        KC_INS,   KC_EJCT, KC_PWR,  KC_SLEP, KC_WAKE, KC_PSCR, KC_SLCK,
303        KC_TRNS,  KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_PAUS,
304                  KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
305        KC_TRNS,  KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
306                           KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
307
308        KC_TRNS, KC_TRNS,
309        KC_MPRV,
310        KC_MNXT, KC_TRNS, KC_TRNS
311 ),
312 };
313
314 const uint16_t PROGMEM fn_actions[] = {
315 };
316
317 void hold_shift(void) {
318     register_code(KC_LSHIFT);
319 }
320
321 void release_shift(void) {
322     unregister_code(KC_LSHIFT);
323 }
324
325 uint16_t hextokeycode(int hex) {
326     if (hex == 0x0) {
327         return KC_P0;
328     } else if (hex < 0xA) {
329         return KC_P1 + (hex - 0x1);
330     } else {
331         return KC_A + (hex - 0xA);
332     }
333 }
334
335 void send_unicode(uint16_t unicode)
336 {
337     // For more info on how this works per OS, see here: https://en.wikipedia.org/wiki/Unicode_input#Hexadecimal_code_input
338     // Implemented for Windows:
339     // Pressing ALT followed by + followed by the unicode code point in hex.
340     // Requires registry key HKEY_CURRENT_USER\Control Panel\Input Method\EnableHexNumpad set to String 1
341     register_code(KC_LALT);
342     register_code(KC_PPLS);
343     unregister_code(KC_PPLS);
344
345     for (int i = 12; i >= 0; i -= 4) {
346         register_code(hextokeycode((unicode >> i) & 0xF));
347         unregister_code(hextokeycode((unicode >> i) & 0xF));
348     }
349
350     unregister_code(KC_LALT);
351 }
352
353 const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
354 {
355   // MACRODOWN only works in this function
356     switch(id) {
357         case 0 ... END_UC:
358             if (record->event.pressed) {
359                 send_unicode(unicode_chars[id]);
360             }
361             break;
362         case M_TGCM:
363             if (record->event.pressed) {
364                 default_layer_xor(1 << LR_CSA);
365             }
366             break;
367         case M_CMSFT:
368             if (record->event.pressed) {
369                 layer_on(LR_CSA_SFT);
370                 hold_shift();
371             } else {
372                 release_shift();
373                 layer_off(LR_CSA_SFT);
374             }
375             break;
376         case M_1 ... M_0:
377         case M_DEGR:
378         case M_SCLN:
379         case M_GRV:
380         case M_NBSP:
381             // macros of the shift layer that require to release shift
382             if (record->event.pressed) {
383                 release_shift();
384                 switch (id) {
385                     case M_1 ... M_0:
386                         register_code(KC_1 + (id - M_1));
387                         break;
388                     case M_DEGR:
389                         return MACRO(DOWN(CSA_ALTGR), D(SCLN), END);
390                     case M_SCLN:
391                         return MACRO(D(SCLN), END);
392                     case M_GRV:
393                         return MACRO(DOWN(CSA_ALTGR), TYPE(CSA_DCRC), UP(CSA_ALTGR), T(SPACE), END);
394                     case M_NBSP:
395                         // use weak mod such that pressing another key will not be affected
396                         add_weak_mods(MOD_BIT(CSA_ALTGR));
397                         return MACRO(D(SPACE), END);
398                 }
399             } else {
400                 hold_shift();
401                 switch (id) {
402                     case M_1 ... M_0:
403                         unregister_code(KC_1 + (id - M_1));
404                         break;
405                     case M_DEGR:
406                         return MACRO(UP(CSA_ALTGR), D(LSFT), U(SCLN), END);
407                     case M_SCLN:
408                         return MACRO(D(LSFT), U(SCLN), END);
409                     case M_NBSP:
410                         del_weak_mods(MOD_BIT(CSA_ALTGR));
411                         return MACRO(U(SPACE), END);
412                 }
413             }
414             break;
415         case M_CRC:
416             if (record->event.pressed) {
417                 return MACRO(TYPE(CSA_DCRC), T(SPACE), END);
418             }
419             break;
420         case M_DBL0:
421             if (record->event.pressed) {
422                 return MACRO( I(25), T(P0), T(P0), END );
423             }
424         break;
425         case M_FNLR:
426             layer_invert(LR_NUMR);
427             layer_invert(LR_FN);
428             break;
429     }
430     return MACRO_NONE;
431 };
432
433 // Runs just one time when the keyboard initializes.
434 void * matrix_init_user(void) {
435     return NULL;
436 };
437
438 // Runs constantly in the background, in a loop.
439 void * matrix_scan_user(void) {
440
441     ergodox_board_led_off();
442     ergodox_right_led_1_off();
443     ergodox_right_led_2_off();
444     ergodox_right_led_3_off();
445     // led 1: numeric layer
446     if (layer_state & (1 << LR_NUMR)) {
447         ergodox_right_led_1_on();
448     }
449     // led 2: BÉPO over Canadian Multilingual
450     if (IS_CA_MULT_ENABLED()) {
451         ergodox_right_led_2_on();
452     }
453     // led 3: caps lock
454     if (host_keyboard_leds() & (1<<USB_LED_CAPS_LOCK)) {
455       ergodox_right_led_3_on();
456     }
457     return NULL;
458 };