]> git.donarmstrong.com Git - qmk_firmware.git/blob - quantum/quantum.c
Merge pull request #496 from fredizzimo/makefile_optimization
[qmk_firmware.git] / quantum / quantum.c
1 #include "quantum.h"
2
3 __attribute__ ((weak))
4 bool process_action_kb(keyrecord_t *record) {
5   return true;
6 }
7
8 __attribute__ ((weak))
9 bool process_record_kb(uint16_t keycode, keyrecord_t *record) {
10   return process_record_user(keycode, record);
11 }
12
13 __attribute__ ((weak))
14 bool process_record_user(uint16_t keycode, keyrecord_t *record) {
15   return true;
16 }
17
18 // Shift / paren setup
19
20 #ifndef LSPO_KEY
21   #define LSPO_KEY KC_9
22 #endif
23 #ifndef RSPC_KEY
24   #define RSPC_KEY KC_0
25 #endif
26
27 static bool shift_interrupted[2] = {0, 0};
28
29 bool process_record_quantum(keyrecord_t *record) {
30
31   /* This gets the keycode from the key pressed */
32   keypos_t key = record->event.key;
33   uint16_t keycode;
34
35   #if !defined(NO_ACTION_LAYER) && defined(PREVENT_STUCK_MODIFIERS)
36     uint8_t layer;
37
38     if (record->event.pressed) {
39       layer = layer_switch_get_layer(key);
40       update_source_layers_cache(key, layer);
41     } else {
42       layer = read_source_layers_cache(key);
43     }
44     keycode = keymap_key_to_keycode(layer, key);
45   #else
46     keycode = keymap_key_to_keycode(layer_switch_get_layer(key), key);
47   #endif
48
49     // This is how you use actions here
50     // if (keycode == KC_LEAD) {
51     //   action_t action;
52     //   action.code = ACTION_DEFAULT_LAYER_SET(0);
53     //   process_action(record, action);
54     //   return false;
55     // }
56
57   if (!(
58     process_record_kb(keycode, record) &&
59   #ifdef MIDI_ENABLE
60     process_midi(keycode, record) &&
61   #endif
62   #ifdef AUDIO_ENABLE
63     process_music(keycode, record) &&
64   #endif
65   #ifdef TAP_DANCE_ENABLE
66     process_tap_dance(keycode, record) &&
67   #endif
68   #ifndef DISABLE_LEADER
69     process_leader(keycode, record) &&
70   #endif
71   #ifndef DISABLE_CHORDING
72     process_chording(keycode, record) &&
73   #endif
74   #ifdef UNICODE_ENABLE
75     process_unicode(keycode, record) &&
76   #endif
77       true)) {
78     return false;
79   }
80
81   // Shift / paren setup
82
83   switch(keycode) {
84     case RESET:
85       if (record->event.pressed) {
86         clear_keyboard();
87         #ifdef AUDIO_ENABLE
88           stop_all_notes();
89           shutdown_user();
90         #endif
91         wait_ms(250);
92         #ifdef CATERINA_BOOTLOADER
93             *(uint16_t *)0x0800 = 0x7777; // these two are a-star-specific
94         #endif
95         bootloader_jump();
96       }
97           return false;
98       break;
99     case DEBUG:
100       if (record->event.pressed) {
101           print("\nDEBUG: enabled.\n");
102           debug_enable = true;
103       }
104           return false;
105       break;
106         #ifdef RGBLIGHT_ENABLE
107         case RGB_TOG:
108                 if (record->event.pressed) {
109                         rgblight_toggle();
110       }
111           return false;
112       break;
113         case RGB_MOD:
114                 if (record->event.pressed) {
115                         rgblight_step();
116       }
117           return false;
118       break;
119         case RGB_HUI:
120                 if (record->event.pressed) {
121                         rgblight_increase_hue();
122       }
123           return false;
124       break;
125         case RGB_HUD:
126                 if (record->event.pressed) {
127                         rgblight_decrease_hue();
128       }
129           return false;
130       break;
131         case RGB_SAI:
132                 if (record->event.pressed) {
133                         rgblight_increase_sat();
134       }
135           return false;
136       break;
137         case RGB_SAD:
138                 if (record->event.pressed) {
139                         rgblight_decrease_sat();
140       }
141           return false;
142       break;
143         case RGB_VAI:
144                 if (record->event.pressed) {
145                         rgblight_increase_val();
146       }
147           return false;
148       break;
149         case RGB_VAD:
150                 if (record->event.pressed) {
151                         rgblight_decrease_val();
152       }
153           return false;
154       break;
155         #endif
156     case MAGIC_SWAP_CONTROL_CAPSLOCK ... MAGIC_UNSWAP_ALT_GUI:
157       if (record->event.pressed) {
158         // MAGIC actions (BOOTMAGIC without the boot)
159         if (!eeconfig_is_enabled()) {
160             eeconfig_init();
161         }
162         /* keymap config */
163         keymap_config.raw = eeconfig_read_keymap();
164         if (keycode == MAGIC_SWAP_CONTROL_CAPSLOCK) {
165             keymap_config.swap_control_capslock = 1;
166         } else if (keycode == MAGIC_CAPSLOCK_TO_CONTROL) {
167             keymap_config.capslock_to_control = 1;
168         } else if (keycode == MAGIC_SWAP_LALT_LGUI) {
169             keymap_config.swap_lalt_lgui = 1;
170         } else if (keycode == MAGIC_SWAP_RALT_RGUI) {
171             keymap_config.swap_ralt_rgui = 1;
172         } else if (keycode == MAGIC_NO_GUI) {
173             keymap_config.no_gui = 1;
174         } else if (keycode == MAGIC_SWAP_GRAVE_ESC) {
175             keymap_config.swap_grave_esc = 1;
176         } else if (keycode == MAGIC_SWAP_BACKSLASH_BACKSPACE) {
177             keymap_config.swap_backslash_backspace = 1;
178         } else if (keycode == MAGIC_HOST_NKRO) {
179             keymap_config.nkro = 1;
180         } else if (keycode == MAGIC_SWAP_ALT_GUI) {
181             keymap_config.swap_lalt_lgui = 1;
182             keymap_config.swap_ralt_rgui = 1;
183         }
184         /* UNs */
185         else if (keycode == MAGIC_UNSWAP_CONTROL_CAPSLOCK) {
186             keymap_config.swap_control_capslock = 0;
187         } else if (keycode == MAGIC_UNCAPSLOCK_TO_CONTROL) {
188             keymap_config.capslock_to_control = 0;
189         } else if (keycode == MAGIC_UNSWAP_LALT_LGUI) {
190             keymap_config.swap_lalt_lgui = 0;
191         } else if (keycode == MAGIC_UNSWAP_RALT_RGUI) {
192             keymap_config.swap_ralt_rgui = 0;
193         } else if (keycode == MAGIC_UNNO_GUI) {
194             keymap_config.no_gui = 0;
195         } else if (keycode == MAGIC_UNSWAP_GRAVE_ESC) {
196             keymap_config.swap_grave_esc = 0;
197         } else if (keycode == MAGIC_UNSWAP_BACKSLASH_BACKSPACE) {
198             keymap_config.swap_backslash_backspace = 0;
199         } else if (keycode == MAGIC_UNHOST_NKRO) {
200             keymap_config.nkro = 0;
201         } else if (keycode == MAGIC_UNSWAP_ALT_GUI) {
202             keymap_config.swap_lalt_lgui = 0;
203             keymap_config.swap_ralt_rgui = 0;
204         }
205         eeconfig_update_keymap(keymap_config.raw);
206         return false;
207       }
208       break;
209     case KC_LSPO: {
210       if (record->event.pressed) {
211         shift_interrupted[0] = false;
212         register_mods(MOD_BIT(KC_LSFT));
213       }
214       else {
215         if (!shift_interrupted[0]) {
216           register_code(LSPO_KEY);
217           unregister_code(LSPO_KEY);
218         }
219         unregister_mods(MOD_BIT(KC_LSFT));
220       }
221       return false;
222       break;
223     }
224
225     case KC_RSPC: {
226       if (record->event.pressed) {
227         shift_interrupted[1] = false;
228         register_mods(MOD_BIT(KC_RSFT));
229       }
230       else {
231         if (!shift_interrupted[1]) {
232           register_code(RSPC_KEY);
233           unregister_code(RSPC_KEY);
234         }
235         unregister_mods(MOD_BIT(KC_RSFT));
236       }
237       return false;
238       break;
239     }
240     default: {
241       shift_interrupted[0] = true;
242       shift_interrupted[1] = true;
243       break;
244     }
245   }
246
247   return process_action_kb(record);
248 }
249
250 const bool ascii_to_qwerty_shift_lut[0x80] PROGMEM = {
251     0, 0, 0, 0, 0, 0, 0, 0,
252     0, 0, 0, 0, 0, 0, 0, 0,
253     0, 0, 0, 0, 0, 0, 0, 0,
254     0, 0, 0, 0, 0, 0, 0, 0,
255     0, 1, 1, 1, 1, 1, 1, 0,
256     1, 1, 1, 1, 0, 0, 0, 0,
257     0, 0, 0, 0, 0, 0, 0, 0,
258     0, 0, 1, 0, 1, 0, 1, 1,
259     1, 1, 1, 1, 1, 1, 1, 1,
260     1, 1, 1, 1, 1, 1, 1, 1,
261     1, 1, 1, 1, 1, 1, 1, 1,
262     1, 1, 1, 0, 0, 0, 1, 1,
263     0, 0, 0, 0, 0, 0, 0, 0,
264     0, 0, 0, 0, 0, 0, 0, 0,
265     0, 0, 0, 0, 0, 0, 0, 0,
266     0, 0, 0, 1, 1, 1, 1, 0
267 };
268
269 const uint8_t ascii_to_qwerty_keycode_lut[0x80] PROGMEM = {
270     0, 0, 0, 0, 0, 0, 0, 0,
271     KC_BSPC, KC_TAB, KC_ENT, 0, 0, 0, 0, 0,
272     0, 0, 0, 0, 0, 0, 0, 0,
273     0, 0, 0, KC_ESC, 0, 0, 0, 0,
274     KC_SPC, KC_1, KC_QUOT, KC_3, KC_4, KC_5, KC_7, KC_QUOT,
275     KC_9, KC_0, KC_8, KC_EQL, KC_COMM, KC_MINS, KC_DOT, KC_SLSH,
276     KC_0, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7,
277     KC_8, KC_9, KC_SCLN, KC_SCLN, KC_COMM, KC_EQL, KC_DOT, KC_SLSH,
278     KC_2, KC_A, KC_B, KC_C, KC_D, KC_E, KC_F, KC_G,
279     KC_H, KC_I, KC_J, KC_K, KC_L, KC_M, KC_N, KC_O,
280     KC_P, KC_Q, KC_R, KC_S, KC_T, KC_U, KC_V, KC_W,
281     KC_X, KC_Y, KC_Z, KC_LBRC, KC_BSLS, KC_RBRC, KC_6, KC_MINS,
282     KC_GRV, KC_A, KC_B, KC_C, KC_D, KC_E, KC_F, KC_G,
283     KC_H, KC_I, KC_J, KC_K, KC_L, KC_M, KC_N, KC_O,
284     KC_P, KC_Q, KC_R, KC_S, KC_T, KC_U, KC_V, KC_W,
285     KC_X, KC_Y, KC_Z, KC_LBRC, KC_BSLS, KC_RBRC, KC_GRV, KC_DEL
286 };
287
288 /* for users whose OSes are set to Colemak */
289 #if 0
290 #include "keymap_colemak.h"
291
292 const bool ascii_to_colemak_shift_lut[0x80] PROGMEM = {
293     0, 0, 0, 0, 0, 0, 0, 0,
294     0, 0, 0, 0, 0, 0, 0, 0,
295     0, 0, 0, 0, 0, 0, 0, 0,
296     0, 0, 0, 0, 0, 0, 0, 0,
297     0, 1, 1, 1, 1, 1, 1, 0,
298     1, 1, 1, 1, 0, 0, 0, 0,
299     0, 0, 0, 0, 0, 0, 0, 0,
300     0, 0, 1, 0, 1, 0, 1, 1,
301     1, 1, 1, 1, 1, 1, 1, 1,
302     1, 1, 1, 1, 1, 1, 1, 1,
303     1, 1, 1, 1, 1, 1, 1, 1,
304     1, 1, 1, 0, 0, 0, 1, 1,
305     0, 0, 0, 0, 0, 0, 0, 0,
306     0, 0, 0, 0, 0, 0, 0, 0,
307     0, 0, 0, 0, 0, 0, 0, 0,
308     0, 0, 0, 1, 1, 1, 1, 0
309 };
310
311 const uint8_t ascii_to_colemak_keycode_lut[0x80] PROGMEM = {
312     0, 0, 0, 0, 0, 0, 0, 0,
313     KC_BSPC, KC_TAB, KC_ENT, 0, 0, 0, 0, 0,
314     0, 0, 0, 0, 0, 0, 0, 0,
315     0, 0, 0, KC_ESC, 0, 0, 0, 0,
316     KC_SPC, KC_1, KC_QUOT, KC_3, KC_4, KC_5, KC_7, KC_QUOT,
317     KC_9, KC_0, KC_8, KC_EQL, KC_COMM, KC_MINS, KC_DOT, KC_SLSH,
318     KC_0, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7,
319     KC_8, KC_9, CM_SCLN, CM_SCLN, KC_COMM, KC_EQL, KC_DOT, KC_SLSH,
320     KC_2, CM_A, CM_B, CM_C, CM_D, CM_E, CM_F, CM_G,
321     CM_H, CM_I, CM_J, CM_K, CM_L, CM_M, CM_N, CM_O,
322     CM_P, CM_Q, CM_R, CM_S, CM_T, CM_U, CM_V, CM_W,
323     CM_X, CM_Y, CM_Z, KC_LBRC, KC_BSLS, KC_RBRC, KC_6, KC_MINS,
324     KC_GRV, CM_A, CM_B, CM_C, CM_D, CM_E, CM_F, CM_G,
325     CM_H, CM_I, CM_J, CM_K, CM_L, CM_M, CM_N, CM_O,
326     CM_P, CM_Q, CM_R, CM_S, CM_T, CM_U, CM_V, CM_W,
327     CM_X, CM_Y, CM_Z, KC_LBRC, KC_BSLS, KC_RBRC, KC_GRV, KC_DEL
328 };
329
330 #endif
331
332 void send_string(const char *str) {
333     while (1) {
334         uint8_t keycode;
335         uint8_t ascii_code = pgm_read_byte(str);
336         if (!ascii_code) break;
337         keycode = pgm_read_byte(&ascii_to_qwerty_keycode_lut[ascii_code]);
338         if (pgm_read_byte(&ascii_to_qwerty_shift_lut[ascii_code])) {
339             register_code(KC_LSFT);
340             register_code(keycode);
341             unregister_code(keycode);
342             unregister_code(KC_LSFT);
343         }
344         else {
345             register_code(keycode);
346             unregister_code(keycode);
347         }
348         ++str;
349     }
350 }
351
352 void update_tri_layer(uint8_t layer1, uint8_t layer2, uint8_t layer3) {
353   if (IS_LAYER_ON(layer1) && IS_LAYER_ON(layer2)) {
354     layer_on(layer3);
355   } else {
356     layer_off(layer3);
357   }
358 }
359
360 void tap_random_base64(void) {
361   #if defined(__AVR_ATmega32U4__)
362     uint8_t key = (TCNT0 + TCNT1 + TCNT3 + TCNT4) % 64;
363   #else
364     uint8_t key = rand() % 64;
365   #endif
366   switch (key) {
367     case 0 ... 25:
368       register_code(KC_LSFT);
369       register_code(key + KC_A);
370       unregister_code(key + KC_A);
371       unregister_code(KC_LSFT);
372       break;
373     case 26 ... 51:
374       register_code(key - 26 + KC_A);
375       unregister_code(key - 26 + KC_A);
376       break;
377     case 52:
378       register_code(KC_0);
379       unregister_code(KC_0);
380       break;
381     case 53 ... 61:
382       register_code(key - 53 + KC_1);
383       unregister_code(key - 53 + KC_1);
384       break;
385     case 62:
386       register_code(KC_LSFT);
387       register_code(KC_EQL);
388       unregister_code(KC_EQL);
389       unregister_code(KC_LSFT);
390       break;
391     case 63:
392       register_code(KC_SLSH);
393       unregister_code(KC_SLSH);
394       break;
395   }
396 }
397
398 void matrix_init_quantum() {
399   #ifdef BACKLIGHT_ENABLE
400     backlight_init_ports();
401   #endif
402   matrix_init_kb();
403 }
404
405 void matrix_scan_quantum() {
406   #ifdef AUDIO_ENABLE
407     matrix_scan_music();
408   #endif
409
410   #ifdef TAP_DANCE_ENABLE
411     matrix_scan_tap_dance();
412   #endif
413   matrix_scan_kb();
414 }
415
416 #if defined(BACKLIGHT_ENABLE) && defined(BACKLIGHT_PIN)
417
418 static const uint8_t backlight_pin = BACKLIGHT_PIN;
419
420 #if BACKLIGHT_PIN == B7
421 #  define COM1x1 COM1C1
422 #  define OCR1x  OCR1C
423 #elif BACKLIGHT_PIN == B6
424 #  define COM1x1 COM1B1
425 #  define OCR1x  OCR1B
426 #elif BACKLIGHT_PIN == B5
427 #  define COM1x1 COM1A1
428 #  define OCR1x  OCR1A
429 #else
430 #  error "Backlight pin not supported - use B5, B6, or B7"
431 #endif
432
433 __attribute__ ((weak))
434 void backlight_init_ports(void)
435 {
436
437   // Setup backlight pin as output and output low.
438   // DDRx |= n
439   _SFR_IO8((backlight_pin >> 4) + 1) |= _BV(backlight_pin & 0xF);
440   // PORTx &= ~n
441   _SFR_IO8((backlight_pin >> 4) + 2) &= ~_BV(backlight_pin & 0xF);
442
443   // Use full 16-bit resolution.
444   ICR1 = 0xFFFF;
445
446   // I could write a wall of text here to explain... but TL;DW
447   // Go read the ATmega32u4 datasheet.
448   // And this: http://blog.saikoled.com/post/43165849837/secret-konami-cheat-code-to-high-resolution-pwm-on
449
450   // Pin PB7 = OCR1C (Timer 1, Channel C)
451   // Compare Output Mode = Clear on compare match, Channel C = COM1C1=1 COM1C0=0
452   // (i.e. start high, go low when counter matches.)
453   // WGM Mode 14 (Fast PWM) = WGM13=1 WGM12=1 WGM11=1 WGM10=0
454   // Clock Select = clk/1 (no prescaling) = CS12=0 CS11=0 CS10=1
455
456   TCCR1A = _BV(COM1x1) | _BV(WGM11); // = 0b00001010;
457   TCCR1B = _BV(WGM13) | _BV(WGM12) | _BV(CS10); // = 0b00011001;
458
459   backlight_init();
460   #ifdef BACKLIGHT_BREATHING
461     breathing_defaults();
462   #endif
463 }
464
465 __attribute__ ((weak))
466 void backlight_set(uint8_t level)
467 {
468   // Prevent backlight blink on lowest level
469   // PORTx &= ~n
470   _SFR_IO8((backlight_pin >> 4) + 2) &= ~_BV(backlight_pin & 0xF);
471
472   if ( level == 0 ) {
473     // Turn off PWM control on backlight pin, revert to output low.
474     TCCR1A &= ~(_BV(COM1x1));
475     OCR1x = 0x0;
476   } else if ( level == BACKLIGHT_LEVELS ) {
477     // Turn on PWM control of backlight pin
478     TCCR1A |= _BV(COM1x1);
479     // Set the brightness
480     OCR1x = 0xFFFF;
481   } else {
482     // Turn on PWM control of backlight pin
483     TCCR1A |= _BV(COM1x1);
484     // Set the brightness
485     OCR1x = 0xFFFF >> ((BACKLIGHT_LEVELS - level) * ((BACKLIGHT_LEVELS + 1) / 2));
486   }
487
488   #ifdef BACKLIGHT_BREATHING
489     breathing_intensity_default();
490   #endif
491 }
492
493
494 #ifdef BACKLIGHT_BREATHING
495
496 #define BREATHING_NO_HALT  0
497 #define BREATHING_HALT_OFF 1
498 #define BREATHING_HALT_ON  2
499
500 static uint8_t breath_intensity;
501 static uint8_t breath_speed;
502 static uint16_t breathing_index;
503 static uint8_t breathing_halt;
504
505 void breathing_enable(void)
506 {
507     if (get_backlight_level() == 0)
508     {
509         breathing_index = 0;
510     }
511     else
512     {
513         // Set breathing_index to be at the midpoint (brightest point)
514         breathing_index = 0x20 << breath_speed;
515     }
516
517     breathing_halt = BREATHING_NO_HALT;
518
519     // Enable breathing interrupt
520     TIMSK1 |= _BV(OCIE1A);
521 }
522
523 void breathing_pulse(void)
524 {
525     if (get_backlight_level() == 0)
526     {
527         breathing_index = 0;
528     }
529     else
530     {
531         // Set breathing_index to be at the midpoint + 1 (brightest point)
532         breathing_index = 0x21 << breath_speed;
533     }
534
535     breathing_halt = BREATHING_HALT_ON;
536
537     // Enable breathing interrupt
538     TIMSK1 |= _BV(OCIE1A);
539 }
540
541 void breathing_disable(void)
542 {
543     // Disable breathing interrupt
544     TIMSK1 &= ~_BV(OCIE1A);
545     backlight_set(get_backlight_level());
546 }
547
548 void breathing_self_disable(void)
549 {
550     if (get_backlight_level() == 0)
551     {
552         breathing_halt = BREATHING_HALT_OFF;
553     }
554     else
555     {
556         breathing_halt = BREATHING_HALT_ON;
557     }
558
559     //backlight_set(get_backlight_level());
560 }
561
562 void breathing_toggle(void)
563 {
564     if (!is_breathing())
565     {
566         if (get_backlight_level() == 0)
567         {
568             breathing_index = 0;
569         }
570         else
571         {
572             // Set breathing_index to be at the midpoint + 1 (brightest point)
573             breathing_index = 0x21 << breath_speed;
574         }
575
576         breathing_halt = BREATHING_NO_HALT;
577     }
578
579     // Toggle breathing interrupt
580     TIMSK1 ^= _BV(OCIE1A);
581
582     // Restore backlight level
583     if (!is_breathing())
584     {
585         backlight_set(get_backlight_level());
586     }
587 }
588
589 bool is_breathing(void)
590 {
591     return (TIMSK1 && _BV(OCIE1A));
592 }
593
594 void breathing_intensity_default(void)
595 {
596     //breath_intensity = (uint8_t)((uint16_t)100 * (uint16_t)get_backlight_level() / (uint16_t)BACKLIGHT_LEVELS);
597     breath_intensity = ((BACKLIGHT_LEVELS - get_backlight_level()) * ((BACKLIGHT_LEVELS + 1) / 2));
598 }
599
600 void breathing_intensity_set(uint8_t value)
601 {
602     breath_intensity = value;
603 }
604
605 void breathing_speed_default(void)
606 {
607     breath_speed = 4;
608 }
609
610 void breathing_speed_set(uint8_t value)
611 {
612     bool is_breathing_now = is_breathing();
613     uint8_t old_breath_speed = breath_speed;
614
615     if (is_breathing_now)
616     {
617         // Disable breathing interrupt
618         TIMSK1 &= ~_BV(OCIE1A);
619     }
620
621     breath_speed = value;
622
623     if (is_breathing_now)
624     {
625         // Adjust index to account for new speed
626         breathing_index = (( (uint8_t)( (breathing_index) >> old_breath_speed ) ) & 0x3F) << breath_speed;
627
628         // Enable breathing interrupt
629         TIMSK1 |= _BV(OCIE1A);
630     }
631
632 }
633
634 void breathing_speed_inc(uint8_t value)
635 {
636     if ((uint16_t)(breath_speed - value) > 10 )
637     {
638         breathing_speed_set(0);
639     }
640     else
641     {
642         breathing_speed_set(breath_speed - value);
643     }
644 }
645
646 void breathing_speed_dec(uint8_t value)
647 {
648     if ((uint16_t)(breath_speed + value) > 10 )
649     {
650         breathing_speed_set(10);
651     }
652     else
653     {
654         breathing_speed_set(breath_speed + value);
655     }
656 }
657
658 void breathing_defaults(void)
659 {
660     breathing_intensity_default();
661     breathing_speed_default();
662     breathing_halt = BREATHING_NO_HALT;
663 }
664
665 /* Breathing Sleep LED brighness(PWM On period) table
666  * (64[steps] * 4[duration]) / 64[PWM periods/s] = 4 second breath cycle
667  *
668  * http://www.wolframalpha.com/input/?i=%28sin%28+x%2F64*pi%29**8+*+255%2C+x%3D0+to+63
669  * (0..63).each {|x| p ((sin(x/64.0*PI)**8)*255).to_i }
670  */
671 static const uint8_t breathing_table[64] PROGMEM = {
672   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,   1,   2,   4,   6,  10,
673  15,  23,  32,  44,  58,  74,  93, 113, 135, 157, 179, 199, 218, 233, 245, 252,
674 255, 252, 245, 233, 218, 199, 179, 157, 135, 113,  93,  74,  58,  44,  32,  23,
675  15,  10,   6,   4,   2,   1,   0,   0,   0,   0,   0,   0,   0,   0,   0,   0,
676 };
677
678 ISR(TIMER1_COMPA_vect)
679 {
680     // OCR1x = (pgm_read_byte(&breathing_table[ ( (uint8_t)( (breathing_index++) >> breath_speed ) ) & 0x3F ] )) * breath_intensity;
681
682
683     uint8_t local_index = ( (uint8_t)( (breathing_index++) >> breath_speed ) ) & 0x3F;
684
685     if (((breathing_halt == BREATHING_HALT_ON) && (local_index == 0x20)) || ((breathing_halt == BREATHING_HALT_OFF) && (local_index == 0x3F)))
686     {
687         // Disable breathing interrupt
688         TIMSK1 &= ~_BV(OCIE1A);
689     }
690
691     OCR1x = (uint16_t)(((uint16_t)pgm_read_byte(&breathing_table[local_index]) * 257)) >> breath_intensity;
692
693 }
694
695
696
697 #endif // breathing
698
699 #else // backlight
700
701 __attribute__ ((weak))
702 void backlight_init_ports(void)
703 {
704
705 }
706
707 __attribute__ ((weak))
708 void backlight_set(uint8_t level)
709 {
710
711 }
712
713 #endif // backlight
714
715
716
717 __attribute__ ((weak))
718 void led_set_user(uint8_t usb_led) {
719
720 }
721
722 __attribute__ ((weak))
723 void led_set_kb(uint8_t usb_led) {
724     led_set_user(usb_led);
725 }
726
727 __attribute__ ((weak))
728 void led_init_ports(void)
729 {
730
731 }
732
733 __attribute__ ((weak))
734 void led_set(uint8_t usb_led)
735 {
736
737   // Example LED Code
738   //
739     // // Using PE6 Caps Lock LED
740     // if (usb_led & (1<<USB_LED_CAPS_LOCK))
741     // {
742     //     // Output high.
743     //     DDRE |= (1<<6);
744     //     PORTE |= (1<<6);
745     // }
746     // else
747     // {
748     //     // Output low.
749     //     DDRE &= ~(1<<6);
750     //     PORTE &= ~(1<<6);
751     // }
752
753   led_set_kb(usb_led);
754 }
755
756
757 //------------------------------------------------------------------------------
758 // Override these functions in your keymap file to play different tunes on
759 // different events such as startup and bootloader jump
760
761 __attribute__ ((weak))
762 void startup_user() {}
763
764 __attribute__ ((weak))
765 void shutdown_user() {}
766
767 //------------------------------------------------------------------------------