aboutsummaryrefslogtreecommitdiff
path: root/quantum
diff options
context:
space:
mode:
Diffstat (limited to 'quantum')
-rw-r--r--quantum/config_common.h80
-rw-r--r--quantum/keymap.h12
-rw-r--r--quantum/led.c54
-rw-r--r--quantum/matrix.c48
-rw-r--r--quantum/quantum.c346
-rw-r--r--quantum/quantum.h30
-rw-r--r--quantum/template/Makefile24
-rw-r--r--quantum/template/config.h6
-rw-r--r--quantum/template/keymaps/default/Makefile21
-rw-r--r--quantum/template/keymaps/default/config.h8
-rw-r--r--quantum/template/keymaps/default/keymap.c20
-rw-r--r--quantum/template/keymaps/default/readme.md1
-rw-r--r--quantum/template/readme.md (renamed from quantum/template/README.md)14
-rw-r--r--quantum/template/template.c84
-rw-r--r--quantum/template/template.h13
-rw-r--r--quantum/tools/readme.md (renamed from quantum/tools/README.md)0
16 files changed, 534 insertions, 227 deletions
diff --git a/quantum/config_common.h b/quantum/config_common.h
index 02f11d979..09a4fe701 100644
--- a/quantum/config_common.h
+++ b/quantum/config_common.h
@@ -5,46 +5,46 @@
5#define COL2ROW 0 5#define COL2ROW 0
6#define ROW2COL 1 6#define ROW2COL 1
7/* I/O pins */ 7/* I/O pins */
8#define B0 { .input_addr = 3, .bit = 0 } 8#define B0 0x30
9#define B1 { .input_addr = 3, .bit = 1 } 9#define B1 0x31
10#define B2 { .input_addr = 3, .bit = 2 } 10#define B2 0x32
11#define B3 { .input_addr = 3, .bit = 3 } 11#define B3 0x33
12#define B4 { .input_addr = 3, .bit = 4 } 12#define B4 0x34
13#define B5 { .input_addr = 3, .bit = 5 } 13#define B5 0x35
14#define B6 { .input_addr = 3, .bit = 6 } 14#define B6 0x36
15#define B7 { .input_addr = 3, .bit = 7 } 15#define B7 0x37
16#define C0 { .input_addr = 6, .bit = 0 } 16#define C0 0x60
17#define C1 { .input_addr = 6, .bit = 1 } 17#define C1 0x61
18#define C2 { .input_addr = 6, .bit = 2 } 18#define C2 0x62
19#define C3 { .input_addr = 6, .bit = 3 } 19#define C3 0x63
20#define C4 { .input_addr = 6, .bit = 4 } 20#define C4 0x64
21#define C5 { .input_addr = 6, .bit = 5 } 21#define C5 0x65
22#define C6 { .input_addr = 6, .bit = 6 } 22#define C6 0x66
23#define C7 { .input_addr = 6, .bit = 7 } 23#define C7 0x67
24#define D0 { .input_addr = 9, .bit = 0 } 24#define D0 0x90
25#define D1 { .input_addr = 9, .bit = 1 } 25#define D1 0x91
26#define D2 { .input_addr = 9, .bit = 2 } 26#define D2 0x92
27#define D3 { .input_addr = 9, .bit = 3 } 27#define D3 0x93
28#define D4 { .input_addr = 9, .bit = 4 } 28#define D4 0x94
29#define D5 { .input_addr = 9, .bit = 5 } 29#define D5 0x95
30#define D6 { .input_addr = 9, .bit = 6 } 30#define D6 0x96
31#define D7 { .input_addr = 9, .bit = 7 } 31#define D7 0x97
32#define E0 { .input_addr = 0xC, .bit = 0 } 32#define E0 0xC0
33#define E1 { .input_addr = 0xC, .bit = 1 } 33#define E1 0xC1
34#define E2 { .input_addr = 0xC, .bit = 2 } 34#define E2 0xC2
35#define E3 { .input_addr = 0xC, .bit = 3 } 35#define E3 0xC3
36#define E4 { .input_addr = 0xC, .bit = 4 } 36#define E4 0xC4
37#define E5 { .input_addr = 0xC, .bit = 5 } 37#define E5 0xC5
38#define E6 { .input_addr = 0xC, .bit = 6 } 38#define E6 0xC6
39#define E7 { .input_addr = 0xC, .bit = 7 } 39#define E7 0xC7
40#define F0 { .input_addr = 0xF, .bit = 0 } 40#define F0 0xF0
41#define F1 { .input_addr = 0xF, .bit = 1 } 41#define F1 0xF1
42#define F2 { .input_addr = 0xF, .bit = 2 } 42#define F2 0xF2
43#define F3 { .input_addr = 0xF, .bit = 3 } 43#define F3 0xF3
44#define F4 { .input_addr = 0xF, .bit = 4 } 44#define F4 0xF4
45#define F5 { .input_addr = 0xF, .bit = 5 } 45#define F5 0xF5
46#define F6 { .input_addr = 0xF, .bit = 6 } 46#define F6 0xF6
47#define F7 { .input_addr = 0xF, .bit = 7 } 47#define F7 0xF7
48 48
49/* USART configuration */ 49/* USART configuration */
50#ifdef BLUETOOTH_ENABLE 50#ifdef BLUETOOTH_ENABLE
diff --git a/quantum/keymap.h b/quantum/keymap.h
index 6ac3d2ace..41fa394ab 100644
--- a/quantum/keymap.h
+++ b/quantum/keymap.h
@@ -125,8 +125,8 @@ enum quantum_keycodes {
125 MUV_DE, 125 MUV_DE,
126 126
127 // Midi mode on/off 127 // Midi mode on/off
128 MI_ON, 128 MIDI_ON,
129 MI_OFF, 129 MIDI_OFF,
130 130
131 // Backlight functionality 131 // Backlight functionality
132 BL_0, 132 BL_0,
@@ -154,7 +154,10 @@ enum quantum_keycodes {
154 KC_LSPO, 154 KC_LSPO,
155 155
156 // Right shift, close paren 156 // Right shift, close paren
157 KC_RSPC 157 KC_RSPC,
158
159 // always leave at the end
160 SAFE_RANGE
158}; 161};
159 162
160// Ability to use mods in layouts 163// Ability to use mods in layouts
@@ -266,6 +269,9 @@ enum quantum_keycodes {
266#define BL_ON BL_9 269#define BL_ON BL_9
267#define BL_OFF BL_0 270#define BL_OFF BL_0
268 271
272#define MI_ON MIDI_ON
273#define MI_OFF MIDI_OFF
274
269// GOTO layer - 16 layers max 275// GOTO layer - 16 layers max
270// when: 276// when:
271// ON_PRESS = 1 277// ON_PRESS = 1
diff --git a/quantum/led.c b/quantum/led.c
deleted file mode 100644
index 2634ab2f6..000000000
--- a/quantum/led.c
+++ /dev/null
@@ -1,54 +0,0 @@
1/*
2Copyright 2012 Jun Wako <wakojun@gmail.com>
3
4This program is free software: you can redistribute it and/or modify
5it under the terms of the GNU General Public License as published by
6the Free Software Foundation, either version 2 of the License, or
7(at your option) any later version.
8
9This program is distributed in the hope that it will be useful,
10but WITHOUT ANY WARRANTY; without even the implied warranty of
11MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12GNU General Public License for more details.
13
14You should have received a copy of the GNU General Public License
15along with this program. If not, see <http://www.gnu.org/licenses/>.
16*/
17
18#include <avr/io.h>
19#include "stdint.h"
20#include "led.h"
21
22__attribute__ ((weak))
23void led_set_kb(uint8_t usb_led) {
24
25}
26
27__attribute__ ((weak))
28void led_init_ports(void)
29{
30
31}
32
33__attribute__ ((weak))
34void led_set(uint8_t usb_led)
35{
36
37 // Example LED Code
38 //
39 // // Using PE6 Caps Lock LED
40 // if (usb_led & (1<<USB_LED_CAPS_LOCK))
41 // {
42 // // Output high.
43 // DDRE |= (1<<6);
44 // PORTE |= (1<<6);
45 // }
46 // else
47 // {
48 // // Output low.
49 // DDRE &= ~(1<<6);
50 // PORTE &= ~(1<<6);
51 // }
52
53 led_set_kb(usb_led);
54}
diff --git a/quantum/matrix.c b/quantum/matrix.c
index 4f1564ac8..6e9f92727 100644
--- a/quantum/matrix.c
+++ b/quantum/matrix.c
@@ -32,8 +32,8 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
32# define DEBOUNCING_DELAY 5 32# define DEBOUNCING_DELAY 5
33#endif 33#endif
34 34
35static const io_pin_t row_pins[MATRIX_ROWS] = MATRIX_ROW_PINS; 35static const uint8_t row_pins[MATRIX_ROWS] = MATRIX_ROW_PINS;
36static const io_pin_t col_pins[MATRIX_COLS] = MATRIX_COL_PINS; 36static const uint8_t col_pins[MATRIX_COLS] = MATRIX_COL_PINS;
37/* matrix state */ 37/* matrix state */
38#if DIODE_DIRECTION == COL2ROW 38#if DIODE_DIRECTION == COL2ROW
39static matrix_row_t matrix[MATRIX_ROWS]; 39static matrix_row_t matrix[MATRIX_ROWS];
@@ -52,10 +52,30 @@ static matrix_col_t read_rows(void);
52 52
53__attribute__ ((weak)) 53__attribute__ ((weak))
54void matrix_init_quantum(void) { 54void matrix_init_quantum(void) {
55 matrix_init_kb();
55} 56}
56 57
57__attribute__ ((weak)) 58__attribute__ ((weak))
58void matrix_scan_quantum(void) { 59void matrix_scan_quantum(void) {
60 matrix_scan_kb();
61}
62
63__attribute__ ((weak))
64void matrix_init_kb(void) {
65 matrix_init_user();
66}
67
68__attribute__ ((weak))
69void matrix_scan_kb(void) {
70 matrix_scan_user();
71}
72
73__attribute__ ((weak))
74void matrix_init_user(void) {
75}
76
77__attribute__ ((weak))
78void matrix_scan_user(void) {
59} 79}
60 80
61uint8_t matrix_rows(void) { 81uint8_t matrix_rows(void) {
@@ -70,22 +90,22 @@ void matrix_power_up(void) {
70#if DIODE_DIRECTION == COL2ROW 90#if DIODE_DIRECTION == COL2ROW
71 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) { 91 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) {
72 /* DDRxn */ 92 /* DDRxn */
73 _SFR_IO8(row_pins[r].input_addr + 1) |= _BV(row_pins[r].bit); 93 _SFR_IO8((row_pins[r] >> 4) + 1) |= _BV(row_pins[r] & 0xF);
74 toggle_row(r); 94 toggle_row(r);
75 } 95 }
76 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) { 96 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) {
77 /* PORTxn */ 97 /* PORTxn */
78 _SFR_IO8(col_pins[c].input_addr + 2) |= _BV(col_pins[c].bit); 98 _SFR_IO8((col_pins[c] >> 4) + 2) |= _BV(col_pins[c] & 0xF);
79 } 99 }
80#else 100#else
81 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) { 101 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) {
82 /* DDRxn */ 102 /* DDRxn */
83 _SFR_IO8(col_pins[c].input_addr + 1) |= _BV(col_pins[c].bit); 103 _SFR_IO8((col_pins[c] >> 4) + 1) |= _BV(col_pins[c] & 0xF);
84 toggle_col(c); 104 toggle_col(c);
85 } 105 }
86 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) { 106 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) {
87 /* PORTxn */ 107 /* PORTxn */
88 _SFR_IO8(row_pins[r].input_addr + 2) |= _BV(row_pins[r].bit); 108 _SFR_IO8((row_pins[r] >> 4) + 2) |= _BV(row_pins[r] & 0xF);
89 } 109 }
90#endif 110#endif
91} 111}
@@ -100,22 +120,22 @@ void matrix_init(void) {
100#if DIODE_DIRECTION == COL2ROW 120#if DIODE_DIRECTION == COL2ROW
101 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) { 121 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) {
102 /* DDRxn */ 122 /* DDRxn */
103 _SFR_IO8(row_pins[r].input_addr + 1) |= _BV(row_pins[r].bit); 123 _SFR_IO8((row_pins[r] >> 4) + 1) |= _BV(row_pins[r] & 0xF);
104 toggle_row(r); 124 toggle_row(r);
105 } 125 }
106 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) { 126 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) {
107 /* PORTxn */ 127 /* PORTxn */
108 _SFR_IO8(col_pins[c].input_addr + 2) |= _BV(col_pins[c].bit); 128 _SFR_IO8((col_pins[c] >> 4) + 2) |= _BV(col_pins[c] & 0xF);
109 } 129 }
110#else 130#else
111 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) { 131 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) {
112 /* DDRxn */ 132 /* DDRxn */
113 _SFR_IO8(col_pins[c].input_addr + 1) |= _BV(col_pins[c].bit); 133 _SFR_IO8((col_pins[c] >> 4) + 1) |= _BV(col_pins[c] & 0xF);
114 toggle_col(c); 134 toggle_col(c);
115 } 135 }
116 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) { 136 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) {
117 /* PORTxn */ 137 /* PORTxn */
118 _SFR_IO8(row_pins[r].input_addr + 2) |= _BV(row_pins[r].bit); 138 _SFR_IO8((row_pins[r] >> 4) + 2) |= _BV(row_pins[r] & 0xF);
119 } 139 }
120#endif 140#endif
121 matrix_init_quantum(); 141 matrix_init_quantum();
@@ -151,14 +171,14 @@ uint8_t matrix_scan(void) {
151 171
152static void toggle_row(uint8_t row) { 172static void toggle_row(uint8_t row) {
153 /* PINxn */ 173 /* PINxn */
154 _SFR_IO8(row_pins[row].input_addr) = _BV(row_pins[row].bit); 174 _SFR_IO8((row_pins[row] >> 4)) = _BV(row_pins[row] & 0xF);
155} 175}
156 176
157static matrix_row_t read_cols(void) { 177static matrix_row_t read_cols(void) {
158 matrix_row_t state = 0; 178 matrix_row_t state = 0;
159 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) { 179 for (int8_t c = MATRIX_COLS - 1; c >= 0; --c) {
160 /* PINxn */ 180 /* PINxn */
161 if (!(_SFR_IO8(col_pins[c].input_addr) & _BV(col_pins[c].bit))) { 181 if (!(_SFR_IO8((col_pins[c] >> 4)) & _BV(col_pins[c] & 0xF))) {
162 state |= (matrix_row_t)1 << c; 182 state |= (matrix_row_t)1 << c;
163 } 183 }
164 } 184 }
@@ -199,14 +219,14 @@ uint8_t matrix_scan(void) {
199 219
200static void toggle_col(uint8_t col) { 220static void toggle_col(uint8_t col) {
201 /* PINxn */ 221 /* PINxn */
202 _SFR_IO8(col_pins[col].input_addr) = _BV(col_pins[col].bit); 222 _SFR_IO8((col_pins[col] >> 4)) = _BV(col_pins[col] & 0xF);
203} 223}
204 224
205static matrix_col_t read_rows(void) { 225static matrix_col_t read_rows(void) {
206 matrix_col_t state = 0; 226 matrix_col_t state = 0;
207 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) { 227 for (int8_t r = MATRIX_ROWS - 1; r >= 0; --r) {
208 /* PINxn */ 228 /* PINxn */
209 if (!(_SFR_IO8(row_pins[r].input_addr) & _BV(row_pins[r].bit))) { 229 if (!(_SFR_IO8((row_pins[r] >> 4)) & _BV(row_pins[r] & 0xF))) {
210 state |= (matrix_col_t)1 << r; 230 state |= (matrix_col_t)1 << r;
211 } 231 }
212 } 232 }
diff --git a/quantum/quantum.c b/quantum/quantum.c
index 006464e5a..3f2edfc92 100644
--- a/quantum/quantum.c
+++ b/quantum/quantum.c
@@ -655,6 +655,9 @@ void update_tri_layer(uint8_t layer1, uint8_t layer2, uint8_t layer3) {
655} 655}
656 656
657void matrix_init_quantum() { 657void matrix_init_quantum() {
658 #ifdef BACKLIGHT_ENABLE
659 backlight_init_ports();
660 #endif
658 matrix_init_kb(); 661 matrix_init_kb();
659} 662}
660 663
@@ -673,6 +676,7 @@ void matrix_scan_quantum() {
673 676
674 matrix_scan_kb(); 677 matrix_scan_kb();
675} 678}
679
676#ifdef AUDIO_ENABLE 680#ifdef AUDIO_ENABLE
677 bool is_music_on(void) { 681 bool is_music_on(void) {
678 return (music_activated != 0); 682 return (music_activated != 0);
@@ -698,6 +702,348 @@ void matrix_scan_quantum() {
698 702
699#endif 703#endif
700 704
705
706#if defined(BACKLIGHT_ENABLE) && defined(BACKLIGHT_PIN)
707
708static const uint8_t backlight_pin = BACKLIGHT_PIN;
709
710#if BACKLIGHT_PIN == B7
711# define COM1x1 COM1C1
712# define OCR1x OCR1C
713#elif BACKLIGHT_PIN == B6
714# define COM1x1 COM1B1
715# define OCR1x OCR1B
716#elif BACKLIGHT_PIN == B5
717# define COM1x1 COM1A1
718# define OCR1x OCR1A
719#else
720# error "Backlight pin not supported - use B5, B6, or B7"
721#endif
722
723__attribute__ ((weak))
724void backlight_init_ports(void)
725{
726
727 // Setup backlight pin as output and output low.
728 // DDRx |= n
729 _SFR_IO8((backlight_pin >> 4) + 1) |= _BV(backlight_pin & 0xF);
730 // PORTx &= ~n
731 _SFR_IO8((backlight_pin >> 4) + 2) &= ~_BV(backlight_pin & 0xF);
732
733 // Use full 16-bit resolution.
734 ICR1 = 0xFFFF;
735
736 // I could write a wall of text here to explain... but TL;DW
737 // Go read the ATmega32u4 datasheet.
738 // And this: http://blog.saikoled.com/post/43165849837/secret-konami-cheat-code-to-high-resolution-pwm-on
739
740 // Pin PB7 = OCR1C (Timer 1, Channel C)
741 // Compare Output Mode = Clear on compare match, Channel C = COM1C1=1 COM1C0=0
742 // (i.e. start high, go low when counter matches.)
743 // WGM Mode 14 (Fast PWM) = WGM13=1 WGM12=1 WGM11=1 WGM10=0
744 // Clock Select = clk/1 (no prescaling) = CS12=0 CS11=0 CS10=1
745
746 TCCR1A = _BV(COM1x1) | _BV(WGM11); // = 0b00001010;
747 TCCR1B = _BV(WGM13) | _BV(WGM12) | _BV(CS10); // = 0b00011001;
748
749 backlight_init();
750 #ifdef BACKLIGHT_BREATHING
751 breathing_defaults();
752 #endif
753}
754
755__attribute__ ((weak))
756void backlight_set(uint8_t level)
757{
758 // Prevent backlight blink on lowest level
759 // PORTx &= ~n
760 _SFR_IO8((backlight_pin >> 4) + 2) &= ~_BV(backlight_pin & 0xF);
761
762 if ( level == 0 ) {
763 // Turn off PWM control on backlight pin, revert to output low.
764 TCCR1A &= ~(_BV(COM1x1));
765 OCR1x = 0x0;
766 } else if ( level == BACKLIGHT_LEVELS ) {
767 // Turn on PWM control of backlight pin
768 TCCR1A |= _BV(COM1x1);
769 // Set the brightness
770 OCR1x = 0xFFFF;
771 } else {
772 // Turn on PWM control of backlight pin
773 TCCR1A |= _BV(COM1x1);
774 // Set the brightness
775 OCR1x = 0xFFFF >> ((BACKLIGHT_LEVELS - level) * ((BACKLIGHT_LEVELS + 1) / 2));
776 }
777
778 #ifdef BACKLIGHT_BREATHING
779 breathing_intensity_default();
780 #endif
781}
782
783
784#ifdef BACKLIGHT_BREATHING
785
786#define BREATHING_NO_HALT 0
787#define BREATHING_HALT_OFF 1
788#define BREATHING_HALT_ON 2
789
790static uint8_t breath_intensity;
791static uint8_t breath_speed;
792static uint16_t breathing_index;
793static uint8_t breathing_halt;
794
795void breathing_enable(void)
796{
797 if (get_backlight_level() == 0)
798 {
799 breathing_index = 0;
800 }
801 else
802 {
803 // Set breathing_index to be at the midpoint (brightest point)
804 breathing_index = 0x20 << breath_speed;
805 }
806
807 breathing_halt = BREATHING_NO_HALT;
808
809 // Enable breathing interrupt
810 TIMSK1 |= _BV(OCIE1A);
811}
812
813void breathing_pulse(void)
814{
815 if (get_backlight_level() == 0)
816 {
817 breathing_index = 0;
818 }
819 else
820 {
821 // Set breathing_index to be at the midpoint + 1 (brightest point)
822 breathing_index = 0x21 << breath_speed;
823 }
824
825 breathing_halt = BREATHING_HALT_ON;
826
827 // Enable breathing interrupt
828 TIMSK1 |= _BV(OCIE1A);
829}
830
831void breathing_disable(void)
832{
833 // Disable breathing interrupt
834 TIMSK1 &= ~_BV(OCIE1A);
835 backlight_set(get_backlight_level());
836}
837
838void breathing_self_disable(void)
839{
840 if (get_backlight_level() == 0)
841 {
842 breathing_halt = BREATHING_HALT_OFF;
843 }
844 else
845 {
846 breathing_halt = BREATHING_HALT_ON;
847 }
848
849 //backlight_set(get_backlight_level());
850}
851
852void breathing_toggle(void)
853{
854 if (!is_breathing())
855 {
856 if (get_backlight_level() == 0)
857 {
858 breathing_index = 0;
859 }
860 else
861 {
862 // Set breathing_index to be at the midpoint + 1 (brightest point)
863 breathing_index = 0x21 << breath_speed;
864 }
865
866 breathing_halt = BREATHING_NO_HALT;
867 }
868
869 // Toggle breathing interrupt
870 TIMSK1 ^= _BV(OCIE1A);
871
872 // Restore backlight level
873 if (!is_breathing())
874 {
875 backlight_set(get_backlight_level());
876 }
877}
878
879bool is_breathing(void)
880{
881 return (TIMSK1 && _BV(OCIE1A));
882}
883
884void breathing_intensity_default(void)
885{
886 //breath_intensity = (uint8_t)((uint16_t)100 * (uint16_t)get_backlight_level() / (uint16_t)BACKLIGHT_LEVELS);
887 breath_intensity = ((BACKLIGHT_LEVELS - get_backlight_level()) * ((BACKLIGHT_LEVELS + 1) / 2));
888}
889
890void breathing_intensity_set(uint8_t value)
891{
892 breath_intensity = value;
893}
894
895void breathing_speed_default(void)
896{
897 breath_speed = 4;
898}
899
900void breathing_speed_set(uint8_t value)
901{
902 bool is_breathing_now = is_breathing();
903 uint8_t old_breath_speed = breath_speed;
904
905 if (is_breathing_now)
906 {
907 // Disable breathing interrupt
908 TIMSK1 &= ~_BV(OCIE1A);
909 }
910
911 breath_speed = value;
912
913 if (is_breathing_now)
914 {
915 // Adjust index to account for new speed
916 breathing_index = (( (uint8_t)( (breathing_index) >> old_breath_speed ) ) & 0x3F) << breath_speed;
917
918 // Enable breathing interrupt
919 TIMSK1 |= _BV(OCIE1A);
920 }
921
922}
923
924void breathing_speed_inc(uint8_t value)
925{
926 if ((uint16_t)(breath_speed - value) > 10 )
927 {
928 breathing_speed_set(0);
929 }
930 else
931 {
932 breathing_speed_set(breath_speed - value);
933 }
934}
935
936void breathing_speed_dec(uint8_t value)
937{
938 if ((uint16_t)(breath_speed + value) > 10 )
939 {
940 breathing_speed_set(10);
941 }
942 else
943 {
944 breathing_speed_set(breath_speed + value);
945 }
946}
947
948void breathing_defaults(void)
949{
950 breathing_intensity_default();
951 breathing_speed_default();
952 breathing_halt = BREATHING_NO_HALT;
953}
954
955/* Breathing Sleep LED brighness(PWM On period) table
956 * (64[steps] * 4[duration]) / 64[PWM periods/s] = 4 second breath cycle
957 *
958 * http://www.wolframalpha.com/input/?i=%28sin%28+x%2F64*pi%29**8+*+255%2C+x%3D0+to+63
959 * (0..63).each {|x| p ((sin(x/64.0*PI)**8)*255).to_i }
960 */
961static const uint8_t breathing_table[64] PROGMEM = {
962 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 2, 4, 6, 10,
963 15, 23, 32, 44, 58, 74, 93, 113, 135, 157, 179, 199, 218, 233, 245, 252,
964255, 252, 245, 233, 218, 199, 179, 157, 135, 113, 93, 74, 58, 44, 32, 23,
965 15, 10, 6, 4, 2, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
966};
967
968ISR(TIMER1_COMPA_vect)
969{
970 // OCR1x = (pgm_read_byte(&breathing_table[ ( (uint8_t)( (breathing_index++) >> breath_speed ) ) & 0x3F ] )) * breath_intensity;
971
972
973 uint8_t local_index = ( (uint8_t)( (breathing_index++) >> breath_speed ) ) & 0x3F;
974
975 if (((breathing_halt == BREATHING_HALT_ON) && (local_index == 0x20)) || ((breathing_halt == BREATHING_HALT_OFF) && (local_index == 0x3F)))
976 {
977 // Disable breathing interrupt
978 TIMSK1 &= ~_BV(OCIE1A);
979 }
980
981 OCR1x = (uint16_t)(((uint16_t)pgm_read_byte(&breathing_table[local_index]) * 257)) >> breath_intensity;
982
983}
984
985
986
987#endif // breathing
988
989#else // backlight
990
991__attribute__ ((weak))
992void backlight_init_ports(void)
993{
994
995}
996
997__attribute__ ((weak))
998void backlight_set(uint8_t level)
999{
1000
1001}
1002
1003#endif // backlight
1004
1005
1006
1007__attribute__ ((weak))
1008void led_set_user(uint8_t usb_led) {
1009
1010}
1011
1012__attribute__ ((weak))
1013void led_set_kb(uint8_t usb_led) {
1014 led_set_user(usb_led);
1015}
1016
1017__attribute__ ((weak))
1018void led_init_ports(void)
1019{
1020
1021}
1022
1023__attribute__ ((weak))
1024void led_set(uint8_t usb_led)
1025{
1026
1027 // Example LED Code
1028 //
1029 // // Using PE6 Caps Lock LED
1030 // if (usb_led & (1<<USB_LED_CAPS_LOCK))
1031 // {
1032 // // Output high.
1033 // DDRE |= (1<<6);
1034 // PORTE |= (1<<6);
1035 // }
1036 // else
1037 // {
1038 // // Output low.
1039 // DDRE &= ~(1<<6);
1040 // PORTE &= ~(1<<6);
1041 // }
1042
1043 led_set_kb(usb_led);
1044}
1045
1046
701//------------------------------------------------------------------------------ 1047//------------------------------------------------------------------------------
702// Override these functions in your keymap file to play different tunes on 1048// Override these functions in your keymap file to play different tunes on
703// different events such as startup and bootloader jump 1049// different events such as startup and bootloader jump
diff --git a/quantum/quantum.h b/quantum/quantum.h
index 1f78f3717..7795294d5 100644
--- a/quantum/quantum.h
+++ b/quantum/quantum.h
@@ -27,6 +27,10 @@
27#include <util/delay.h> 27#include <util/delay.h>
28#include "bootloader.h" 28#include "bootloader.h"
29#include "timer.h" 29#include "timer.h"
30#include "config_common.h"
31#include <avr/interrupt.h>
32#include "led.h"
33#include "action_util.h"
30 34
31extern uint32_t default_layer_state; 35extern uint32_t default_layer_state;
32 36
@@ -74,6 +78,8 @@ void update_tri_layer(uint8_t layer1, uint8_t layer2, uint8_t layer3);
74 78
75void matrix_init_kb(void); 79void matrix_init_kb(void);
76void matrix_scan_kb(void); 80void matrix_scan_kb(void);
81void matrix_init_user(void);
82void matrix_scan_user(void);
77bool process_action_kb(keyrecord_t *record); 83bool process_action_kb(keyrecord_t *record);
78bool process_record_kb(uint16_t keycode, keyrecord_t *record); 84bool process_record_kb(uint16_t keycode, keyrecord_t *record);
79bool process_record_user(uint16_t keycode, keyrecord_t *record); 85bool process_record_user(uint16_t keycode, keyrecord_t *record);
@@ -89,4 +95,28 @@ void audio_on_user(void);
89void music_on_user(void); 95void music_on_user(void);
90void music_scale_user(void); 96void music_scale_user(void);
91 97
98#ifdef BACKLIGHT_ENABLE
99void backlight_init_ports(void);
100
101#ifdef BACKLIGHT_BREATHING
102void breathing_enable(void);
103void breathing_pulse(void);
104void breathing_disable(void);
105void breathing_self_disable(void);
106void breathing_toggle(void);
107bool is_breathing(void);
108
109void breathing_defaults(void);
110void breathing_intensity_default(void);
111void breathing_speed_default(void);
112void breathing_speed_set(uint8_t value);
113void breathing_speed_inc(uint8_t value);
114void breathing_speed_dec(uint8_t value);
115#endif
116
117#endif
118
119void led_set_user(uint8_t usb_led);
120void led_set_kb(uint8_t usb_led);
121
92#endif 122#endif
diff --git a/quantum/template/Makefile b/quantum/template/Makefile
index 87e4c2d2b..3f6d133c9 100644
--- a/quantum/template/Makefile
+++ b/quantum/template/Makefile
@@ -53,20 +53,20 @@ OPT_DEFS += -DBOOTLOADER_SIZE=512
53# Build Options 53# Build Options
54# change yes to no to disable 54# change yes to no to disable
55# 55#
56BOOTMAGIC_ENABLE = no # Virtual DIP switch configuration(+1000) 56BOOTMAGIC_ENABLE ?= no # Virtual DIP switch configuration(+1000)
57MOUSEKEY_ENABLE = yes # Mouse keys(+4700) 57MOUSEKEY_ENABLE ?= yes # Mouse keys(+4700)
58EXTRAKEY_ENABLE = yes # Audio control and System control(+450) 58EXTRAKEY_ENABLE ?= yes # Audio control and System control(+450)
59CONSOLE_ENABLE = yes # Console for debug(+400) 59CONSOLE_ENABLE ?= yes # Console for debug(+400)
60COMMAND_ENABLE = yes # Commands for debug and configuration 60COMMAND_ENABLE ?= yes # Commands for debug and configuration
61# Do not enable SLEEP_LED_ENABLE. it uses the same timer as BACKLIGHT_ENABLE 61# Do not enable SLEEP_LED_ENABLE. it uses the same timer as BACKLIGHT_ENABLE
62SLEEP_LED_ENABLE = no # Breathing sleep LED during USB suspend 62SLEEP_LED_ENABLE ?= no # Breathing sleep LED during USB suspend
63# if this doesn't work, see here: https://github.com/tmk/tmk_keyboard/wiki/FAQ#nkro-doesnt-work 63# if this doesn't work, see here: https://github.com/tmk/tmk_keyboard/wiki/FAQ#nkro-doesnt-work
64NKRO_ENABLE = no # USB Nkey Rollover 64NKRO_ENABLE ?= no # USB Nkey Rollover
65BACKLIGHT_ENABLE = no # Enable keyboard backlight functionality on B7 by default 65BACKLIGHT_ENABLE ?= no # Enable keyboard backlight functionality on B7 by default
66MIDI_ENABLE = no # MIDI controls 66MIDI_ENABLE ?= no # MIDI controls
67UNICODE_ENABLE = no # Unicode 67UNICODE_ENABLE ?= no # Unicode
68BLUETOOTH_ENABLE = no # Enable Bluetooth with the Adafruit EZ-Key HID 68BLUETOOTH_ENABLE ?= no # Enable Bluetooth with the Adafruit EZ-Key HID
69AUDIO_ENABLE = no # Audio output on port C6 69AUDIO_ENABLE ?= no # Audio output on port C6
70 70
71ifndef QUANTUM_DIR 71ifndef QUANTUM_DIR
72 include ../../Makefile 72 include ../../Makefile
diff --git a/quantum/template/config.h b/quantum/template/config.h
index cad3e3260..b02f0c7eb 100644
--- a/quantum/template/config.h
+++ b/quantum/template/config.h
@@ -48,6 +48,11 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
48 48
49/* COL2ROW or ROW2COL */ 49/* COL2ROW or ROW2COL */
50#define DIODE_DIRECTION COL2ROW 50#define DIODE_DIRECTION COL2ROW
51
52// #define BACKLIGHT_PIN B7
53// #define BACKLIGHT_BREATHING
54// #define BACKLIGHT_LEVELS 3
55
51 56
52/* Debounce reduces chatter (unintended double-presses) - set 0 if debouncing is not needed */ 57/* Debounce reduces chatter (unintended double-presses) - set 0 if debouncing is not needed */
53#define DEBOUNCING_DELAY 5 58#define DEBOUNCING_DELAY 5
@@ -56,7 +61,6 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
56//#define MATRIX_HAS_GHOST 61//#define MATRIX_HAS_GHOST
57 62
58/* number of backlight levels */ 63/* number of backlight levels */
59#define BACKLIGHT_LEVELS 3
60 64
61/* Mechanical locking support. Use KC_LCAP, KC_LNUM or KC_LSCR instead in keymap */ 65/* Mechanical locking support. Use KC_LCAP, KC_LNUM or KC_LSCR instead in keymap */
62#define LOCKING_SUPPORT_ENABLE 66#define LOCKING_SUPPORT_ENABLE
diff --git a/quantum/template/keymaps/default/Makefile b/quantum/template/keymaps/default/Makefile
new file mode 100644
index 000000000..f4671a9d1
--- /dev/null
+++ b/quantum/template/keymaps/default/Makefile
@@ -0,0 +1,21 @@
1# Build Options
2# change to "no" to disable the options, or define them in the Makefile in
3# the appropriate keymap folder that will get included automatically
4#
5BOOTMAGIC_ENABLE = no # Virtual DIP switch configuration(+1000)
6MOUSEKEY_ENABLE = yes # Mouse keys(+4700)
7EXTRAKEY_ENABLE = yes # Audio control and System control(+450)
8CONSOLE_ENABLE = no # Console for debug(+400)
9COMMAND_ENABLE = yes # Commands for debug and configuration
10NKRO_ENABLE = yes # Nkey Rollover - if this doesn't work, see here: https://github.com/tmk/tmk_keyboard/wiki/FAQ#nkro-doesnt-work
11BACKLIGHT_ENABLE = no # Enable keyboard backlight functionality
12MIDI_ENABLE = no # MIDI controls
13AUDIO_ENABLE = no # Audio output on port C6
14UNICODE_ENABLE = no # Unicode
15BLUETOOTH_ENABLE = no # Enable Bluetooth with the Adafruit EZ-Key HID
16RGBLIGHT_ENABLE = no # Enable WS2812 RGB underlight. Do not enable this with audio at the same time.
17SLEEP_LED_ENABLE = no # Breathing sleep LED during USB suspend
18
19ifndef QUANTUM_DIR
20 include ../../../../Makefile
21endif \ No newline at end of file
diff --git a/quantum/template/keymaps/default/config.h b/quantum/template/keymaps/default/config.h
new file mode 100644
index 000000000..df06a2620
--- /dev/null
+++ b/quantum/template/keymaps/default/config.h
@@ -0,0 +1,8 @@
1#ifndef CONFIG_USER_H
2#define CONFIG_USER_H
3
4#include "../../config.h"
5
6// place overrides here
7
8#endif \ No newline at end of file
diff --git a/quantum/template/keymaps/default/keymap.c b/quantum/template/keymaps/default/keymap.c
index 4121fd860..e28a4723e 100644
--- a/quantum/template/keymaps/default/keymap.c
+++ b/quantum/template/keymaps/default/keymap.c
@@ -1,6 +1,3 @@
1// This is the canonical layout file for the Quantum project. If you want to add another keyboard,
2// this is the style you want to emulate.
3
4#include "%KEYBOARD%.h" 1#include "%KEYBOARD%.h"
5 2
6const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = { 3const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
@@ -28,3 +25,20 @@ const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
28 } 25 }
29 return MACRO_NONE; 26 return MACRO_NONE;
30}; 27};
28
29
30void matrix_init_user(void) {
31
32}
33
34void matrix_scan_user(void) {
35
36}
37
38bool process_record_user(uint16_t keycode, keyrecord_t *record) {
39 return true;
40}
41
42void led_set_user(uint8_t usb_led) {
43
44} \ No newline at end of file
diff --git a/quantum/template/keymaps/default/readme.md b/quantum/template/keymaps/default/readme.md
new file mode 100644
index 000000000..21aa663d5
--- /dev/null
+++ b/quantum/template/keymaps/default/readme.md
@@ -0,0 +1 @@
# The default keymap for %KEYBOARD% \ No newline at end of file
diff --git a/quantum/template/README.md b/quantum/template/readme.md
index d6b0ac936..b2fb4dd98 100644
--- a/quantum/template/README.md
+++ b/quantum/template/readme.md
@@ -3,7 +3,7 @@
3 3
4## Quantum MK Firmware 4## Quantum MK Firmware
5 5
6For the full Quantum feature list, see [the parent README.md](/doc/README.md). 6For the full Quantum feature list, see [the parent readme.md](/doc/readme.md).
7 7
8## Building 8## Building
9 9
@@ -12,13 +12,17 @@ Download or clone the whole firmware and navigate to the keyboards/%KEYBOARD% fo
12Depending on which keymap you would like to use, you will have to compile slightly differently. 12Depending on which keymap you would like to use, you will have to compile slightly differently.
13 13
14### Default 14### Default
15
15To build with the default keymap, simply run `make`. 16To build with the default keymap, simply run `make`.
16 17
17### Other Keymaps 18### Other Keymaps
18Several version of keymap are available in advance but you are recommended to define your favorite layout yourself. To define your own keymap create file named `<name>.c` in the keymaps folder, and see keymap document (you can find in top README.md) and existent keymap files.
19 19
20To build the firmware binary hex file with a keymap just do `make` with `KEYMAP` option like: 20Several version of keymap are available in advance but you are recommended to define your favorite layout yourself. To define your own keymap create a folder with the name of your keymap in the keymaps folder, and see keymap documentation (you can find in top readme.md) and existant keymap files.
21
22To build the firmware binary hex file with a keymap just do `make` with `keymap` option like:
23
21``` 24```
22$ make KEYMAP=[default|jack|<name>] 25$ make keymap=[default|jack|<name>]
23``` 26```
24Keymaps follow the format **__\<name\>.c__** and are stored in the `keymaps` folder. \ No newline at end of file 27
28Keymaps follow the format **__keymap.c__** and are stored in folders in the `keymaps` folder, eg `keymaps/my_keymap/` \ No newline at end of file
diff --git a/quantum/template/template.c b/quantum/template/template.c
index 649072eb2..dcc4b0a22 100644
--- a/quantum/template/template.c
+++ b/quantum/template/template.c
@@ -1,26 +1,5 @@
1#include "%KEYBOARD%.h" 1#include "%KEYBOARD%.h"
2 2
3__attribute__ ((weak))
4void matrix_init_user(void) {
5 // leave this function blank - it can be defined in a keymap file
6};
7
8__attribute__ ((weak))
9void matrix_scan_user(void) {
10 // leave this function blank - it can be defined in a keymap file
11}
12
13__attribute__ ((weak))
14bool process_action_user(keyrecord_t *record) {
15 // leave this function blank - it can be defined in a keymap file
16 return true;
17}
18
19__attribute__ ((weak))
20void led_set_user(uint8_t usb_led) {
21 // leave this function blank - it can be defined in a keymap file
22}
23
24void matrix_init_kb(void) { 3void matrix_init_kb(void) {
25 // put your keyboard start-up code here 4 // put your keyboard start-up code here
26 // runs once when the firmware starts up 5 // runs once when the firmware starts up
@@ -35,7 +14,7 @@ void matrix_scan_kb(void) {
35 matrix_scan_user(); 14 matrix_scan_user();
36} 15}
37 16
38bool process_action_kb(keyrecord_t *record) { 17bool process_record_kb(uint16_t keycode, keyrecord_t *record) {
39 // put your per-action keyboard code here 18 // put your per-action keyboard code here
40 // runs for every action, just before processing by the firmware 19 // runs for every action, just before processing by the firmware
41 20
@@ -47,64 +26,3 @@ void led_set_kb(uint8_t usb_led) {
47 26
48 led_set_user(usb_led); 27 led_set_user(usb_led);
49} 28}
50
51#ifdef BACKLIGHT_ENABLE
52#define CHANNEL OCR1C
53
54void backlight_init_ports()
55{
56
57 // Setup PB7 as output and output low.
58 DDRB |= (1<<7);
59 PORTB &= ~(1<<7);
60
61 // Use full 16-bit resolution.
62 ICR1 = 0xFFFF;
63
64 // I could write a wall of text here to explain... but TL;DW
65 // Go read the ATmega32u4 datasheet.
66 // And this: http://blog.saikoled.com/post/43165849837/secret-konami-cheat-code-to-high-resolution-pwm-on
67
68 // Pin PB7 = OCR1C (Timer 1, Channel C)
69 // Compare Output Mode = Clear on compare match, Channel C = COM1C1=1 COM1C0=0
70 // (i.e. start high, go low when counter matches.)
71 // WGM Mode 14 (Fast PWM) = WGM13=1 WGM12=1 WGM11=1 WGM10=0
72 // Clock Select = clk/1 (no prescaling) = CS12=0 CS11=0 CS10=1
73
74 TCCR1A = _BV(COM1C1) | _BV(WGM11); // = 0b00001010;
75 TCCR1B = _BV(WGM13) | _BV(WGM12) | _BV(CS10); // = 0b00011001;
76
77 backlight_init();
78}
79
80void backlight_set(uint8_t level)
81{
82 if ( level == 0 )
83 {
84 // Turn off PWM control on PB7, revert to output low.
85 TCCR1A &= ~(_BV(COM1C1));
86 CHANNEL = 0x0;
87 // Prevent backlight blink on lowest level
88 PORTB &= ~(_BV(PORTB7));
89 }
90 else if ( level == BACKLIGHT_LEVELS )
91 {
92 // Prevent backlight blink on lowest level
93 PORTB &= ~(_BV(PORTB7));
94 // Turn on PWM control of PB7
95 TCCR1A |= _BV(COM1C1);
96 // Set the brightness
97 CHANNEL = 0xFFFF;
98 }
99 else
100 {
101 // Prevent backlight blink on lowest level
102 PORTB &= ~(_BV(PORTB7));
103 // Turn on PWM control of PB7
104 TCCR1A |= _BV(COM1C1);
105 // Set the brightness
106 CHANNEL = 0xFFFF >> ((BACKLIGHT_LEVELS - level) * ((BACKLIGHT_LEVELS + 1) / 2));
107 }
108}
109
110#endif \ No newline at end of file
diff --git a/quantum/template/template.h b/quantum/template/template.h
index b8e7a0456..cd78a54e3 100644
--- a/quantum/template/template.h
+++ b/quantum/template/template.h
@@ -1,13 +1,7 @@
1#ifndef %KEYBOARD_UPPERCASE%_H 1#ifndef %KEYBOARD_UPPERCASE%_H
2#define %KEYBOARD_UPPERCASE%_H 2#define %KEYBOARD_UPPERCASE%_H
3 3
4#include "matrix.h" 4#include "quantum.h"
5#include "keymap.h"
6#ifdef BACKLIGHT_ENABLE
7 #include "backlight.h"
8#endif
9#include <avr/io.h>
10#include <stddef.h>
11 5
12// This a shortcut to help you visually see your layout. 6// This a shortcut to help you visually see your layout.
13// The following is an example using the Planck MIT layout 7// The following is an example using the Planck MIT layout
@@ -22,9 +16,4 @@
22 { k10, KC_NO, k11 }, \ 16 { k10, KC_NO, k11 }, \
23} 17}
24 18
25void matrix_init_user(void);
26void matrix_scan_user(void);
27bool process_action_user(keyrecord_t *record);
28void led_set_user(uint8_t usb_led);
29
30#endif 19#endif
diff --git a/quantum/tools/README.md b/quantum/tools/readme.md
index 5f355256d..5f355256d 100644
--- a/quantum/tools/README.md
+++ b/quantum/tools/readme.md