Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
2b55c419ea | ||
|
|
83e1b9ab6e | ||
|
|
ca598c3df6 | ||
|
|
4588c979bd | ||
|
|
60ee8bddfc | ||
|
|
5f9fb01020 | ||
|
|
c4960b7579 | ||
|
|
d4917318cc | ||
|
|
047a7f4e33 | ||
|
|
c8ab8e0bab | ||
|
|
038a86a9b8 | ||
|
|
9ae15e8c79 | ||
|
|
666cb44673 | ||
|
|
03c790a0f2 | ||
|
|
29b4f83a1f | ||
|
|
e6bcc232ed | ||
|
|
5eb4675fda | ||
|
|
0fcefdc013 | ||
|
|
fe744eb1ad | ||
|
|
85e20a5cf4 | ||
|
|
da5aed6bef | ||
|
|
acb9cf12c4 | ||
|
|
ade3bdf7e7 | ||
|
|
83bc0b9e80 | ||
|
|
29ebb99b1f | ||
|
|
355f075b57 | ||
|
|
c2ca57c8f4 | ||
|
|
5c8b23ccff | ||
|
|
13a8d1681c | ||
|
|
b30d0361c5 | ||
|
|
063a74b660 | ||
|
|
3ff635b9a8 | ||
|
|
2c98c4dd4e | ||
|
|
8c66c5aa9b | ||
|
|
b7dc2eb9ab | ||
|
|
00fc35539d | ||
|
|
65c9da5a65 | ||
|
|
d1819f02df | ||
|
|
e1cdfdc0e7 | ||
|
|
97c18bfbc4 | ||
|
|
0e76b27661 | ||
|
|
bd4c66a26b | ||
|
|
7c57efaaf9 | ||
|
|
d4dc2a577f | ||
|
|
92839f8a09 | ||
|
|
907c1c64cf | ||
|
|
8b9e3e9979 | ||
|
|
6600f32d35 | ||
|
|
e9fa41631c | ||
|
|
91efcfb43a | ||
|
|
24f59c2d72 | ||
|
|
398a7e5b3f | ||
|
|
48db3ad6ef | ||
|
|
12b43f55d6 | ||
|
|
6d6340a82b | ||
|
|
67beec5e94 | ||
|
|
09a53d1aa3 | ||
|
|
4f9e5d4cde | ||
|
|
cf17a8eb95 | ||
|
|
207b17bc4d | ||
|
|
1baa99c647 | ||
|
|
e9e6054ee7 | ||
|
|
4e4a3449a7 | ||
|
|
7c17b87215 | ||
|
|
62ceb46e9d | ||
|
|
2c0201e80f | ||
|
|
51509ec07b | ||
|
|
b215bc3aba | ||
|
|
0928496220 | ||
|
|
a8904d47b7 | ||
|
|
32a47e7af4 | ||
|
|
b27c20d204 | ||
|
|
b87895dc12 | ||
|
|
2344b6865a | ||
|
|
3d45861216 | ||
|
|
e184da91a6 | ||
|
|
d36d5ecfad | ||
|
|
7baeaae9bb | ||
|
|
c85e010d45 | ||
|
|
097df6afdb | ||
|
|
6574ac52ad | ||
|
|
751a1789b5 | ||
|
|
ac7b1d0bf3 | ||
|
|
7369e195c2 | ||
|
|
30f4b4d763 | ||
|
|
9236c3a9d0 | ||
|
|
c2dd19de51 | ||
|
|
6d88794960 | ||
|
|
7a710fb426 | ||
|
|
c8b35b6230 | ||
|
|
995464cb9c | ||
|
|
45c73b13e1 | ||
|
|
9b85bd68a4 | ||
|
|
ce91b36c5d | ||
|
|
2521b970e5 | ||
|
|
598c392709 | ||
|
|
4d218566cc | ||
|
|
a4b2baa2ba | ||
|
|
4b80ee46f8 | ||
|
|
9b398a8f31 | ||
|
|
c30170b868 | ||
|
|
39b483ad32 | ||
|
|
88ebf92184 | ||
|
|
8d792cfb5f | ||
|
|
bd1b51cbd1 | ||
|
|
3028662fa3 | ||
|
|
aea2d6845a | ||
|
|
a502ce43c3 | ||
|
|
b0e30862d6 | ||
|
|
146873fd8e | ||
|
|
b3b617633c | ||
|
|
9ae8a45197 | ||
|
|
a8bb5840ad | ||
|
|
d353fcb99c | ||
|
|
f0bde7906d | ||
|
|
24b0cda3e8 | ||
|
|
1ab8f969f6 | ||
|
|
58af0305f5 | ||
|
|
c7cc20918b | ||
|
|
924573ece2 | ||
|
|
5f06fce2c5 | ||
|
|
4b13c49578 | ||
|
|
98642ca028 | ||
|
|
82dc8faaf3 | ||
|
|
0b09189087 | ||
|
|
3d6d899666 | ||
|
|
cb13dd0a33 | ||
|
|
af4bc251f9 | ||
|
|
e79fb2c26e | ||
|
|
3e0f8f9c8b | ||
|
|
b0a31f0bf3 | ||
|
|
a91034b802 | ||
|
|
2f85f6fbff | ||
|
|
32340e14fb | ||
|
|
b7da69ec85 | ||
|
|
f36112e957 | ||
|
|
30cdf9331a | ||
|
|
8252f378d9 | ||
|
|
d7f9e6fcf1 | ||
|
|
5c07363054 | ||
|
|
b6e9ef8dd1 | ||
|
|
e58ab6d326 | ||
|
|
02781979d6 | ||
|
|
69b484600f | ||
|
|
de79d55187 | ||
|
|
580cb2c1df | ||
|
|
d9eae3ef03 | ||
|
|
05e6cc2655 | ||
|
|
8b572de523 | ||
|
|
18e561b82c | ||
|
|
c785148445 | ||
|
|
b43bdc1c69 | ||
|
|
5a5ecd7dd9 | ||
|
|
60be8d9f24 | ||
|
|
3f85e90126 | ||
|
|
3eefe31a54 | ||
|
|
7be65f2cd0 | ||
|
|
016b4be751 | ||
|
|
db80209e69 | ||
|
|
716924de3e | ||
|
|
d88dca3ca7 | ||
|
|
9c1097e768 | ||
|
|
f7eb030e91 | ||
|
|
aae1814319 | ||
|
|
78fdd40622 | ||
|
|
43b6f031b1 | ||
|
|
3e27ceee42 | ||
|
|
67f374029d | ||
|
|
30fd69886d | ||
|
|
ed528403fd | ||
|
|
faae375ccd | ||
|
|
b0fd064491 | ||
|
|
abf466e57d | ||
|
|
157319fbd0 | ||
|
|
39ff121d73 | ||
|
|
8018f4db2d | ||
|
|
1a159a38ed | ||
|
|
a0bf235644 | ||
|
|
f420741f9b | ||
|
|
0b7b74f56a | ||
|
|
80b2b710da | ||
|
|
3814dacf27 | ||
|
|
7576f6162e | ||
|
|
e8a02afc8c | ||
|
|
357a888d80 | ||
|
|
7f5656996c | ||
|
|
b008a9afe6 | ||
|
|
d8e3294aea | ||
|
|
a8d073368f | ||
|
|
44d93285d1 | ||
|
|
8e0af2f5ba | ||
|
|
da76734fe0 | ||
|
|
c029c5b187 | ||
|
|
294cfd8d33 | ||
|
|
622e94c6cd | ||
|
|
ba7f52aaeb | ||
|
|
307013a2f8 | ||
|
|
f68abbf6c8 | ||
|
|
897c4cd175 | ||
|
|
1f2807c2de | ||
|
|
b160913309 | ||
|
|
867fded980 | ||
|
|
d1730ec760 | ||
|
|
4057d44989 | ||
|
|
2bfcb6bfc5 | ||
|
|
1f42071238 | ||
|
|
400423d10b | ||
|
|
54ef02dead | ||
|
|
044b4aaf01 | ||
|
|
ccb4b81b3f | ||
|
|
e269977387 | ||
|
|
0cb4da2c74 | ||
|
|
9b0c734733 | ||
|
|
fffee6ade1 | ||
|
|
97ddc7ea18 | ||
|
|
3afd2d81b8 | ||
|
|
2543bad250 | ||
|
|
a056d94561 | ||
|
|
573d1fbb92 | ||
|
|
437446ba8f | ||
|
|
8640b43214 | ||
|
|
09fc6cab34 | ||
|
|
7e8dc2e570 | ||
|
|
263536586d | ||
|
|
7aa4cc9603 | ||
|
|
e26bc21d14 | ||
|
|
5c2b46dc47 | ||
|
|
713d34cda4 | ||
|
|
cce301ae83 | ||
|
|
08e08b660c | ||
|
|
cff3c3bf28 | ||
|
|
b7cb4111ea | ||
|
|
184c362324 | ||
|
|
1d1c0503b6 | ||
|
|
01e74b0ac6 | ||
|
|
c0cb2ab1c1 | ||
|
|
7281e86e98 | ||
|
|
86812f22e4 | ||
|
|
b83fb9eb71 | ||
|
|
3736db6081 | ||
|
|
b19187c62c | ||
|
|
4a7725b3ee | ||
|
|
93a1c5ca16 | ||
|
|
407d6a2b67 | ||
|
|
d7523c1260 | ||
|
|
a7f093b40c | ||
|
|
b9a38487f3 | ||
|
|
9f400794c0 | ||
|
|
12efb28e13 | ||
|
|
3972978c8d | ||
|
|
b327d20402 | ||
|
|
ca451c5aa0 | ||
|
|
7a75af8342 | ||
|
|
d03bc3a9c1 | ||
|
|
c12e429da2 | ||
|
|
9219f9e724 | ||
|
|
f4ff225c00 | ||
|
|
a68b0ed9a2 | ||
|
|
a2dee4494d | ||
|
|
6cfc3cd940 | ||
|
|
e84e9a2004 | ||
|
|
232b9dabbe | ||
|
|
7b2c09de59 | ||
|
|
e571f53ae9 | ||
|
|
6fc4f1eddd | ||
|
|
be73820f7b | ||
|
|
81a2113cbd | ||
|
|
d17572b125 | ||
|
|
517d607fa4 | ||
|
|
1110fe6c6f | ||
|
|
eefc05e078 | ||
|
|
f1e09dd388 | ||
|
|
0def9ed528 | ||
|
|
c73125eea7 | ||
|
|
306d02aa93 | ||
|
|
b8ddfd34ec | ||
|
|
14eccef7bf | ||
|
|
aab5c44c7d | ||
|
|
563d5919b3 | ||
|
|
0fee906e09 | ||
|
|
c2fd7f1b5b | ||
|
|
faa3e62e70 | ||
|
|
5f5a6fff8b | ||
|
|
f1c33423b0 | ||
|
|
5f8e8540fb | ||
|
|
4f6f7b59cf | ||
|
|
e2e287ec5f | ||
|
|
dfcd4f0d25 | ||
|
|
b2271d984d | ||
|
|
8d3fca57a3 | ||
|
|
fced377ac0 | ||
|
|
7b8a013826 | ||
|
|
5263dfd465 | ||
|
|
13206b2f87 | ||
|
|
cb9be8a9dc | ||
|
|
a1af8542c7 | ||
|
|
1a5dc278bc | ||
|
|
10c1e1b3ab | ||
|
|
00c1401d3c | ||
|
|
a9b3c0a807 | ||
|
|
ac447d8acb | ||
|
|
a5e749d8cd | ||
|
|
4ee623fdd5 | ||
|
|
751316c344 | ||
|
|
5d3bf8a050 | ||
|
|
6501377070 | ||
|
|
af2ca13604 | ||
|
|
451c472d1d | ||
|
|
bfe76053ba | ||
|
|
9d41281a1d | ||
|
|
ba5e1f1bae | ||
|
|
e4823aadec | ||
|
|
5c9906eb4f | ||
|
|
f56d333db1 | ||
|
|
d8f76f9e6d | ||
|
|
6ca00c2152 | ||
|
|
dc6fe85b87 | ||
|
|
883dd2df80 | ||
|
|
2ac3a51d71 | ||
|
|
f66680d233 | ||
|
|
503cf18aed | ||
|
|
38d2c8cedf | ||
|
|
53224e03d6 | ||
|
|
7ef2ea3d49 | ||
|
|
9e4037465a | ||
|
|
fd4f102977 | ||
|
|
6d84795bc1 | ||
|
|
179e5c018f | ||
|
|
5246acb2e4 | ||
|
|
02a8c874f8 | ||
|
|
dae6f6b39b | ||
|
|
526c185e7e | ||
|
|
c63fd051da | ||
|
|
b95979560c | ||
|
|
65150984bd | ||
|
|
205321c377 | ||
|
|
1816ad01d0 | ||
|
|
9c8f61dfa0 | ||
|
|
d1df576ece | ||
|
|
83ebbf57b3 | ||
|
|
8e1f706ac6 | ||
|
|
b0c780ed32 | ||
|
|
3ad2be52a7 | ||
|
|
0fbcb41c85 | ||
|
|
ddca422776 | ||
|
|
82bb7d2852 | ||
|
|
1044519f36 | ||
|
|
209942366b | ||
|
|
494b34b63f | ||
|
|
58e3b01f37 | ||
|
|
6c2008c688 | ||
|
|
bcedc80ec7 | ||
|
|
ef5fad137b | ||
|
|
15dd05c402 | ||
|
|
32d03db371 | ||
|
|
c9d396dd47 | ||
|
|
2afb29e095 | ||
|
|
fcf150bd82 | ||
|
|
ee2eb01653 | ||
|
|
0bece1d442 | ||
|
|
be69dd22e8 | ||
|
|
b9675d2106 | ||
|
|
f689f043b1 | ||
|
|
54b04d9665 | ||
|
|
4604c70c4c | ||
|
|
010c5b12bd | ||
|
|
4adf4d5a89 | ||
|
|
d0e0202b27 | ||
|
|
fb9425df82 | ||
|
|
22ad35b225 | ||
|
|
f6cec668c7 | ||
|
|
2651edc243 | ||
|
|
2a43989d30 | ||
|
|
2f5521cd48 | ||
|
|
ac3d2a3810 | ||
|
|
1786490993 | ||
|
|
e55d55edc0 | ||
|
|
ad014c2539 | ||
|
|
81698df056 | ||
|
|
fca35a3540 | ||
|
|
5d01cc45be | ||
|
|
eaab0844e8 | ||
|
|
ce842f912e | ||
|
|
cceab93baa | ||
|
|
4161573b28 | ||
|
|
d0e684ef55 | ||
|
|
f125406700 | ||
|
|
afebb6576c | ||
|
|
7f6ba2bf8a | ||
|
|
142ebaea46 | ||
|
|
bbd17def21 | ||
|
|
d89e552419 | ||
|
|
9cf69a1997 | ||
|
|
c6cf1ae4e7 | ||
|
|
2c9ab8a606 | ||
|
|
0bf60acc4b | ||
|
|
6b54f3ce1c | ||
|
|
c3aaed8dfb | ||
|
|
ebc274209e | ||
|
|
1bdfac8afc | ||
|
|
9b716b7ada | ||
|
|
b591c0c24a | ||
|
|
6ba014a572 | ||
|
|
2dd47a3bf4 | ||
|
|
887c1c4e0e | ||
|
|
f66850bfd0 | ||
|
|
632285c982 | ||
|
|
805f5cb72b | ||
|
|
a8a8bf0ff3 | ||
|
|
fadd3cb461 | ||
|
|
a41f973f75 | ||
|
|
7abbc95cd6 | ||
|
|
30a6f231bf | ||
|
|
44ff14f290 | ||
|
|
741c7d5eec | ||
|
|
f3c30e80cc | ||
|
|
d846660e00 | ||
|
|
774384ce31 | ||
|
|
361ac2f32a | ||
|
|
d15a60d2d3 | ||
|
|
73992c68d5 | ||
|
|
8ca4ed9a98 | ||
|
|
640d12d070 | ||
|
|
3beda5c16e | ||
|
|
fb7fc54923 | ||
|
|
179c868059 | ||
|
|
7b11dcce10 | ||
|
|
e2fa05c6d2 | ||
|
|
4c4009c0fd | ||
|
|
e7860d673b | ||
|
|
2fe7e221ec | ||
|
|
e0f548085c | ||
|
|
94fc32f431 | ||
|
|
1f7bbf279c | ||
|
|
803610a284 | ||
|
|
cd0edbb1fb | ||
|
|
6919772fb9 | ||
|
|
fedd8e81d1 | ||
|
|
adda5d7770 | ||
|
|
d2581884d9 | ||
|
|
58fd782ce0 | ||
|
|
8e56d10e4e | ||
|
|
43868a5e20 | ||
|
|
db167ecf79 | ||
|
|
2b8b1045a1 | ||
|
|
7a6e52b5d8 | ||
|
|
ae5f7365ea | ||
|
|
606438692d | ||
|
|
5d29a13e22 | ||
|
|
81c648e947 | ||
|
|
923bad46f9 | ||
|
|
19513fac5f | ||
|
|
7bb9c76c80 | ||
|
|
57e67a4cc8 | ||
|
|
cf3913cd79 | ||
|
|
a30cc37c09 | ||
|
|
b18c261040 | ||
|
|
bac5d6bc6a | ||
|
|
ab1650606c | ||
|
|
dc00942be1 | ||
|
|
e8f842e798 | ||
|
|
3745ebc22b | ||
|
|
d646cba72a | ||
|
|
15e84f79f1 | ||
|
|
6f30b402a2 | ||
|
|
1ff526dac0 | ||
|
|
e17b55e33a | ||
|
|
f31bf1b202 | ||
|
|
5f82b0782f | ||
|
|
2e6959ed87 | ||
|
|
c482a2944b | ||
|
|
406dc2fb2d | ||
|
|
65c8ac9ac9 | ||
|
|
e182a38e7c | ||
|
|
fe4581c1a1 | ||
|
|
ddd055b1e2 | ||
|
|
f7324ec684 | ||
|
|
3d760caa85 | ||
|
|
750c7c2bdb | ||
|
|
4846c8eba0 | ||
|
|
3de4c3ea6a | ||
|
|
830bd5460c | ||
|
|
9f54a26dc0 | ||
|
|
16a15c1cfc | ||
|
|
37a4b53c4f | ||
|
|
a84d239661 | ||
|
|
41fd60d624 | ||
|
|
231464c49c | ||
|
|
d26a14c169 | ||
|
|
195be50745 | ||
|
|
8fdb229b66 | ||
|
|
fd3456f362 | ||
|
|
812d80efbd | ||
|
|
86c4c4e91d | ||
|
|
168ba88ada | ||
|
|
5f5c2a219c | ||
|
|
e415198235 | ||
|
|
b17482c3fd | ||
|
|
5b4870c046 | ||
|
|
374525c995 | ||
|
|
e02a3c559d | ||
|
|
e1217dae5a | ||
|
|
485a0b0bc3 | ||
|
|
23cfc4b145 | ||
|
|
bd639752db | ||
|
|
aaeef7a833 | ||
|
|
0d6614f71f | ||
|
|
d322ec5452 | ||
|
|
c7449b3840 | ||
|
|
4c51049b2b | ||
|
|
dd60fcda28 | ||
|
|
fd6b674b49 | ||
|
|
2c0deb8a13 | ||
|
|
a904371b29 | ||
|
|
cfdd105d9d | ||
|
|
82ae6ee007 | ||
|
|
f220e7d713 | ||
|
|
3cb6fb2935 | ||
|
|
5c666398d5 | ||
|
|
a47915d2d2 | ||
|
|
6ec3cc029e | ||
|
|
4597f2bcc8 | ||
|
|
52af38da37 | ||
|
|
b2dbc3f515 | ||
|
|
86b62eadc2 | ||
|
|
3337eb10b2 | ||
|
|
32bab55def | ||
|
|
47fc2f8855 | ||
|
|
ee29b515ec | ||
|
|
c031e13982 | ||
|
|
84bf82f2c9 | ||
|
|
af26238385 | ||
|
|
28e5969f78 | ||
|
|
59246756e5 | ||
|
|
423ce39f18 | ||
|
|
217debff07 | ||
|
|
52e9719d09 | ||
|
|
9df367e227 | ||
|
|
8650b9f10c | ||
|
|
5c9c45619e | ||
|
|
09caf19389 | ||
|
|
4baf49191f | ||
|
|
427da3c19c | ||
|
|
1df8bb3cdb | ||
|
|
99eacdc47a | ||
|
|
5e235d30c7 | ||
|
|
6586280bf3 | ||
|
|
0722986d7a | ||
|
|
22a10cc8a3 | ||
|
|
b349fa0a57 | ||
|
|
e98a9578a1 | ||
|
|
d2b03bf150 | ||
|
|
35ca1c2212 | ||
|
|
ccc8338b0e | ||
|
|
bafa35ff46 | ||
|
|
182286680a | ||
|
|
c1c579c554 | ||
|
|
19bd8aa942 | ||
|
|
d0d105b083 | ||
|
|
c0a57c2a50 | ||
|
|
738c6612ca | ||
|
|
643fc1d806 | ||
|
|
f78896589e | ||
|
|
837ffd0006 | ||
|
|
92a50a386a | ||
|
|
357c6009be | ||
|
|
e916ce5f3e | ||
|
|
086a7cf800 | ||
|
|
99f7fe6bd4 | ||
|
|
d0c3a4c8d5 | ||
|
|
2dca087b04 | ||
|
|
b80340c207 | ||
|
|
cb4a86475e | ||
|
|
7e4cf9ace2 | ||
|
|
0d658e0c95 | ||
|
|
1522d97c2b | ||
|
|
2d39a9dcdb | ||
|
|
33bf4863f5 | ||
|
|
ad547c1fdd | ||
|
|
9b70e53508 | ||
|
|
33a5dc4fcf | ||
|
|
e0fffcde99 | ||
|
|
06bffbd45b | ||
|
|
c261076f8e | ||
|
|
51ecd37d7b | ||
|
|
ed5e69093c | ||
|
|
43785126a7 | ||
|
|
8c97b4a3a4 | ||
|
|
0698b15aa5 | ||
|
|
d600631ad1 | ||
|
|
f3595f65b7 | ||
|
|
23df763a31 | ||
|
|
ed910c8e97 | ||
|
|
7e1c0bd4c0 | ||
|
|
d2b8398f75 | ||
|
|
195324cc4c | ||
|
|
cd5399942b | ||
|
|
fd4bbd8d11 | ||
|
|
f43cb31476 | ||
|
|
89eb3a9e42 | ||
|
|
66d94dc22a | ||
|
|
5a8f59503e | ||
|
|
7918f7d61d | ||
|
|
a6bd8fe67b | ||
|
|
55b43f02f0 | ||
|
|
db4b11f866 | ||
|
|
46a84ec84a | ||
|
|
3b5998085c | ||
|
|
7a9980fd85 | ||
|
|
bc13dcd349 | ||
|
|
55002338b1 | ||
|
|
99d9250045 | ||
|
|
4a92dd327c | ||
|
|
7873b49d40 | ||
|
|
fcf2b45263 | ||
|
|
5607af8524 | ||
|
|
5a45627e17 | ||
|
|
17d0f6338e | ||
|
|
484c059d86 | ||
|
|
3cc68543ca | ||
|
|
daf6dedb02 | ||
|
|
7a0d145e27 | ||
|
|
e990863296 | ||
|
|
d06340f665 | ||
|
|
4c0065dda7 | ||
|
|
2ae39ccf38 | ||
|
|
5185c52b4a | ||
|
|
c0b99badcb | ||
|
|
f9bb9ef0b8 | ||
|
|
3d9ffd3efb | ||
|
|
3cea9fedff | ||
|
|
575d99816e | ||
|
|
4bccde37d4 | ||
|
|
f6b40da7f8 | ||
|
|
6fb048fdaf | ||
|
|
06b571aa53 | ||
|
|
355b693e4e | ||
|
|
f514ad5503 | ||
|
|
09a1917103 | ||
|
|
46e4493761 | ||
|
|
157d121c71 | ||
|
|
7e6b550ebf | ||
|
|
7f4ce4a8b7 | ||
|
|
6452973761 | ||
|
|
a2309b306a | ||
|
|
52ac6c4303 | ||
|
|
05e9ff6554 | ||
|
|
17bda000f3 | ||
|
|
46a69d1f3b | ||
|
|
b56a41800a | ||
|
|
d3c29c9b3c | ||
|
|
370577e4ed | ||
|
|
6e84247ec2 | ||
|
|
5380c29dd7 | ||
|
|
23f19852b9 | ||
|
|
8a5c1e1859 | ||
|
|
6265b78307 | ||
|
|
23124b9fd1 | ||
|
|
eb7fc7f9d9 | ||
|
|
c2df714c3b | ||
|
|
799b21f8cd | ||
|
|
750179e111 | ||
|
|
f538b2273a | ||
|
|
50e85f91e8 | ||
|
|
27e7f322a5 | ||
|
|
dfdc89296b | ||
|
|
671020af08 | ||
|
|
b8c3f4c60b | ||
|
|
511fe643c2 | ||
|
|
f7601dba13 | ||
|
|
89cab95b63 | ||
|
|
cc38627816 | ||
|
|
6c2c3c13e9 | ||
|
|
e4cc642a79 | ||
|
|
c3c3943432 | ||
|
|
061ed87b89 | ||
|
|
5c1aca0b88 | ||
|
|
6384a2abd8 | ||
|
|
439afc883a | ||
|
|
07c75feba3 | ||
|
|
b5aa5e4338 | ||
|
|
be8443b35b | ||
|
|
4b10235f67 | ||
|
|
6ef13f83e2 | ||
|
|
be2f5816b6 | ||
|
|
ff213d5fe1 | ||
|
|
3234118e52 | ||
|
|
a1ffc40b36 | ||
|
|
8fe5c718b4 | ||
|
|
38f14c4174 | ||
|
|
eb683c8c52 | ||
|
|
21799be1ca | ||
|
|
5cfc3ce02e | ||
|
|
724f20ed32 | ||
|
|
c61f016fa4 | ||
|
|
ea7e40bae1 | ||
|
|
974f83ec4b | ||
|
|
400ca2d035 | ||
|
|
e409fb47f2 | ||
|
|
0499f30f59 | ||
|
|
ae74922d14 | ||
|
|
3349a8b49b | ||
|
|
b4ef72423e | ||
|
|
f4b67cde8a | ||
|
|
0a643be39e | ||
|
|
6c8e205fc0 | ||
|
|
7901006753 | ||
|
|
9bfa713421 | ||
|
|
b6fc3ad8e7 | ||
|
|
e0909a31c7 | ||
|
|
d6bffdf577 | ||
|
|
d1190df10b | ||
|
|
bf38f39c3f | ||
|
|
6add103827 | ||
|
|
62d1d69ba9 | ||
|
|
7642075fc3 | ||
|
|
ca91dc594b | ||
|
|
26cb83b8c0 | ||
|
|
2392ddb76b | ||
|
|
6de77141a4 | ||
|
|
6f6c2e1c5c | ||
|
|
48cad94d7e | ||
|
|
90665aeec9 | ||
|
|
845953cc67 | ||
|
|
c3c2eb71e1 | ||
|
|
28a6a4a15b | ||
|
|
ccb37f673a | ||
|
|
c5efbc45a1 | ||
|
|
6a0d3c3517 | ||
|
|
2fbbac04bb | ||
|
|
04c81a04c7 | ||
|
|
120fcc58b6 | ||
|
|
2f15cb2126 | ||
|
|
8af156d976 | ||
|
|
70b5015162 | ||
|
|
3fad3854d6 | ||
|
|
38d7145da2 | ||
|
|
6e8876be39 | ||
|
|
0bb2924670 | ||
|
|
2f623daa45 | ||
|
|
ebbaba9001 | ||
|
|
5f35b07102 | ||
|
|
59188bf29d | ||
|
|
9c4bf0ac4a | ||
|
|
f2901375ce | ||
|
|
f65e79477f | ||
|
|
3094422b33 | ||
|
|
31fd0cbc1c | ||
|
|
2b427f774a | ||
|
|
85444176b2 | ||
|
|
52b48997eb | ||
|
|
808aab8496 | ||
|
|
0742f9fc96 | ||
|
|
58a9c84d6b | ||
|
|
c217186bea | ||
|
|
781308507d | ||
|
|
2eb6cb0dfd | ||
|
|
95c5c11d0b | ||
|
|
b6a09502c6 | ||
|
|
1962135418 | ||
|
|
d79be051dd | ||
|
|
3fe8d604a4 | ||
|
|
194bc7a7e1 | ||
|
|
fec4283022 | ||
|
|
17af712b7c | ||
|
|
712ded1f2f | ||
|
|
c67e304593 | ||
|
|
8c80475fcc | ||
|
|
3e18bb914c | ||
|
|
4434649c2f | ||
|
|
c6c94eeabc | ||
|
|
2c201ab9ad | ||
|
|
e5b10079cf | ||
|
|
854d46f833 | ||
|
|
bdfdc506da | ||
|
|
51a81813b0 | ||
|
|
8566a684bc | ||
|
|
28d3c29704 | ||
|
|
dd5cb64851 | ||
|
|
b9a64ec93b | ||
|
|
c9067dfe4f | ||
|
|
1592d7df24 | ||
|
|
9acd5e04d5 | ||
|
|
0afcb8a36c | ||
|
|
89a675d57c | ||
|
|
b892a1429d | ||
|
|
e90d66f93e | ||
|
|
bfef2c7b05 | ||
|
|
74c01654c7 | ||
|
|
dc98d44582 | ||
|
|
defa1a1dc7 | ||
|
|
c89c084146 | ||
|
|
13fff52f6b | ||
|
|
7bf9d9dc0a | ||
|
|
14079ce698 | ||
|
|
05d9a0ff03 | ||
|
|
b9d0b1f064 | ||
|
|
ed80874f72 | ||
|
|
23e942ae4e | ||
|
|
c077300e19 | ||
|
|
11f12d386b | ||
|
|
4d76d85d7b | ||
|
|
981ea87b05 | ||
|
|
65252ebf67 | ||
|
|
5bd0a5a585 | ||
|
|
9fbf17b90e | ||
|
|
96bfce7000 | ||
|
|
d68c4d8106 | ||
|
|
9fb988b6e8 | ||
|
|
016d417253 | ||
|
|
de58b07659 | ||
|
|
6ceaae30f5 | ||
|
|
5075a1d9e4 | ||
|
|
3587e20e70 | ||
|
|
963bba1fc3 | ||
|
|
571a589cfa | ||
|
|
3c2d5599b9 | ||
|
|
3b05f25221 | ||
|
|
e05e671871 | ||
|
|
2d5b492550 | ||
|
|
ad8774d6fa | ||
|
|
297aad6ebd | ||
|
|
8f69983c58 | ||
|
|
b779078c60 | ||
|
|
b936048b0b | ||
|
|
7e0dc5376f | ||
|
|
6d1af63842 | ||
|
|
6c4a744a1b | ||
|
|
f7722ef9ca | ||
|
|
76cb2b1160 | ||
|
|
5117dff6a2 | ||
|
|
e5d34fd084 | ||
|
|
bfb2f8e0a8 | ||
|
|
d8f3c28a37 | ||
|
|
eef0cb2f90 | ||
|
|
63e4ad13c8 | ||
|
|
f9e67338a4 | ||
|
|
5f9f62fb8c | ||
|
|
147bc6ec43 | ||
|
|
bea62add55 | ||
|
|
d511e52c1f | ||
|
|
789e199450 | ||
|
|
a747c1c3de | ||
|
|
a521fc2b6c | ||
|
|
8651eef298 | ||
|
|
f4799481cd | ||
|
|
675b153525 | ||
|
|
5df2424651 | ||
|
|
f9c53ca71a | ||
|
|
0d189582c1 | ||
|
|
c6b667623a | ||
|
|
d96380e654 | ||
|
|
7e80686f1e | ||
|
|
e967471c4f | ||
|
|
eca3f9d935 | ||
|
|
44c62117ee | ||
|
|
f235822fba | ||
|
|
5d5ff807c6 | ||
|
|
1c7c5daad4 | ||
|
|
aeab11da88 | ||
|
|
b53934805a | ||
|
|
6bfbdc30ca | ||
|
|
02eb949479 | ||
|
|
3a0f11eb27 | ||
|
|
c2013f0b7c | ||
|
|
19d7cbc858 | ||
|
|
73f903906e | ||
|
|
d235612e48 | ||
|
|
6ad3328b83 | ||
|
|
13d736d6ab | ||
|
|
0b810bdff3 | ||
|
|
3f19117124 | ||
|
|
fe3e5cba69 | ||
|
|
6ba383cc5f | ||
|
|
d44ca60cb0 | ||
|
|
42b0e95ae6 | ||
|
|
b6316c5024 | ||
|
|
fc4ef6934d | ||
|
|
0dff26b550 | ||
|
|
76d8558b1a | ||
|
|
8123dd2649 | ||
|
|
1ec648932f | ||
|
|
427f7b3a39 | ||
|
|
c670240503 | ||
|
|
59d6b0faab | ||
|
|
6f55aa993a | ||
|
|
e34764502f | ||
|
|
8b0efc2124 | ||
|
|
2f936420dd | ||
|
|
6698af9c3d | ||
|
|
61da615308 | ||
|
|
ece14278ef | ||
|
|
567bfc97ac | ||
|
|
7aff643031 | ||
|
|
7fe4097792 | ||
|
|
652f4492d3 | ||
|
|
910c466cfe | ||
|
|
19dbcf3814 | ||
|
|
c89012566c | ||
|
|
9dfebb9d67 | ||
|
|
2a31fbf9a6 | ||
|
|
cce2420bb2 | ||
|
|
b272c035ba | ||
|
|
5f1f370463 | ||
|
|
49a2fbea0c | ||
|
|
4b1430fd09 | ||
|
|
f1c6fa3895 | ||
|
|
fe1a055391 | ||
|
|
c18b51e68e | ||
|
|
dc68418660 | ||
|
|
499d7c8ce6 | ||
|
|
60b020acab | ||
|
|
b5be96f8bb | ||
|
|
7aa21cc287 | ||
|
|
d597af9e1e | ||
|
|
03ed819717 | ||
|
|
141535c9db | ||
|
|
a92947fcdb | ||
|
|
cde5237a88 | ||
|
|
dc79792ab4 | ||
|
|
e6a9f700de | ||
|
|
0fdd37ee19 | ||
|
|
40e8d60ecd | ||
|
|
f81b0e35a6 | ||
|
|
5e98eaaaff | ||
|
|
9e8767917d | ||
|
|
f89439ae09 | ||
|
|
3cd2a27ac0 | ||
|
|
28d94b7248 | ||
|
|
abd8e75cb7 | ||
|
|
9046107183 | ||
|
|
2b63896466 | ||
|
|
6734a39811 | ||
|
|
799acb2802 | ||
|
|
18bc525493 | ||
|
|
4edb5a5e8c | ||
|
|
3b5fd4cc51 | ||
|
|
cd9a430d66 | ||
|
|
1b267d4840 | ||
|
|
32d03eef90 | ||
|
|
f2f2afe13b | ||
|
|
3a3ea03b6e | ||
|
|
f3afc716cb | ||
|
|
e72562fe6f | ||
|
|
2b66acf04a | ||
|
|
5ac6fe1888 | ||
|
|
979ac0d8da | ||
|
|
7a89b51018 | ||
|
|
2a05d433c9 |
No files matched your search
@@ -1,24 +0,0 @@
|
|||||||
|
|
||||||
-I.
|
|
||||||
-I./drivers
|
|
||||||
-I./drivers/avr
|
|
||||||
-I./keyboards/ergodox_ez
|
|
||||||
-I./keyboards/ergodox_ez/keymaps/vim
|
|
||||||
-I./lib
|
|
||||||
-I./lib/lufa
|
|
||||||
-I./quantum
|
|
||||||
-I./quantum/api
|
|
||||||
-I./quantum/audio
|
|
||||||
-I./quantum/keymap_extras
|
|
||||||
-I./quantum/process_keycode
|
|
||||||
-I./quantum/serial_link
|
|
||||||
-I./quantum/template
|
|
||||||
-I./quantum/tools
|
|
||||||
-I./quantum/visualizer
|
|
||||||
-I./tmk_core
|
|
||||||
-I./tmk_core/common
|
|
||||||
-I./tmk_core/common/debug.h
|
|
||||||
-I./tmk_core/protocol
|
|
||||||
-I./tmk_core/protocol/lufa
|
|
||||||
-I./util
|
|
||||||
-DQMK_KEYBOARD=\"$(KEYBOARD)\" -DQMK_KEYMAP=\"$(KEYMAP)\"
|
|
||||||
File renamed without changes.
@@ -19,7 +19,7 @@ jobs:
|
|||||||
container: qmkfm/base_container
|
container: qmkfm/base_container
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v1
|
- uses: actions/checkout@v2
|
||||||
with:
|
with:
|
||||||
submodules: recursive
|
submodules: recursive
|
||||||
- name: Install dependencies
|
- name: Install dependencies
|
||||||
|
|||||||
@@ -0,0 +1,49 @@
|
|||||||
|
name: PR Lint keyboards
|
||||||
|
|
||||||
|
on:
|
||||||
|
pull_request:
|
||||||
|
paths:
|
||||||
|
- 'keyboards/**'
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
info:
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
|
||||||
|
container: qmkfm/base_container
|
||||||
|
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v2
|
||||||
|
with:
|
||||||
|
fetch-depth: 0
|
||||||
|
|
||||||
|
- name: Print info
|
||||||
|
run: |
|
||||||
|
git rev-parse --short HEAD
|
||||||
|
echo ${{ github.event.pull_request.base.sha }}
|
||||||
|
git diff --name-only ${{ github.event.pull_request.base.sha }}...
|
||||||
|
|
||||||
|
- name: Run qmk info
|
||||||
|
shell: 'bash {0}'
|
||||||
|
run: |
|
||||||
|
QMK_CHANGES=$(git diff --name-only ${{ github.event.pull_request.base.sha }}...)
|
||||||
|
QMK_KEYBOARDS=$(qmk list-keyboards)
|
||||||
|
|
||||||
|
exit_code=0
|
||||||
|
for KB in $QMK_KEYBOARDS; do
|
||||||
|
KEYBOARD_CHANGES=$(echo "$QMK_CHANGES" | grep -E '^(keyboards/'${KB}'/)')
|
||||||
|
if [[ -z "$KEYBOARD_CHANGES" ]]; then
|
||||||
|
# skip as no changes for this keyboard
|
||||||
|
continue
|
||||||
|
fi
|
||||||
|
|
||||||
|
KEYMAP_ONLY=$(echo "$KEYBOARD_CHANGES" | grep -cv /keymaps/)
|
||||||
|
if [[ $KEYMAP_ONLY -gt 0 ]]; then
|
||||||
|
echo "linting ${KB}"
|
||||||
|
|
||||||
|
# TODO: info info always returns 0 - right now the only way to know failure is to inspect log lines
|
||||||
|
qmk info -kb ${KB} 2>&1 | tee /tmp/$$
|
||||||
|
!(grep -cq ☒ /tmp/$$)
|
||||||
|
: $((exit_code = $exit_code + $?))
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
exit $exit_code
|
||||||
+1
-1
@@ -24,6 +24,7 @@ quantum/version.h
|
|||||||
.idea/
|
.idea/
|
||||||
CMakeLists.txt
|
CMakeLists.txt
|
||||||
cmake-build-debug
|
cmake-build-debug
|
||||||
|
.clang_complete
|
||||||
doxygen/
|
doxygen/
|
||||||
.DS_Store
|
.DS_Store
|
||||||
/util/wsl_downloaded
|
/util/wsl_downloaded
|
||||||
@@ -47,7 +48,6 @@ doxygen/
|
|||||||
*.iml
|
*.iml
|
||||||
.browse.VC.db*
|
.browse.VC.db*
|
||||||
*.stackdump
|
*.stackdump
|
||||||
util/Win_Check_Output.txt
|
|
||||||
# Let these ones be user specific, since we have so many different configurations
|
# Let these ones be user specific, since we have so many different configurations
|
||||||
.vscode/c_cpp_properties.json
|
.vscode/c_cpp_properties.json
|
||||||
.vscode/launch.json
|
.vscode/launch.json
|
||||||
|
|||||||
+7
-1
@@ -12,7 +12,13 @@
|
|||||||
branch = master
|
branch = master
|
||||||
[submodule "lib/googletest"]
|
[submodule "lib/googletest"]
|
||||||
path = lib/googletest
|
path = lib/googletest
|
||||||
url = https://github.com/google/googletest
|
url = https://github.com/qmk/googletest
|
||||||
[submodule "lib/lufa"]
|
[submodule "lib/lufa"]
|
||||||
path = lib/lufa
|
path = lib/lufa
|
||||||
url = https://github.com/qmk/lufa
|
url = https://github.com/qmk/lufa
|
||||||
|
[submodule "lib/vusb"]
|
||||||
|
path = lib/vusb
|
||||||
|
url = https://github.com/qmk/v-usb
|
||||||
|
[submodule "lib/printf"]
|
||||||
|
path = lib/printf
|
||||||
|
url = https://github.com/qmk/printf
|
||||||
Vendored
+12
-7
@@ -9,12 +9,17 @@
|
|||||||
"**/*.bin": true
|
"**/*.bin": true
|
||||||
},
|
},
|
||||||
"files.associations": {
|
"files.associations": {
|
||||||
"*.h": "c",
|
"*.h": "c",
|
||||||
"*.c": "c",
|
"*.c": "c",
|
||||||
"*.cpp": "cpp",
|
"*.inc": "c",
|
||||||
"*.hpp": "cpp",
|
"*.cpp": "cpp",
|
||||||
"xstddef": "c",
|
"*.hpp": "cpp",
|
||||||
"type_traits": "c",
|
"xstddef": "c",
|
||||||
"utility": "c"
|
"type_traits": "c",
|
||||||
|
"utility": "c"
|
||||||
|
},
|
||||||
|
"[markdown]": {
|
||||||
|
"editor.trimAutoWhitespace": false,
|
||||||
|
"files.trimTrailingWhitespace": false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -29,6 +29,9 @@ $(info QMK Firmware $(QMK_VERSION))
|
|||||||
endif
|
endif
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
# avoid 'Entering|Leaving directory' messages
|
||||||
|
MAKEFLAGS += --no-print-directory
|
||||||
|
|
||||||
ON_ERROR := error_occurred=1
|
ON_ERROR := error_occurred=1
|
||||||
|
|
||||||
BREAK_ON_ERRORS = no
|
BREAK_ON_ERRORS = no
|
||||||
@@ -291,8 +294,8 @@ define PARSE_RULE
|
|||||||
$$(info | QMK's make format recently changed to use folder locations and colons:)
|
$$(info | QMK's make format recently changed to use folder locations and colons:)
|
||||||
$$(info | make project_folder:keymap[:target])
|
$$(info | make project_folder:keymap[:target])
|
||||||
$$(info | Examples:)
|
$$(info | Examples:)
|
||||||
$$(info | make planck/rev4:default:dfu)
|
$$(info | make dz60:default)
|
||||||
$$(info | make planck:default)
|
$$(info | make planck/rev6:default:flash)
|
||||||
$$(info |)
|
$$(info |)
|
||||||
endif
|
endif
|
||||||
endef
|
endef
|
||||||
@@ -559,14 +562,16 @@ endef
|
|||||||
%:
|
%:
|
||||||
# Check if we have the CMP tool installed
|
# Check if we have the CMP tool installed
|
||||||
cmp $(ROOT_DIR)/Makefile $(ROOT_DIR)/Makefile >/dev/null 2>&1; if [ $$? -gt 0 ]; then printf "$(MSG_NO_CMP)"; exit 1; fi;
|
cmp $(ROOT_DIR)/Makefile $(ROOT_DIR)/Makefile >/dev/null 2>&1; if [ $$? -gt 0 ]; then printf "$(MSG_NO_CMP)"; exit 1; fi;
|
||||||
# Ensure that python3 is installed. This check can be removed after python is used in more places.
|
# Ensure that bin/qmk works. This will be a failing check after the next develop merge on 2020 Aug 29.
|
||||||
if ! python3 --version 1> /dev/null 2>&1; then printf "$(MSG_PYTHON_MISSING)"; fi
|
if ! bin/qmk hello 1> /dev/null 2>&1; then printf "$(MSG_PYTHON_MISSING)"; fi
|
||||||
# Check if the submodules are dirty, and display a warning if they are
|
# Check if the submodules are dirty, and display a warning if they are
|
||||||
ifndef SKIP_GIT
|
ifndef SKIP_GIT
|
||||||
if [ ! -e lib/chibios ]; then git submodule sync lib/chibios && git submodule update --depth 50 --init lib/chibios; fi
|
if [ ! -e lib/chibios ]; then git submodule sync lib/chibios && git submodule update --depth 50 --init lib/chibios; fi
|
||||||
if [ ! -e lib/chibios-contrib ]; then git submodule sync lib/chibios-contrib && git submodule update --depth 50 --init lib/chibios-contrib; fi
|
if [ ! -e lib/chibios-contrib ]; then git submodule sync lib/chibios-contrib && git submodule update --depth 50 --init lib/chibios-contrib; fi
|
||||||
if [ ! -e lib/ugfx ]; then git submodule sync lib/ugfx && git submodule update --depth 50 --init lib/ugfx; fi
|
if [ ! -e lib/ugfx ]; then git submodule sync lib/ugfx && git submodule update --depth 50 --init lib/ugfx; fi
|
||||||
if [ ! -e lib/lufa ]; then git submodule sync lib/lufa && git submodule update --depth 50 --init lib/lufa; fi
|
if [ ! -e lib/lufa ]; then git submodule sync lib/lufa && git submodule update --depth 50 --init lib/lufa; fi
|
||||||
|
if [ ! -e lib/vusb ]; then git submodule sync lib/vusb && git submodule update --depth 50 --init lib/vusb; fi
|
||||||
|
if [ ! -e lib/printf ]; then git submodule sync lib/printf && git submodule update --depth 50 --init lib/printf; fi
|
||||||
git submodule status --recursive 2>/dev/null | \
|
git submodule status --recursive 2>/dev/null | \
|
||||||
while IFS= read -r x; do \
|
while IFS= read -r x; do \
|
||||||
case "$$x" in \
|
case "$$x" in \
|
||||||
|
|||||||
Vendored
+1
-1
@@ -89,7 +89,7 @@ Vagrant.configure(2) do |config|
|
|||||||
|
|
||||||
Examples:
|
Examples:
|
||||||
make planck/rev4:default:dfu
|
make planck/rev4:default:dfu
|
||||||
make planck:default
|
make planck/rev4:default
|
||||||
|
|
||||||
EOT
|
EOT
|
||||||
end
|
end
|
||||||
@@ -1 +0,0 @@
|
|||||||
complete -W " 9key-default alps64-default amj40-default amj40-fabian amj60-default_60_ansi amj60-iso_split_rshift amj60-maximized amjpad-default amjpad-max amjpad-ortho_left amjpad-ortho_right atomic-default atomic-default_ortho_5x15 atomic-pvc atreus-alphadox atreus-classic atreus-default atreus-erlandsona atreus-gerb atreus-jeremy atreus-replicaJunction atreus-xyverz atreus62-atreus52 atreus62-default atreus62-mneme atreus62-xyverz bananasplit-0010 bananasplit-coloneljesus bananasplit-default bananasplit-hhkbanana bananasplit-nic bananasplit-rask bantam44-default chibios_test-default clueboard-bloodlvst clueboard-caps_fn clueboard-colemak clueboard-default clueboard-jokrik clueboard-mac_optimized clueboard-magicmonty clueboard-maximised clueboard-mouse_keys clueboard-serubin clueboard-shift_fn clueboard-skully clueboard-smt clueboard-tetris clueboard-unix_optimized clueboard-win_optimized clueboard-xyverz cluecard-default cluecard-rgb_effects cluepad-default deltasplit75-default deltasplit75-itsaferbie deltasplit75-protosplit dk60-default eco-default eco-that_canadian ergodone-333fred ergodone-ab ergodone-absenth ergodone-adam ergodone-adnw_k_o_y ergodone-albert ergodone-alexjj ergodone-algernon ergodone-alphadox ergodone-andrew_osx ergodone-belak ergodone-bepo ergodone-bepo_csa ergodone-bryan ergodone-coderkun_neo2 ergodone-colemak ergodone-colemak_osx_pc_no ergodone-colemak_programmer ergodone-common_nighthawk ergodone-csharp_dev ergodone-dave ergodone-deadcyclo ergodone-default ergodone-default_ergodox ergodone-dragon788 ergodone-dvorak ergodone-dvorak_emacs ergodone-dvorak_emacs_software ergodone-dvorak_intl_squisher ergodone-dvorak_plover ergodone-dvorak_programmer ergodone-dvorak_programmer_swe ergodone-dvorak_spanish ergodone-emacs_osx_dk ergodone-erez_experimental ergodone-familiar ergodone-french_hacker ergodone-galson ergodone-german ergodone-german-kinergo ergodone-german-lukas ergodone-german-manuneo ergodone-guni ergodone-ishigoya-jp ergodone-italian ergodone-j3rn ergodone-jack ergodone-jacobono ergodone-jafo ergodone-jgarr ergodone-josh ergodone-kastyle ergodone-kines-ish ergodone-kristian ergodone-maz ergodone-mclennon_osx ergodone-mpiechotka ergodone-msc ergodone-naps62 ergodone-neo2_on_qwertz_hardware ergodone-norwegian_programmer_osx_pc ergodone-norwegian_programmer_osx_pc_colemak ergodone-ordinary ergodone-osx_de ergodone-osx_de_adnw_koy ergodone-osx_de_experimental ergodone-osx_fr ergodone-osx_kinesis_pnut ergodone-osx_whiskey_tango_foxtrot_capslock ergodone-phoenix ergodone-plover ergodone-plums ergodone-pvinis ergodone-replicaJunction ergodone-reset_eeprom ergodone-robot_test_layout ergodone-romanzolotarev-norman-osx ergodone-romanzolotarev-norman-plover-osx ergodone-romanzolotarev-norman-plover-osx-hjkl ergodone-romanzolotarev-norman-qwerty-osx ergodone-sethbc ergodone-siroken3 ergodone-sneako ergodone-software_neo2 ergodone-supercoder ergodone-swedish ergodone-swedish-lindhe ergodone-swissgerman ergodone-techtomas ergodone-teckinesis ergodone-tkuichooseyou ergodone-tm2030 ergodone-tonyabra_osx ergodone-townk_osx ergodone-twentylives_dvorak_with_hebrew ergodone-twey ergodone-videck ergodone-win10_writers-block ergodone-workman_osx_mdw ergodone-xyverz ergodone-yoruian ergodone-zweihander-osx ergodox_ez-333fred ergodox_ez-ab ergodox_ez-absenth ergodox_ez-adam ergodox_ez-adnw_k_o_y ergodox_ez-albert ergodox_ez-alexjj ergodox_ez-algernon ergodox_ez-alphadox ergodox_ez-andrew_osx ergodox_ez-belak ergodox_ez-bepo ergodox_ez-bepo_csa ergodox_ez-blakedietz ergodox_ez-bryan ergodox_ez-coderkun_neo2 ergodox_ez-colemak ergodox_ez-colemak_osx_pc_no ergodox_ez-colemak_programmer ergodox_ez-common_nighthawk ergodox_ez-csharp_dev ergodox_ez-dave ergodox_ez-deadcyclo ergodox_ez-default ergodox_ez-default_ergodox ergodox_ez-default_osx ergodox_ez-dragon788 ergodox_ez-drashna ergodox_ez-drashna-custom ergodox_ez-dvorak ergodox_ez-dvorak_emacs ergodox_ez-dvorak_emacs_software ergodox_ez-dvorak_intl_squisher ergodox_ez-dvorak_plover ergodox_ez-dvorak_programmer ergodox_ez-dvorak_programmer_swe ergodox_ez-dvorak_spanish ergodox_ez-emacs_osx_dk ergodox_ez-erez_experimental ergodox_ez-familiar ergodox_ez-french_hacker ergodox_ez-galson ergodox_ez-german ergodox_ez-german-kinergo ergodox_ez-german-lukas ergodox_ez-german-manuneo ergodox_ez-guni ergodox_ez-ishigoya-jp ergodox_ez-italian ergodox_ez-j3rn ergodox_ez-jack ergodox_ez-jacobono ergodox_ez-jafo ergodox_ez-jgarr ergodox_ez-josh ergodox_ez-kastyle ergodox_ez-kines-ish ergodox_ez-kristian ergodox_ez-maz ergodox_ez-mclennon_osx ergodox_ez-mpiechotka ergodox_ez-msc ergodox_ez-naps62 ergodox_ez-neo2_on_qwertz_hardware ergodox_ez-norwegian_programmer_osx_pc ergodox_ez-norwegian_programmer_osx_pc_colemak ergodox_ez-ordinary ergodox_ez-osx_de ergodox_ez-osx_de_adnw_koy ergodox_ez-osx_de_experimental ergodox_ez-osx_fr ergodox_ez-osx_kinesis_pnut ergodox_ez-osx_whiskey_tango_foxtrot_capslock ergodox_ez-phoenix ergodox_ez-plover ergodox_ez-plums ergodox_ez-prLine truncated
|
|
||||||
@@ -2,52 +2,61 @@
|
|||||||
"""CLI wrapper for running QMK commands.
|
"""CLI wrapper for running QMK commands.
|
||||||
"""
|
"""
|
||||||
import os
|
import os
|
||||||
import subprocess
|
|
||||||
import sys
|
import sys
|
||||||
from importlib.util import find_spec
|
from importlib.util import find_spec
|
||||||
from time import strftime
|
from pathlib import Path
|
||||||
|
|
||||||
# Add the QMK python libs to our path
|
# Add the QMK python libs to our path
|
||||||
script_dir = os.path.dirname(os.path.realpath(__file__))
|
script_dir = Path(os.path.realpath(__file__)).parent
|
||||||
qmk_dir = os.path.abspath(os.path.join(script_dir, '..'))
|
qmk_dir = script_dir.parent
|
||||||
python_lib_dir = os.path.abspath(os.path.join(qmk_dir, 'lib', 'python'))
|
python_lib_dir = Path(qmk_dir / 'lib' / 'python').resolve()
|
||||||
sys.path.append(python_lib_dir)
|
sys.path.append(str(python_lib_dir))
|
||||||
|
|
||||||
# Make sure our modules have been setup
|
|
||||||
with open(os.path.join(qmk_dir, 'requirements.txt'), 'r') as fd:
|
|
||||||
for line in fd.readlines():
|
|
||||||
line = line.strip().replace('<', '=').replace('>', '=')
|
|
||||||
|
|
||||||
if line[0] == '#':
|
def _check_modules(requirements):
|
||||||
continue
|
""" Check if the modules in the given requirements.txt are available.
|
||||||
|
"""
|
||||||
|
with Path(qmk_dir / requirements).open() as fd:
|
||||||
|
for line in fd.readlines():
|
||||||
|
line = line.strip().replace('<', '=').replace('>', '=')
|
||||||
|
|
||||||
if '#' in line:
|
if len(line) == 0 or line[0] == '#' or line.startswith('-r'):
|
||||||
line = line.split('#')[0]
|
continue
|
||||||
|
|
||||||
module = line.split('=')[0] if '=' in line else line
|
if '#' in line:
|
||||||
|
line = line.split('#')[0]
|
||||||
|
|
||||||
|
module = dict()
|
||||||
|
module['name'] = module['import'] = line.split('=')[0] if '=' in line else line
|
||||||
|
|
||||||
if module in ['pep8-naming']:
|
|
||||||
# Not every module is importable by its own name.
|
# Not every module is importable by its own name.
|
||||||
continue
|
if module['name'] == "pep8-naming":
|
||||||
|
module['import'] = "pep8ext_naming"
|
||||||
|
|
||||||
if not find_spec(module):
|
if not find_spec(module['import']):
|
||||||
print('Could not find module %s!' % module)
|
print('Could not find module %s!' % module['name'])
|
||||||
print('Please run `pip3 install -r requirements.txt` to install the python dependencies.')
|
print('Please run `python3 -m pip install -r %s` to install required python dependencies.' % (qmk_dir / requirements,))
|
||||||
exit(255)
|
if developer:
|
||||||
|
print('You can also turn off developer mode: qmk config user.developer=None')
|
||||||
|
print()
|
||||||
|
exit(255)
|
||||||
|
|
||||||
# Figure out our version
|
|
||||||
# TODO(skullydazed/anyone): Find a method that doesn't involve git. This is slow in docker and on windows.
|
|
||||||
command = ['git', 'describe', '--abbrev=6', '--dirty', '--always', '--tags']
|
|
||||||
result = subprocess.run(command, universal_newlines=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
|
|
||||||
|
|
||||||
if result.returncode == 0:
|
developer = False
|
||||||
os.environ['QMK_VERSION'] = result.stdout.strip()
|
# Make sure our modules have been setup
|
||||||
else:
|
_check_modules('requirements.txt')
|
||||||
os.environ['QMK_VERSION'] = 'nogit-' + strftime('%Y-%m-%d-%H:%M:%S') + '-dirty'
|
|
||||||
|
|
||||||
# Setup the CLI
|
# Setup the CLI
|
||||||
import milc # noqa
|
import milc # noqa
|
||||||
|
|
||||||
|
# For developers additional modules are needed
|
||||||
|
if milc.cli.config.user.developer:
|
||||||
|
# Do not run the check for 'config',
|
||||||
|
# so users can turn off developer mode
|
||||||
|
if len(sys.argv) == 1 or (len(sys.argv) > 1 and 'config' != sys.argv[1]):
|
||||||
|
developer = True
|
||||||
|
_check_modules('requirements-dev.txt')
|
||||||
|
|
||||||
milc.EMOJI_LOGLEVELS['INFO'] = '{fg_blue}Ψ{style_reset_all}'
|
milc.EMOJI_LOGLEVELS['INFO'] = '{fg_blue}Ψ{style_reset_all}'
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
+6
-1
@@ -21,6 +21,11 @@ else ifneq ("$(wildcard $(MAIN_KEYMAP_PATH_1)/keymap.json)","")
|
|||||||
KEYMAP_PATH := $(MAIN_KEYMAP_PATH_1)
|
KEYMAP_PATH := $(MAIN_KEYMAP_PATH_1)
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
# Load the keymap-level rules.mk if exists
|
||||||
|
ifneq ("$(wildcard $(KEYMAP_PATH))", "")
|
||||||
|
-include $(KEYMAP_PATH)/rules.mk
|
||||||
|
endif
|
||||||
|
|
||||||
# Generate the keymap.c
|
# Generate the keymap.c
|
||||||
$(KEYBOARD_OUTPUT)/src/keymap.c: $(KEYMAP_JSON)
|
$(KEYBOARD_OUTPUT)/src/keymap.c: $(KEYMAP_JSON)
|
||||||
bin/qmk json-keymap --quiet --output $(KEYMAP_C) $(KEYMAP_JSON)
|
bin/qmk json2c --quiet --output $(KEYMAP_C) $(KEYMAP_JSON)
|
||||||
+12
-48
@@ -231,44 +231,19 @@ endif
|
|||||||
# We can assume a ChibiOS target When MCU_FAMILY is defined since it's
|
# We can assume a ChibiOS target When MCU_FAMILY is defined since it's
|
||||||
# not used for LUFA
|
# not used for LUFA
|
||||||
ifdef MCU_FAMILY
|
ifdef MCU_FAMILY
|
||||||
FIRMWARE_FORMAT?=bin
|
|
||||||
PLATFORM=CHIBIOS
|
PLATFORM=CHIBIOS
|
||||||
|
PLATFORM_KEY=chibios
|
||||||
|
FIRMWARE_FORMAT?=bin
|
||||||
else ifdef ARM_ATSAM
|
else ifdef ARM_ATSAM
|
||||||
PLATFORM=ARM_ATSAM
|
PLATFORM=ARM_ATSAM
|
||||||
|
PLATFORM_KEY=arm_atsam
|
||||||
FIRMWARE_FORMAT=bin
|
FIRMWARE_FORMAT=bin
|
||||||
else
|
else
|
||||||
PLATFORM=AVR
|
PLATFORM=AVR
|
||||||
|
PLATFORM_KEY=avr
|
||||||
FIRMWARE_FORMAT?=hex
|
FIRMWARE_FORMAT?=hex
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(PLATFORM),CHIBIOS)
|
|
||||||
include $(TMK_PATH)/chibios.mk
|
|
||||||
OPT_OS = chibios
|
|
||||||
ifneq ("$(wildcard $(KEYBOARD_PATH_5)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_5)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(KEYBOARD_PATH_5)/boards/$(BOARD)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_5)/boards/$(BOARD)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(KEYBOARD_PATH_4)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_4)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(KEYBOARD_PATH_4)/boards/$(BOARD)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_4)/boards/$(BOARD)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(KEYBOARD_PATH_3)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_3)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(KEYBOARD_PATH_3)/boards/$(BOARD)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_3)/boards/$(BOARD)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(KEYBOARD_PATH_2)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_2)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(KEYBOARD_PATH_2)/boards/$(BOARD)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_2)/boards/$(BOARD)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(KEYBOARD_PATH_1)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_1)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(KEYBOARD_PATH_1)/boards/$(BOARD)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(KEYBOARD_PATH_1)/boards/$(BOARD)/bootloader_defs.h
|
|
||||||
else ifneq ("$(wildcard $(TOP_DIR)/drivers/boards/$(BOARD)/bootloader_defs.h)","")
|
|
||||||
OPT_DEFS += -include $(TOP_DIR)/drivers/boards/$(BOARD)/bootloader_defs.h
|
|
||||||
endif
|
|
||||||
endif
|
|
||||||
|
|
||||||
# Find all of the config.h files and add them to our CONFIG_H define.
|
# Find all of the config.h files and add them to our CONFIG_H define.
|
||||||
CONFIG_H :=
|
CONFIG_H :=
|
||||||
ifneq ("$(wildcard $(KEYBOARD_PATH_5)/config.h)","")
|
ifneq ("$(wildcard $(KEYBOARD_PATH_5)/config.h)","")
|
||||||
@@ -304,11 +279,6 @@ ifneq ("$(wildcard $(KEYBOARD_PATH_5)/post_config.h)","")
|
|||||||
POST_CONFIG_H += $(KEYBOARD_PATH_5)/post_config.h
|
POST_CONFIG_H += $(KEYBOARD_PATH_5)/post_config.h
|
||||||
endif
|
endif
|
||||||
|
|
||||||
# Save the defines and includes here, so we don't include any keymap specific ones
|
|
||||||
PROJECT_DEFS := $(OPT_DEFS)
|
|
||||||
PROJECT_INC := $(VPATH) $(EXTRAINCDIRS) $(KEYBOARD_PATHS)
|
|
||||||
PROJECT_CONFIG := $(CONFIG_H)
|
|
||||||
|
|
||||||
# Userspace setup and definitions
|
# Userspace setup and definitions
|
||||||
ifeq ("$(USER_NAME)","")
|
ifeq ("$(USER_NAME)","")
|
||||||
USER_NAME := $(KEYMAP)
|
USER_NAME := $(KEYMAP)
|
||||||
@@ -354,23 +324,17 @@ SRC += $(TMK_COMMON_SRC)
|
|||||||
OPT_DEFS += $(TMK_COMMON_DEFS)
|
OPT_DEFS += $(TMK_COMMON_DEFS)
|
||||||
EXTRALDFLAGS += $(TMK_COMMON_LDFLAGS)
|
EXTRALDFLAGS += $(TMK_COMMON_LDFLAGS)
|
||||||
|
|
||||||
ifeq ($(PLATFORM),AVR)
|
include $(TMK_PATH)/$(PLATFORM_KEY).mk
|
||||||
ifeq ($(strip $(PROTOCOL)), VUSB)
|
ifneq ($(strip $(PROTOCOL)),)
|
||||||
include $(TMK_PATH)/protocol/vusb.mk
|
include $(TMK_PATH)/protocol/$(strip $(shell echo $(PROTOCOL) | tr '[:upper:]' '[:lower:]')).mk
|
||||||
else
|
else
|
||||||
include $(TMK_PATH)/protocol/lufa.mk
|
include $(TMK_PATH)/protocol/$(PLATFORM_KEY).mk
|
||||||
endif
|
|
||||||
include $(TMK_PATH)/avr.mk
|
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(PLATFORM),ARM_ATSAM)
|
# TODO: remove this bodge?
|
||||||
include $(TMK_PATH)/arm_atsam.mk
|
PROJECT_DEFS := $(OPT_DEFS)
|
||||||
include $(TMK_PATH)/protocol/arm_atsam.mk
|
PROJECT_INC := $(VPATH) $(EXTRAINCDIRS) $(KEYBOARD_PATHS)
|
||||||
endif
|
PROJECT_CONFIG := $(CONFIG_H)
|
||||||
|
|
||||||
ifeq ($(PLATFORM),CHIBIOS)
|
|
||||||
include $(TMK_PATH)/protocol/chibios.mk
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(VISUALIZER_ENABLE)), yes)
|
ifeq ($(strip $(VISUALIZER_ENABLE)), yes)
|
||||||
VISUALIZER_DIR = $(QUANTUM_DIR)/visualizer
|
VISUALIZER_DIR = $(QUANTUM_DIR)/visualizer
|
||||||
|
|||||||
+11
-2
@@ -3,8 +3,14 @@ LAYOUTS_REPOS := $(patsubst %/,%,$(sort $(dir $(wildcard $(LAYOUTS_PATH)/*/))))
|
|||||||
|
|
||||||
define SEARCH_LAYOUTS_REPO
|
define SEARCH_LAYOUTS_REPO
|
||||||
LAYOUT_KEYMAP_PATH := $$(LAYOUTS_REPO)/$$(LAYOUT)/$$(KEYMAP)
|
LAYOUT_KEYMAP_PATH := $$(LAYOUTS_REPO)/$$(LAYOUT)/$$(KEYMAP)
|
||||||
|
LAYOUT_KEYMAP_JSON := $$(LAYOUT_KEYMAP_PATH)/keymap.json
|
||||||
LAYOUT_KEYMAP_C := $$(LAYOUT_KEYMAP_PATH)/keymap.c
|
LAYOUT_KEYMAP_C := $$(LAYOUT_KEYMAP_PATH)/keymap.c
|
||||||
ifneq ("$$(wildcard $$(LAYOUT_KEYMAP_C))","")
|
ifneq ("$$(wildcard $$(LAYOUT_KEYMAP_JSON))","")
|
||||||
|
-include $$(LAYOUT_KEYMAP_PATH)/rules.mk
|
||||||
|
KEYMAP_C := $(KEYBOARD_OUTPUT)/src/keymap.c
|
||||||
|
KEYMAP_JSON := $$(LAYOUT_KEYMAP_JSON)
|
||||||
|
KEYMAP_PATH := $$(LAYOUT_KEYMAP_PATH)
|
||||||
|
else ifneq ("$$(wildcard $$(LAYOUT_KEYMAP_C))","")
|
||||||
-include $$(LAYOUT_KEYMAP_PATH)/rules.mk
|
-include $$(LAYOUT_KEYMAP_PATH)/rules.mk
|
||||||
KEYMAP_C := $$(LAYOUT_KEYMAP_C)
|
KEYMAP_C := $$(LAYOUT_KEYMAP_C)
|
||||||
KEYMAP_PATH := $$(LAYOUT_KEYMAP_PATH)
|
KEYMAP_PATH := $$(LAYOUT_KEYMAP_PATH)
|
||||||
@@ -24,4 +30,7 @@ ifneq ($(FORCE_LAYOUT),)
|
|||||||
endif
|
endif
|
||||||
endif
|
endif
|
||||||
|
|
||||||
$(foreach LAYOUT,$(LAYOUTS),$(eval $(call SEARCH_LAYOUTS)))
|
$(foreach LAYOUT,$(LAYOUTS),$(eval $(call SEARCH_LAYOUTS)))
|
||||||
|
|
||||||
|
# Use rule from build_json.mk, but update prerequisite in case KEYMAP_JSON was updated
|
||||||
|
$(KEYBOARD_OUTPUT)/src/keymap.c: $(KEYMAP_JSON)
|
||||||
@@ -41,6 +41,7 @@ all: elf
|
|||||||
|
|
||||||
VPATH += $(COMMON_VPATH)
|
VPATH += $(COMMON_VPATH)
|
||||||
PLATFORM:=TEST
|
PLATFORM:=TEST
|
||||||
|
PLATFORM_KEY:=test
|
||||||
|
|
||||||
ifneq ($(filter $(FULL_TESTS),$(TEST)),)
|
ifneq ($(filter $(FULL_TESTS),$(TEST)),)
|
||||||
include tests/$(TEST)/rules.mk
|
include tests/$(TEST)/rules.mk
|
||||||
|
|||||||
+120
-111
@@ -13,52 +13,42 @@
|
|||||||
# You should have received a copy of the GNU General Public License
|
# You should have received a copy of the GNU General Public License
|
||||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
SERIAL_DIR := $(QUANTUM_DIR)/serial_link
|
|
||||||
SERIAL_PATH := $(QUANTUM_PATH)/serial_link
|
SERIAL_PATH := $(QUANTUM_PATH)/serial_link
|
||||||
SERIAL_SRC := $(wildcard $(SERIAL_PATH)/protocol/*.c)
|
|
||||||
SERIAL_SRC += $(wildcard $(SERIAL_PATH)/system/*.c)
|
QUANTUM_SRC += \
|
||||||
SERIAL_DEFS += -DSERIAL_LINK_ENABLE
|
$(QUANTUM_DIR)/quantum.c \
|
||||||
COMMON_VPATH += $(SERIAL_PATH)
|
$(QUANTUM_DIR)/keymap_common.c \
|
||||||
|
$(QUANTUM_DIR)/keycode_config.c
|
||||||
|
|
||||||
ifeq ($(strip $(API_SYSEX_ENABLE)), yes)
|
ifeq ($(strip $(API_SYSEX_ENABLE)), yes)
|
||||||
OPT_DEFS += -DAPI_SYSEX_ENABLE
|
OPT_DEFS += -DAPI_SYSEX_ENABLE
|
||||||
SRC += $(QUANTUM_DIR)/api/api_sysex.c
|
|
||||||
OPT_DEFS += -DAPI_ENABLE
|
OPT_DEFS += -DAPI_ENABLE
|
||||||
SRC += $(QUANTUM_DIR)/api.c
|
|
||||||
MIDI_ENABLE=yes
|
MIDI_ENABLE=yes
|
||||||
|
SRC += $(QUANTUM_DIR)/api/api_sysex.c
|
||||||
|
SRC += $(QUANTUM_DIR)/api.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
MUSIC_ENABLE := 0
|
|
||||||
|
|
||||||
ifeq ($(strip $(AUDIO_ENABLE)), yes)
|
ifeq ($(strip $(AUDIO_ENABLE)), yes)
|
||||||
OPT_DEFS += -DAUDIO_ENABLE
|
OPT_DEFS += -DAUDIO_ENABLE
|
||||||
MUSIC_ENABLE := 1
|
MUSIC_ENABLE = yes
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_audio.c
|
SRC += $(QUANTUM_DIR)/process_keycode/process_audio.c
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_clicky.c
|
SRC += $(QUANTUM_DIR)/process_keycode/process_clicky.c
|
||||||
ifeq ($(PLATFORM),AVR)
|
SRC += $(QUANTUM_DIR)/audio/audio_$(PLATFORM_KEY).c
|
||||||
SRC += $(QUANTUM_DIR)/audio/audio.c
|
|
||||||
else
|
|
||||||
SRC += $(QUANTUM_DIR)/audio/audio_arm.c
|
|
||||||
endif
|
|
||||||
SRC += $(QUANTUM_DIR)/audio/voices.c
|
SRC += $(QUANTUM_DIR)/audio/voices.c
|
||||||
SRC += $(QUANTUM_DIR)/audio/luts.c
|
SRC += $(QUANTUM_DIR)/audio/luts.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(strip $(MIDI_ENABLE)), yes)
|
ifeq ($(strip $(MIDI_ENABLE)), yes)
|
||||||
OPT_DEFS += -DMIDI_ENABLE
|
OPT_DEFS += -DMIDI_ENABLE
|
||||||
MUSIC_ENABLE := 1
|
MUSIC_ENABLE = yes
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_midi.c
|
SRC += $(QUANTUM_DIR)/process_keycode/process_midi.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(MUSIC_ENABLE), 1)
|
MUSIC_ENABLE ?= no
|
||||||
|
ifeq ($(MUSIC_ENABLE), yes)
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_music.c
|
SRC += $(QUANTUM_DIR)/process_keycode/process_music.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(strip $(COMBO_ENABLE)), yes)
|
|
||||||
OPT_DEFS += -DCOMBO_ENABLE
|
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_combo.c
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(STENO_ENABLE)), yes)
|
ifeq ($(strip $(STENO_ENABLE)), yes)
|
||||||
OPT_DEFS += -DSTENO_ENABLE
|
OPT_DEFS += -DSTENO_ENABLE
|
||||||
VIRTSER_ENABLE ?= yes
|
VIRTSER_ENABLE ?= yes
|
||||||
@@ -80,29 +70,7 @@ ifeq ($(strip $(POINTING_DEVICE_ENABLE)), yes)
|
|||||||
SRC += $(QUANTUM_DIR)/pointing_device.c
|
SRC += $(QUANTUM_DIR)/pointing_device.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(strip $(UCIS_ENABLE)), yes)
|
VALID_EEPROM_DRIVER_TYPES := vendor custom transient i2c spi
|
||||||
OPT_DEFS += -DUCIS_ENABLE
|
|
||||||
UNICODE_COMMON := yes
|
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_ucis.c
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(UNICODEMAP_ENABLE)), yes)
|
|
||||||
OPT_DEFS += -DUNICODEMAP_ENABLE
|
|
||||||
UNICODE_COMMON := yes
|
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_unicodemap.c
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(UNICODE_ENABLE)), yes)
|
|
||||||
OPT_DEFS += -DUNICODE_ENABLE
|
|
||||||
UNICODE_COMMON := yes
|
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_unicode.c
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(UNICODE_COMMON)), yes)
|
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_unicode_common.c
|
|
||||||
endif
|
|
||||||
|
|
||||||
VALID_EEPROM_DRIVER_TYPES := vendor custom transient i2c
|
|
||||||
EEPROM_DRIVER ?= vendor
|
EEPROM_DRIVER ?= vendor
|
||||||
ifeq ($(filter $(EEPROM_DRIVER),$(VALID_EEPROM_DRIVER_TYPES)),)
|
ifeq ($(filter $(EEPROM_DRIVER),$(VALID_EEPROM_DRIVER_TYPES)),)
|
||||||
$(error EEPROM_DRIVER="$(EEPROM_DRIVER)" is not a valid EEPROM driver)
|
$(error EEPROM_DRIVER="$(EEPROM_DRIVER)" is not a valid EEPROM driver)
|
||||||
@@ -117,6 +85,11 @@ else
|
|||||||
COMMON_VPATH += $(DRIVER_PATH)/eeprom
|
COMMON_VPATH += $(DRIVER_PATH)/eeprom
|
||||||
QUANTUM_LIB_SRC += i2c_master.c
|
QUANTUM_LIB_SRC += i2c_master.c
|
||||||
SRC += eeprom_driver.c eeprom_i2c.c
|
SRC += eeprom_driver.c eeprom_i2c.c
|
||||||
|
else ifeq ($(strip $(EEPROM_DRIVER)), spi)
|
||||||
|
OPT_DEFS += -DEEPROM_DRIVER -DEEPROM_SPI
|
||||||
|
COMMON_VPATH += $(DRIVER_PATH)/eeprom
|
||||||
|
QUANTUM_LIB_SRC += spi_master.c
|
||||||
|
SRC += eeprom_driver.c eeprom_spi.c
|
||||||
else ifeq ($(strip $(EEPROM_DRIVER)), transient)
|
else ifeq ($(strip $(EEPROM_DRIVER)), transient)
|
||||||
OPT_DEFS += -DEEPROM_DRIVER -DEEPROM_TRANSIENT
|
OPT_DEFS += -DEEPROM_DRIVER -DEEPROM_TRANSIENT
|
||||||
COMMON_VPATH += $(DRIVER_PATH)/eeprom
|
COMMON_VPATH += $(DRIVER_PATH)/eeprom
|
||||||
@@ -141,6 +114,10 @@ else
|
|||||||
SRC += $(PLATFORM_COMMON_DIR)/flash_stm32.c
|
SRC += $(PLATFORM_COMMON_DIR)/flash_stm32.c
|
||||||
OPT_DEFS += -DEEPROM_EMU_STM32F072xB
|
OPT_DEFS += -DEEPROM_EMU_STM32F072xB
|
||||||
OPT_DEFS += -DSTM32_EEPROM_ENABLE
|
OPT_DEFS += -DSTM32_EEPROM_ENABLE
|
||||||
|
else ifneq ($(filter $(MCU_SERIES),STM32L0xx STM32L1xx),)
|
||||||
|
OPT_DEFS += -DEEPROM_DRIVER
|
||||||
|
COMMON_VPATH += $(DRIVER_PATH)/eeprom
|
||||||
|
SRC += eeprom_driver.c eeprom_stm32_L0_L1.c
|
||||||
else
|
else
|
||||||
# This will effectively work the same as "transient" if not supported by the chip
|
# This will effectively work the same as "transient" if not supported by the chip
|
||||||
SRC += $(PLATFORM_COMMON_DIR)/eeprom_teensy.c
|
SRC += $(PLATFORM_COMMON_DIR)/eeprom_teensy.c
|
||||||
@@ -167,7 +144,7 @@ ifeq ($(strip $(RGBLIGHT_ENABLE)), yes)
|
|||||||
endif
|
endif
|
||||||
endif
|
endif
|
||||||
|
|
||||||
VALID_MATRIX_TYPES := yes IS31FL3731 IS31FL3733 IS31FL3737 WS2812 custom
|
VALID_MATRIX_TYPES := yes IS31FL3731 IS31FL3733 IS31FL3737 IS31FL3741 WS2812 custom
|
||||||
|
|
||||||
LED_MATRIX_ENABLE ?= no
|
LED_MATRIX_ENABLE ?= no
|
||||||
ifneq ($(strip $(LED_MATRIX_ENABLE)), no)
|
ifneq ($(strip $(LED_MATRIX_ENABLE)), no)
|
||||||
@@ -228,6 +205,13 @@ ifeq ($(strip $(RGB_MATRIX_ENABLE)), IS31FL3737)
|
|||||||
QUANTUM_LIB_SRC += i2c_master.c
|
QUANTUM_LIB_SRC += i2c_master.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(RGB_MATRIX_ENABLE)), IS31FL3741)
|
||||||
|
OPT_DEFS += -DIS31FL3741 -DSTM32_I2C -DHAL_USE_I2C=TRUE
|
||||||
|
COMMON_VPATH += $(DRIVER_PATH)/issi
|
||||||
|
SRC += is31fl3741.c
|
||||||
|
QUANTUM_LIB_SRC += i2c_master.c
|
||||||
|
endif
|
||||||
|
|
||||||
ifeq ($(strip $(RGB_MATRIX_ENABLE)), WS2812)
|
ifeq ($(strip $(RGB_MATRIX_ENABLE)), WS2812)
|
||||||
OPT_DEFS += -DWS2812
|
OPT_DEFS += -DWS2812
|
||||||
WS2812_DRIVER_REQUIRED := yes
|
WS2812_DRIVER_REQUIRED := yes
|
||||||
@@ -245,31 +229,18 @@ ifeq ($(strip $(RGB_KEYCODES_ENABLE)), yes)
|
|||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_rgb.c
|
SRC += $(QUANTUM_DIR)/process_keycode/process_rgb.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(strip $(TAP_DANCE_ENABLE)), yes)
|
|
||||||
OPT_DEFS += -DTAP_DANCE_ENABLE
|
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_tap_dance.c
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(KEY_LOCK_ENABLE)), yes)
|
|
||||||
OPT_DEFS += -DKEY_LOCK_ENABLE
|
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_key_lock.c
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(PRINTING_ENABLE)), yes)
|
ifeq ($(strip $(PRINTING_ENABLE)), yes)
|
||||||
OPT_DEFS += -DPRINTING_ENABLE
|
OPT_DEFS += -DPRINTING_ENABLE
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_printer.c
|
SRC += $(QUANTUM_DIR)/process_keycode/process_printer.c
|
||||||
SRC += $(TMK_DIR)/protocol/serial_uart.c
|
SRC += $(TMK_DIR)/protocol/serial_uart.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(strip $(AUTO_SHIFT_ENABLE)), yes)
|
|
||||||
OPT_DEFS += -DAUTO_SHIFT_ENABLE
|
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_auto_shift.c
|
|
||||||
ifeq ($(strip $(AUTO_SHIFT_MODIFIERS)), yes)
|
|
||||||
OPT_DEFS += -DAUTO_SHIFT_MODIFIERS
|
|
||||||
endif
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(SERIAL_LINK_ENABLE)), yes)
|
ifeq ($(strip $(SERIAL_LINK_ENABLE)), yes)
|
||||||
|
SERIAL_SRC := $(wildcard $(SERIAL_PATH)/protocol/*.c)
|
||||||
|
SERIAL_SRC += $(wildcard $(SERIAL_PATH)/system/*.c)
|
||||||
|
SERIAL_DEFS += -DSERIAL_LINK_ENABLE
|
||||||
|
COMMON_VPATH += $(SERIAL_PATH)
|
||||||
|
|
||||||
SRC += $(patsubst $(QUANTUM_PATH)/%,%,$(SERIAL_SRC))
|
SRC += $(patsubst $(QUANTUM_PATH)/%,%,$(SERIAL_SRC))
|
||||||
OPT_DEFS += $(SERIAL_DEFS)
|
OPT_DEFS += $(SERIAL_DEFS)
|
||||||
VAPTH += $(SERIAL_PATH)
|
VAPTH += $(SERIAL_PATH)
|
||||||
@@ -311,11 +282,7 @@ ifeq ($(strip $(BACKLIGHT_ENABLE)), yes)
|
|||||||
else
|
else
|
||||||
SRC += $(QUANTUM_DIR)/backlight/backlight_driver_common.c
|
SRC += $(QUANTUM_DIR)/backlight/backlight_driver_common.c
|
||||||
ifeq ($(strip $(BACKLIGHT_DRIVER)), pwm)
|
ifeq ($(strip $(BACKLIGHT_DRIVER)), pwm)
|
||||||
ifeq ($(PLATFORM),AVR)
|
SRC += $(QUANTUM_DIR)/backlight/backlight_$(PLATFORM_KEY).c
|
||||||
SRC += $(QUANTUM_DIR)/backlight/backlight_avr.c
|
|
||||||
else
|
|
||||||
SRC += $(QUANTUM_DIR)/backlight/backlight_arm.c
|
|
||||||
endif
|
|
||||||
else
|
else
|
||||||
SRC += $(QUANTUM_DIR)/backlight/backlight_$(strip $(BACKLIGHT_DRIVER)).c
|
SRC += $(QUANTUM_DIR)/backlight/backlight_$(strip $(BACKLIGHT_DRIVER)).c
|
||||||
endif
|
endif
|
||||||
@@ -367,34 +334,16 @@ ifeq ($(strip $(USB_HID_ENABLE)), yes)
|
|||||||
include $(TMK_DIR)/protocol/usb_hid.mk
|
include $(TMK_DIR)/protocol/usb_hid.mk
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(WPM_ENABLE)), yes)
|
||||||
|
SRC += $(QUANTUM_DIR)/wpm.c
|
||||||
|
OPT_DEFS += -DWPM_ENABLE
|
||||||
|
endif
|
||||||
|
|
||||||
ifeq ($(strip $(ENCODER_ENABLE)), yes)
|
ifeq ($(strip $(ENCODER_ENABLE)), yes)
|
||||||
SRC += $(QUANTUM_DIR)/encoder.c
|
SRC += $(QUANTUM_DIR)/encoder.c
|
||||||
OPT_DEFS += -DENCODER_ENABLE
|
OPT_DEFS += -DENCODER_ENABLE
|
||||||
endif
|
endif
|
||||||
|
|
||||||
HAPTIC_ENABLE ?= no
|
|
||||||
ifneq ($(strip $(HAPTIC_ENABLE)),no)
|
|
||||||
COMMON_VPATH += $(DRIVER_PATH)/haptic
|
|
||||||
SRC += haptic.c
|
|
||||||
OPT_DEFS += -DHAPTIC_ENABLE
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifneq ($(filter DRV2605L, $(HAPTIC_ENABLE)), )
|
|
||||||
SRC += DRV2605L.c
|
|
||||||
QUANTUM_LIB_SRC += i2c_master.c
|
|
||||||
OPT_DEFS += -DDRV2605L
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifneq ($(filter SOLENOID, $(HAPTIC_ENABLE)), )
|
|
||||||
SRC += solenoid.c
|
|
||||||
OPT_DEFS += -DSOLENOID_ENABLE
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(HD44780_ENABLE)), yes)
|
|
||||||
SRC += drivers/avr/hd44780.c
|
|
||||||
OPT_DEFS += -DHD44780_ENABLE
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(strip $(VELOCIKEY_ENABLE)), yes)
|
ifeq ($(strip $(VELOCIKEY_ENABLE)), yes)
|
||||||
OPT_DEFS += -DVELOCIKEY_ENABLE
|
OPT_DEFS += -DVELOCIKEY_ENABLE
|
||||||
SRC += $(QUANTUM_DIR)/velocikey.c
|
SRC += $(QUANTUM_DIR)/velocikey.c
|
||||||
@@ -413,26 +362,11 @@ ifeq ($(strip $(DYNAMIC_KEYMAP_ENABLE)), yes)
|
|||||||
SRC += $(QUANTUM_DIR)/dynamic_keymap.c
|
SRC += $(QUANTUM_DIR)/dynamic_keymap.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
ifeq ($(strip $(LEADER_ENABLE)), yes)
|
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_leader.c
|
|
||||||
OPT_DEFS += -DLEADER_ENABLE
|
|
||||||
endif
|
|
||||||
|
|
||||||
|
|
||||||
ifeq ($(strip $(DIP_SWITCH_ENABLE)), yes)
|
ifeq ($(strip $(DIP_SWITCH_ENABLE)), yes)
|
||||||
SRC += $(QUANTUM_DIR)/dip_switch.c
|
OPT_DEFS += -DDIP_SWITCH_ENABLE
|
||||||
OPT_DEFS += -DDIP_SWITCH_ENABLE
|
SRC += $(QUANTUM_DIR)/dip_switch.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
include $(DRIVER_PATH)/qwiic/qwiic.mk
|
|
||||||
|
|
||||||
QUANTUM_SRC:= \
|
|
||||||
$(QUANTUM_DIR)/quantum.c \
|
|
||||||
$(QUANTUM_DIR)/keymap_common.c \
|
|
||||||
$(QUANTUM_DIR)/keycode_config.c
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
VALID_CUSTOM_MATRIX_TYPES:= yes lite no
|
VALID_CUSTOM_MATRIX_TYPES:= yes lite no
|
||||||
|
|
||||||
CUSTOM_MATRIX ?= no
|
CUSTOM_MATRIX ?= no
|
||||||
@@ -490,6 +424,29 @@ ifeq ($(strip $(SPLIT_KEYBOARD)), yes)
|
|||||||
COMMON_VPATH += $(QUANTUM_PATH)/split_common
|
COMMON_VPATH += $(QUANTUM_PATH)/split_common
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
HAPTIC_ENABLE ?= no
|
||||||
|
ifneq ($(strip $(HAPTIC_ENABLE)),no)
|
||||||
|
COMMON_VPATH += $(DRIVER_PATH)/haptic
|
||||||
|
SRC += haptic.c
|
||||||
|
OPT_DEFS += -DHAPTIC_ENABLE
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifneq ($(filter DRV2605L, $(HAPTIC_ENABLE)), )
|
||||||
|
SRC += DRV2605L.c
|
||||||
|
QUANTUM_LIB_SRC += i2c_master.c
|
||||||
|
OPT_DEFS += -DDRV2605L
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifneq ($(filter SOLENOID, $(HAPTIC_ENABLE)), )
|
||||||
|
SRC += solenoid.c
|
||||||
|
OPT_DEFS += -DSOLENOID_ENABLE
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(HD44780_ENABLE)), yes)
|
||||||
|
SRC += drivers/avr/hd44780.c
|
||||||
|
OPT_DEFS += -DHD44780_ENABLE
|
||||||
|
endif
|
||||||
|
|
||||||
ifeq ($(strip $(OLED_DRIVER_ENABLE)), yes)
|
ifeq ($(strip $(OLED_DRIVER_ENABLE)), yes)
|
||||||
OPT_DEFS += -DOLED_DRIVER_ENABLE
|
OPT_DEFS += -DOLED_DRIVER_ENABLE
|
||||||
COMMON_VPATH += $(DRIVER_PATH)/oled
|
COMMON_VPATH += $(DRIVER_PATH)/oled
|
||||||
@@ -497,10 +454,34 @@ ifeq ($(strip $(OLED_DRIVER_ENABLE)), yes)
|
|||||||
SRC += oled_driver.c
|
SRC += oled_driver.c
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
include $(DRIVER_PATH)/qwiic/qwiic.mk
|
||||||
|
|
||||||
|
ifeq ($(strip $(UCIS_ENABLE)), yes)
|
||||||
|
OPT_DEFS += -DUCIS_ENABLE
|
||||||
|
UNICODE_COMMON := yes
|
||||||
|
SRC += $(QUANTUM_DIR)/process_keycode/process_ucis.c
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(UNICODEMAP_ENABLE)), yes)
|
||||||
|
OPT_DEFS += -DUNICODEMAP_ENABLE
|
||||||
|
UNICODE_COMMON := yes
|
||||||
|
SRC += $(QUANTUM_DIR)/process_keycode/process_unicodemap.c
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(UNICODE_ENABLE)), yes)
|
||||||
|
OPT_DEFS += -DUNICODE_ENABLE
|
||||||
|
UNICODE_COMMON := yes
|
||||||
|
SRC += $(QUANTUM_DIR)/process_keycode/process_unicode.c
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(UNICODE_COMMON)), yes)
|
||||||
|
SRC += $(QUANTUM_DIR)/process_keycode/process_unicode_common.c
|
||||||
|
endif
|
||||||
|
|
||||||
SPACE_CADET_ENABLE ?= yes
|
SPACE_CADET_ENABLE ?= yes
|
||||||
ifeq ($(strip $(SPACE_CADET_ENABLE)), yes)
|
ifeq ($(strip $(SPACE_CADET_ENABLE)), yes)
|
||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_space_cadet.c
|
SRC += $(QUANTUM_DIR)/process_keycode/process_space_cadet.c
|
||||||
OPT_DEFS += -DSPACE_CADET_ENABLE
|
OPT_DEFS += -DSPACE_CADET_ENABLE
|
||||||
endif
|
endif
|
||||||
|
|
||||||
MAGIC_ENABLE ?= yes
|
MAGIC_ENABLE ?= yes
|
||||||
@@ -519,3 +500,31 @@ ifeq ($(strip $(DYNAMIC_MACRO_ENABLE)), yes)
|
|||||||
SRC += $(QUANTUM_DIR)/process_keycode/process_dynamic_macro.c
|
SRC += $(QUANTUM_DIR)/process_keycode/process_dynamic_macro.c
|
||||||
OPT_DEFS += -DDYNAMIC_MACRO_ENABLE
|
OPT_DEFS += -DDYNAMIC_MACRO_ENABLE
|
||||||
endif
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(COMBO_ENABLE)), yes)
|
||||||
|
SRC += $(QUANTUM_DIR)/process_keycode/process_combo.c
|
||||||
|
OPT_DEFS += -DCOMBO_ENABLE
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(TAP_DANCE_ENABLE)), yes)
|
||||||
|
SRC += $(QUANTUM_DIR)/process_keycode/process_tap_dance.c
|
||||||
|
OPT_DEFS += -DTAP_DANCE_ENABLE
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(KEY_LOCK_ENABLE)), yes)
|
||||||
|
SRC += $(QUANTUM_DIR)/process_keycode/process_key_lock.c
|
||||||
|
OPT_DEFS += -DKEY_LOCK_ENABLE
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(LEADER_ENABLE)), yes)
|
||||||
|
SRC += $(QUANTUM_DIR)/process_keycode/process_leader.c
|
||||||
|
OPT_DEFS += -DLEADER_ENABLE
|
||||||
|
endif
|
||||||
|
|
||||||
|
ifeq ($(strip $(AUTO_SHIFT_ENABLE)), yes)
|
||||||
|
SRC += $(QUANTUM_DIR)/process_keycode/process_auto_shift.c
|
||||||
|
OPT_DEFS += -DAUTO_SHIFT_ENABLE
|
||||||
|
ifeq ($(strip $(AUTO_SHIFT_MODIFIERS)), yes)
|
||||||
|
OPT_DEFS += -DAUTO_SHIFT_MODIFIERS
|
||||||
|
endif
|
||||||
|
endif
|
||||||
@@ -0,0 +1,239 @@
|
|||||||
|
# QMK Breaking Change - 2020 May 30 Changelog
|
||||||
|
|
||||||
|
Four times a year QMK runs a process for merging Breaking Changes. A Breaking Change is any change which modifies how QMK behaves in a way that is incompatible or potentially dangerous. We limit these changes to 4 times per year so that users can have confidence that updating their QMK tree will not break their keymaps.
|
||||||
|
|
||||||
|
The list of changes follows.
|
||||||
|
|
||||||
|
|
||||||
|
## Core Changes
|
||||||
|
|
||||||
|
### Converting V-USB usbdrv to a submodule
|
||||||
|
|
||||||
|
[#8321](https://github.com/qmk/qmk_firmware/pull/8321) and [qmk_compiler#62](https://github.com/qmk/qmk_compiler/pull/62).
|
||||||
|
|
||||||
|
These PRs move the V-USB driver code out of the qmk_firmware repository and into a submodule pointed at https://github.com/obdev/v-usb. This will make it easier to update the codebase if needed, while applying any potential QMK-specific modifications by forking it to the QMK GitHub organization.
|
||||||
|
|
||||||
|
### Unify Tap Hold functions and documentation
|
||||||
|
|
||||||
|
[#8348](https://github.com/qmk/qmk_firmware/pull/8348)
|
||||||
|
|
||||||
|
Updates all of the per key tap-hold functions to pass the `keyrecord_t` structure, and include documentation changes.
|
||||||
|
|
||||||
|
Any remaining versions or code outside of the main repo will need to be converted:
|
||||||
|
| Old function | New Function |
|
||||||
|
|------------------------------------------------------|---------------------------------------------------------------------------|
|
||||||
|
|`uint16_t get_tapping_term(uint16_t keycode)` |`uint16_t get_tapping_term(uint16_t keycode, keyrecord_t *record)` |
|
||||||
|
|`bool get_ignore_mod_tap_interrupt(uint16_t keycode)` |`bool get_ignore_mod_tap_interrupt(uint16_t keycode, keyrecord_t *record)` |
|
||||||
|
|
||||||
|
### Python Required In The Build Process
|
||||||
|
|
||||||
|
[#9000](https://github.com/qmk/qmk_firmware/pull/9000)
|
||||||
|
|
||||||
|
This is the last release of QMK that will work without having Python 3.6 (or later) installed. If your environment is not fully setup you will get a warning instructing you to set it up.
|
||||||
|
|
||||||
|
After the next breaking change you will not be able to build if `bin/qmk hello` does not work.
|
||||||
|
|
||||||
|
### Upgrade from tinyprintf to mpaland/printf
|
||||||
|
|
||||||
|
[#8269](https://github.com/qmk/qmk_firmware/pull/8269)
|
||||||
|
|
||||||
|
- Provides debug functionality on ChibiOS/ARM that is more compliant than previous integrations.
|
||||||
|
- Less maintenence, fewer QMK customisations, and allows QMK to sidestep previous compile and runtime issues.
|
||||||
|
- A `make git-submodule` may be required after pulling the latest QMK Firmware code to update to the new dependency.
|
||||||
|
|
||||||
|
### Fixed RGB_DISABLE_AFTER_TIMEOUT to be seconds based & small internals cleanup
|
||||||
|
|
||||||
|
[#6480](https://github.com/qmk/qmk_firmware/pull/6480)
|
||||||
|
|
||||||
|
- Changes `RGB_DISABLE_AFTER_TIMEOUT` to be based on milliseconds instead of ticks.
|
||||||
|
- Includes a code cleanup, resulting in a savings of 100 bytes, depending on features used.
|
||||||
|
- Fixed issues with timeouts / suspending at the wrong time not turning off all LEDs in some cases.
|
||||||
|
|
||||||
|
The `RGB_DISABLE_AFTER_TIMEOUT` definition is now deprecated, and has been superseded by `RGB_DISABLE_TIMEOUT`. To use the new definition, rename `RGB_DISABLE_AFTER_TIMEOUT` to `RGB_DISABLE_TIMEOUT` in your `config.h` file, and multiply the value set by 1200.
|
||||||
|
|
||||||
|
Before: `#define RGB_DISABLE_AFTER_TIMEOUT 100`
|
||||||
|
After: `#define RGB_DISABLE_TIMEOUT 120000`
|
||||||
|
|
||||||
|
### Switch to qmk forks for everything
|
||||||
|
|
||||||
|
[#9019](https://github.com/qmk/qmk_firmware/pull/9019)
|
||||||
|
|
||||||
|
Fork all QMK submodules to protect against upstream repositories disappearing.
|
||||||
|
|
||||||
|
### code cleanup regarding deprecated macro PLAY_NOTE_ARRAY by replacing it with PLAY_SONG
|
||||||
|
|
||||||
|
[#8484](https://github.com/qmk/qmk_firmware/pull/8484)
|
||||||
|
|
||||||
|
Removes the deprecated `PLAY_NOTE_ARRAY` macro. References to it are replaced with `PLAY_SONG`, which references the same function.
|
||||||
|
|
||||||
|
### fixing wrong configuration of AUDIO feature
|
||||||
|
|
||||||
|
[#8903](https://github.com/qmk/qmk_firmware/pull/8903) and [#8974](https://github.com/qmk/qmk_firmware/pull/8974)
|
||||||
|
|
||||||
|
`audio_avr.c` does not default to any pin; there has to be a #define XX_AUDIO in config.h at some level for Audio to actually work. Otherwise, the Audio code ends up cluttering the firmware, possibly breaking builds because the maximum allowed firmware size is exceeded.
|
||||||
|
|
||||||
|
These changes fix this by disabling Audio on keyboards that have the feature misconfigured, and therefore non-functional.
|
||||||
|
|
||||||
|
Also, add a compile-time error to alert the user to a missing pin-configuration (on AVR boards) when `AUDIO_ENABLE = yes` is set.
|
||||||
|
|
||||||
|
|
||||||
|
## Keyboard Refactors
|
||||||
|
|
||||||
|
### Migrating Lily58 to use split_common
|
||||||
|
|
||||||
|
[#6260](https://github.com/qmk/qmk_firmware/pull/6260)
|
||||||
|
|
||||||
|
Modifies the default firmware for Lily58 to use the `split_common` library, instead of including and depending on its own set of libraries for the following functionality:
|
||||||
|
|
||||||
|
- SSD1306 display
|
||||||
|
- i2c for OLED
|
||||||
|
- Serial Communication
|
||||||
|
|
||||||
|
This allows current lily58 firmware to advance with updates to the `split_common` library, which is shared with many other split keyboards.
|
||||||
|
|
||||||
|
#### To migrate existing Lily58 firmware:
|
||||||
|
|
||||||
|
[Changes to `config.h`](https://github.com/qmk/qmk_firmware/pull/6260/files#diff-445ac369c8717dcd6fc6fc3630836fc1):
|
||||||
|
- Remove `#define SSD1306OLED` from config.h
|
||||||
|
|
||||||
|
|
||||||
|
[Changes to `keymap.c`](https://github.com/qmk/qmk_firmware/pull/6260/files#diff-20943ea59856e9bdf3d99ecb2eee40b7):
|
||||||
|
- Find/Replace each instance of `#ifdef SSD1306OLED` with `#ifdef OLED_DRIVER_ENABLE`
|
||||||
|
- The following changes are for compatibility with the OLED driver. If you don't use the OLED driver you may safely delete [this section](https://github.com/qmk/qmk_firmware/blob/e6b9980bd45c186f7360df68c24b6e05a80c10dc/keyboards/lily58/keymaps/default/keymap.c#L144-L190)
|
||||||
|
- Alternatively, if you did not change the OLED code from that in `default`, you may find it easier to simply copy the [relevant section](https://github.com/qmk/qmk_firmware/blob/4ac310668501ae6786c711ecc8f01f62ddaa1c0b/keyboards/lily58/keymaps/default/keymap.c#L138-L172). Otherwise, the changes you need to make are as follows (sample change [here](https://github.com/qmk/qmk_firmware/pull/6260/files#diff-20943ea59856e9bdf3d99ecb2eee40b7R138-R173))
|
||||||
|
- [Remove](https://github.com/qmk/qmk_firmware/pull/6260/files#diff-20943ea59856e9bdf3d99ecb2eee40b7L138-L141) the block
|
||||||
|
```c
|
||||||
|
#ifdef SSD1306OLED
|
||||||
|
iota_gfx_init(!has_usb()); // turns on the display
|
||||||
|
#endif
|
||||||
|
```
|
||||||
|
- Within the block bounded by `#ifdef OLED_DRIVER_ENABLE` and `#endif // OLED_DRIVER_ENABLE`, add the following block to ensure that your two OLEDs are rotated correctly across the left and right sides:
|
||||||
|
```c
|
||||||
|
oled_rotation_t oled_init_user(oled_rotation_t rotation) {
|
||||||
|
if (!is_keyboard_master())
|
||||||
|
return OLED_ROTATION_180; // flips the display 180 degrees if offhand
|
||||||
|
return rotation;
|
||||||
|
}
|
||||||
|
```
|
||||||
|
- Remove the functions `matrix_scan_user`, `matrix_update` and `iota_gfx_task_user`
|
||||||
|
- Find/Replace `matrix_render_user(struct CharacterMatrix *matrix)` with `iota_gfx_task_user(void)`
|
||||||
|
- Find/Replace `is_master` with `is_keyboard_master()`
|
||||||
|
- For each instance of `matrix_write_ln(matrix, display_fn())`, rewrite it as `oled_write_ln(read_layer_state(), false);`
|
||||||
|
- For each instance of `matrix_write(matrix, read_logo());`, replace with `oled_write(read_logo(), false);`
|
||||||
|
|
||||||
|
### Refactor zinc to use split_common
|
||||||
|
|
||||||
|
[#7114](https://github.com/qmk/qmk_firmware/pull/7114) and [#9171](https://github.com/qmk/qmk_firmware/pull/9171)
|
||||||
|
|
||||||
|
* Refactor to use split_common and remove split codes under the zinc/revx/
|
||||||
|
* Add - backlight RGB LED and/or underglow RGB LED option
|
||||||
|
* Add - continuous RGB animations feature (between L and R halves)
|
||||||
|
* Fix - keymap files to adapt to changes
|
||||||
|
* all authors of keymaps confirmed this PR
|
||||||
|
* Update - documents and rules.mk
|
||||||
|
|
||||||
|
### Refactor of TKC1800 to use common OLED code
|
||||||
|
|
||||||
|
[#8472](https://github.com/qmk/qmk_firmware/pull/8472)
|
||||||
|
|
||||||
|
Modifies the default firmware for TKC1800 to use the in-built I2C and OLED drivers, instead of including and depending on its own set of libraries for the following functionality:
|
||||||
|
|
||||||
|
- SSD1306 display
|
||||||
|
- i2c for OLED
|
||||||
|
|
||||||
|
This allows current TKC1800 firmware to advance with updates to those drivers, which are shared with other keyboards.
|
||||||
|
|
||||||
|
#### To migrate existing TKC1800 firmware:
|
||||||
|
|
||||||
|
[Changes to `config.h`](https://github.com/qmk/qmk_firmware/pull/8472/files#diff-d10b26e676b4a55cbb00d71955116526):
|
||||||
|
- Remove `#define SSD1306OLED` from config.h
|
||||||
|
|
||||||
|
[Changes to `tkc1800.c`](https://github.com/qmk/qmk_firmware/pull/8472/files#diff-3b35bd30abe89c8110717c6972cd2cc5):
|
||||||
|
- Add the following to avoid debug errors on HID_listen if the screen is not present
|
||||||
|
```c
|
||||||
|
void keyboard_pre_init_kb(void) {
|
||||||
|
setPinInputHigh(D0);
|
||||||
|
setPinInputHigh(D1);
|
||||||
|
|
||||||
|
keyboard_pre_init_user();
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
[Changes to `keymap.c`](https://github.com/qmk/qmk_firmware/pull/8472/files#diff-05a2a344ce27e4d045fe68520ccd4771):
|
||||||
|
- Find/Replace each instance of `#ifdef SSD1306OLED` with `#ifdef OLED_DRIVER_ENABLE`
|
||||||
|
- The following changes are for compatibility with the OLED driver. If you don't use the OLED driver you may safely delete [this section](https://github.com/qmk/qmk_firmware/blob/e6b9980bd45c186f7360df68c24b6e05a80c10dc/keyboards/lily58/keymaps/default/keymap.c#L144-L190)
|
||||||
|
- [Remove](https://github.com/qmk/qmk_firmware/pull/6260/files#diff-20943ea59856e9bdf3d99ecb2eee40b7L91-L158) the block
|
||||||
|
```c
|
||||||
|
#ifdef SSD1306OLED
|
||||||
|
iota_gfx_init(!has_usb()); // turns on the display
|
||||||
|
#endif
|
||||||
|
```
|
||||||
|
- Within the block bounded by `#ifdef OLED_DRIVER_ENABLE` and `#endif // OLED_DRIVER_ENABLE`, add the following block to ensure that your two OLEDs are rotated correctly across the left and right sides:
|
||||||
|
```c
|
||||||
|
oled_rotation_t oled_init_user(oled_rotation_t rotation) {
|
||||||
|
if (!is_keyboard_master())
|
||||||
|
return OLED_ROTATION_180; // flips the display 180 degrees if offhand
|
||||||
|
return rotation;
|
||||||
|
}
|
||||||
|
```
|
||||||
|
- Remove the function `iota_gfx_task_user`
|
||||||
|
|
||||||
|
### Split HHKB to ANSI and JP layouts and Add VIA support for each
|
||||||
|
|
||||||
|
[#8582](https://github.com/qmk/qmk_firmware/pull/8582)
|
||||||
|
|
||||||
|
- Splits the HHKB codebase into two separate folders `keyboards/hhkb/ansi` and `keyboards/hhkb/jp`.
|
||||||
|
- Adds VIA Configurator support for both versions.
|
||||||
|
|
||||||
|
#### Migrating existing HHKB keymaps
|
||||||
|
|
||||||
|
- Remove any checks for the `HHKB_JP` definition
|
||||||
|
- All checks for this definition have been removed, and each version uses the source that is appropriate to that version.
|
||||||
|
- Move the directory for your keymap into the appropriate `keymaps` directory
|
||||||
|
- `keyboards/hhkb/ansi/keymaps/` for ANSI HHKBs
|
||||||
|
- `keyboards/hhkb/jp/keymaps/` for HHKB JPs
|
||||||
|
- Compile with the new keyboard names
|
||||||
|
- This PR changes the compilation instructions for the HHKB Alternate Controller. To compile firmware for this controller moving forward, use:
|
||||||
|
- `make hhkb/ansi` for ANSI-layout HHKBs
|
||||||
|
- `make hhkb/jp` for HHKB JP keyboards
|
||||||
|
|
||||||
|
|
||||||
|
## Keyboard Moves
|
||||||
|
|
||||||
|
- [#8412](https://github.com/qmk/qmk_firmware/pull/8412 "Changing board names to prevent confusion") by blindassassin111
|
||||||
|
- [#8499](https://github.com/qmk/qmk_firmware/pull/8499 "Move the Keyboardio Model01 to a keyboardio/ subdir") by algernon
|
||||||
|
- [#8830](https://github.com/qmk/qmk_firmware/pull/8830 "Move spaceman keyboards") by Spaceman (formerly known as Rionlion100)
|
||||||
|
- [#8537](https://github.com/qmk/qmk_firmware/pull/8537 "Organizing my keyboards (plaid, tartan, ergoinu)") by hsgw
|
||||||
|
|
||||||
|
Keyboards by Keyboardio, Spaceman, and hsgw move to vendor folders, while PCBs designed by blindassassin111 are renamed.
|
||||||
|
|
||||||
|
Old Name | New Name
|
||||||
|
:----------------- | :-----------------
|
||||||
|
2_milk | spaceman/2_milk
|
||||||
|
at101_blackheart | at101_bh
|
||||||
|
ergoinu | dm9records/ergoinu
|
||||||
|
model01 | keyboardio/model01
|
||||||
|
omnikey_blackheart | omnikey_bh
|
||||||
|
pancake | spaceman/pancake
|
||||||
|
plaid | dm9records/plaid
|
||||||
|
tartan | dm9records/tartan
|
||||||
|
z150_blackheart | z150_bh
|
||||||
|
|
||||||
|
If you own one of these PCBs, please use the new names to compile your firmware moving forward.
|
||||||
|
|
||||||
|
|
||||||
|
## Keycode Migration PRs
|
||||||
|
|
||||||
|
[#8954](https://github.com/qmk/qmk_firmware/pull/8954 "Migrate `ACTION_LAYER_TOGGLE` to `TG()`"), [#8957](https://github.com/qmk/qmk_firmware/pull/8957 "Migrate `ACTION_MODS_ONESHOT` to `OSM()`"), [#8958](https://github.com/qmk/qmk_firmware/pull/8958 "Migrate `ACTION_DEFAULT_LAYER_SET` to `DF()`"), [#8959](https://github.com/qmk/qmk_firmware/pull/8959 "Migrate `ACTION_LAYER_MODS` to `LM()`"), [#8968](https://github.com/qmk/qmk_firmware/pull/8968 "Migrate `ACTION_MODS_TAP_KEY` to `MT()`"), [#8977](https://github.com/qmk/qmk_firmware/pull/8977 "Migrate miscellaneous `fn_actions` entries"), and [#8979](https://github.com/qmk/qmk_firmware/pull/8979 "Migrate `ACTION_MODS_KEY` to chained mod keycodes")
|
||||||
|
|
||||||
|
Authored by fauxpark, these pull requests remove references to deprecated TMK macros that have been superseded by native QMK keycodes.
|
||||||
|
|
||||||
|
Old `fn_actions` action | New QMK keycode
|
||||||
|
:---------------------- | :--------------
|
||||||
|
`ACTION_DEFAULT_LAYER_SET(layer)` | `DF(layer)`
|
||||||
|
`ACTION_LAYER_MODS(layer, mod)` | `LM(layer, mod)`
|
||||||
|
`ACTION_LAYER_ONESHOT(mod)` | `OSL(mod)`
|
||||||
|
`ACTION_LAYER_TOGGLE(layer)` | `TG(layer)`
|
||||||
|
`ACTION_MODS_ONESHOT(mod)` | `OSM(mod)`
|
||||||
|
`ACTION_MODS_TAP_KEY(mod, kc)` | `MT(mod, kc)`
|
||||||
|
`ACTION_MODS_KEY(mod, kc)`<br>e.g. `ACTION_MODS_KEY(MOD_LCTL, KC_0)` | `MOD(kc)`<br>e.g. `LCTL(KC_0)`
|
||||||
+17
-4
@@ -6,6 +6,7 @@
|
|||||||
* [Testing and Debugging](newbs_testing_debugging.md)
|
* [Testing and Debugging](newbs_testing_debugging.md)
|
||||||
* [Getting Help/Support](support.md)
|
* [Getting Help/Support](support.md)
|
||||||
* [Other Resources](newbs_learn_more_resources.md)
|
* [Other Resources](newbs_learn_more_resources.md)
|
||||||
|
* [Syllabus](syllabus.md)
|
||||||
|
|
||||||
* FAQs
|
* FAQs
|
||||||
* [General FAQ](faq_general.md)
|
* [General FAQ](faq_general.md)
|
||||||
@@ -18,7 +19,6 @@
|
|||||||
* [Overview](newbs_building_firmware_configurator.md)
|
* [Overview](newbs_building_firmware_configurator.md)
|
||||||
* [Step by Step](configurator_step_by_step.md)
|
* [Step by Step](configurator_step_by_step.md)
|
||||||
* [Troubleshooting](configurator_troubleshooting.md)
|
* [Troubleshooting](configurator_troubleshooting.md)
|
||||||
* [Problems and Bugs](configurator_problems.md)
|
|
||||||
* QMK API
|
* QMK API
|
||||||
* [Overview](api_overview.md)
|
* [Overview](api_overview.md)
|
||||||
* [API Documentation](api_docs.md)
|
* [API Documentation](api_docs.md)
|
||||||
@@ -34,7 +34,9 @@
|
|||||||
* [Customizing Functionality](custom_quantum_functions.md)
|
* [Customizing Functionality](custom_quantum_functions.md)
|
||||||
* [Driver Installation with Zadig](driver_installation_zadig.md)
|
* [Driver Installation with Zadig](driver_installation_zadig.md)
|
||||||
* [Keymap Overview](keymap.md)
|
* [Keymap Overview](keymap.md)
|
||||||
* [Vagrant Guide](getting_started_vagrant.md)
|
* Development Environments
|
||||||
|
* [Docker Guide](getting_started_docker.md)
|
||||||
|
* [Vagrant Guide](getting_started_vagrant.md)
|
||||||
* Flashing
|
* Flashing
|
||||||
* [Flashing](flashing.md)
|
* [Flashing](flashing.md)
|
||||||
* [Flashing ATmega32A (ps2avrgb)](flashing_bootloadhid.md)
|
* [Flashing ATmega32A (ps2avrgb)](flashing_bootloadhid.md)
|
||||||
@@ -53,7 +55,8 @@
|
|||||||
* Simple Keycodes
|
* Simple Keycodes
|
||||||
* [Full List](keycodes.md)
|
* [Full List](keycodes.md)
|
||||||
* [Basic Keycodes](keycodes_basic.md)
|
* [Basic Keycodes](keycodes_basic.md)
|
||||||
* [Layer Switching](feature_advanced_keycodes.md)
|
* [Language-Specific Keycodes](reference_keymap_extras.md)
|
||||||
|
* [Modifier Keys](feature_advanced_keycodes.md)
|
||||||
* [Quantum Keycodes](quantum_keycodes.md)
|
* [Quantum Keycodes](quantum_keycodes.md)
|
||||||
|
|
||||||
* Advanced Keycodes
|
* Advanced Keycodes
|
||||||
@@ -72,14 +75,17 @@
|
|||||||
* [Combos](feature_combo.md)
|
* [Combos](feature_combo.md)
|
||||||
* [Debounce API](feature_debounce_type.md)
|
* [Debounce API](feature_debounce_type.md)
|
||||||
* [Key Lock](feature_key_lock.md)
|
* [Key Lock](feature_key_lock.md)
|
||||||
|
* [Layers](feature_layers.md)
|
||||||
* [One Shot Keys](one_shot_keys.md)
|
* [One Shot Keys](one_shot_keys.md)
|
||||||
* [Pointing Device](feature_pointing_device.md)
|
* [Pointing Device](feature_pointing_device.md)
|
||||||
|
* [Raw HID](feature_rawhid.md)
|
||||||
* [Swap Hands](feature_swap_hands.md)
|
* [Swap Hands](feature_swap_hands.md)
|
||||||
* [Tap Dance](feature_tap_dance.md)
|
* [Tap Dance](feature_tap_dance.md)
|
||||||
* [Tap-Hold Configuration](tap_hold.md)
|
* [Tap-Hold Configuration](tap_hold.md)
|
||||||
* [Terminal](feature_terminal.md)
|
* [Terminal](feature_terminal.md)
|
||||||
* [Unicode](feature_unicode.md)
|
* [Unicode](feature_unicode.md)
|
||||||
* [Userspace](feature_userspace.md)
|
* [Userspace](feature_userspace.md)
|
||||||
|
* [WPM Calculation](feature_wpm.md)
|
||||||
|
|
||||||
* Hardware Features
|
* Hardware Features
|
||||||
* Displays
|
* Displays
|
||||||
@@ -109,6 +115,7 @@
|
|||||||
* [Overview](breaking_changes.md)
|
* [Overview](breaking_changes.md)
|
||||||
* [My Pull Request Was Flagged](breaking_changes_instructions.md)
|
* [My Pull Request Was Flagged](breaking_changes_instructions.md)
|
||||||
* History
|
* History
|
||||||
|
* [2020 May 30](ChangeLog/20200530.md)
|
||||||
* [2020 Feb 29](ChangeLog/20200229.md)
|
* [2020 Feb 29](ChangeLog/20200229.md)
|
||||||
* [2019 Aug 30](ChangeLog/20190830.md)
|
* [2019 Aug 30](ChangeLog/20190830.md)
|
||||||
|
|
||||||
@@ -120,21 +127,27 @@
|
|||||||
* [Drivers](hardware_drivers.md)
|
* [Drivers](hardware_drivers.md)
|
||||||
* [ADC Driver](adc_driver.md)
|
* [ADC Driver](adc_driver.md)
|
||||||
* [I2C Driver](i2c_driver.md)
|
* [I2C Driver](i2c_driver.md)
|
||||||
|
* [SPI Driver](spi_driver.md)
|
||||||
* [WS2812 Driver](ws2812_driver.md)
|
* [WS2812 Driver](ws2812_driver.md)
|
||||||
* [EEPROM Driver](eeprom_driver.md)
|
* [EEPROM Driver](eeprom_driver.md)
|
||||||
|
* ['serial' Driver](serial_driver.md)
|
||||||
* [GPIO Controls](internals_gpio_control.md)
|
* [GPIO Controls](internals_gpio_control.md)
|
||||||
* [Keyboard Guidelines](hardware_keyboard_guidelines.md)
|
* [Keyboard Guidelines](hardware_keyboard_guidelines.md)
|
||||||
|
|
||||||
* Python Development
|
* Python Development
|
||||||
* [Coding Conventions](coding_conventions_python.md)
|
* [Coding Conventions](coding_conventions_python.md)
|
||||||
* [QMK CLI Development](cli_development.md)
|
* [QMK CLI Development](cli_development.md)
|
||||||
* [QMK CLI Config](cli_dev_configuration.md)
|
|
||||||
|
|
||||||
* Configurator Development
|
* Configurator Development
|
||||||
* QMK API
|
* QMK API
|
||||||
* [Development Environment](api_development_environment.md)
|
* [Development Environment](api_development_environment.md)
|
||||||
* [Architecture Overview](api_development_overview.md)
|
* [Architecture Overview](api_development_overview.md)
|
||||||
|
|
||||||
|
* Hardware Platform Development
|
||||||
|
* Arm/ChibiOS
|
||||||
|
* [Selecting an MCU](platformdev_selecting_arm_mcu.md)
|
||||||
|
* [Early initialization](platformdev_chibios_earlyinit.md)
|
||||||
|
|
||||||
* QMK Reference
|
* QMK Reference
|
||||||
* [Contributing to QMK](contributing.md)
|
* [Contributing to QMK](contributing.md)
|
||||||
* [Translating the QMK Docs](translating.md)
|
* [Translating the QMK Docs](translating.md)
|
||||||
|
|||||||
+106
-3
@@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
QMK can leverage the Analog-to-Digital Converter (ADC) on supported MCUs to measure voltages on certain pins. This can be useful for implementing things such as battery level indicators for Bluetooth keyboards, or volume controls using a potentiometer, as opposed to a [rotary encoder](feature_encoders.md).
|
QMK can leverage the Analog-to-Digital Converter (ADC) on supported MCUs to measure voltages on certain pins. This can be useful for implementing things such as battery level indicators for Bluetooth keyboards, or volume controls using a potentiometer, as opposed to a [rotary encoder](feature_encoders.md).
|
||||||
|
|
||||||
This driver is currently AVR-only. The values returned are 10-bit integers (0-1023) mapped between 0V and VCC (usually 5V or 3.3V).
|
This driver currently supports both AVR and a limited selection of ARM devices. The values returned are 10-bit integers (0-1023) mapped between 0V and VCC (usually 5V or 3.3V for AVR, 3.3V only for ARM), however on ARM there is more flexibility in control of operation through `#define`s if you need more precision.
|
||||||
|
|
||||||
## Usage
|
## Usage
|
||||||
|
|
||||||
@@ -20,7 +20,9 @@ Then place this include at the top of your code:
|
|||||||
|
|
||||||
## Channels
|
## Channels
|
||||||
|
|
||||||
|Channel|AT90USB64/128|ATmega16/32U4|ATmega32A|ATmega328P|
|
### AVR
|
||||||
|
|
||||||
|
|Channel|AT90USB64/128|ATmega16/32U4|ATmega32A|ATmega328/P|
|
||||||
|-------|-------------|-------------|---------|----------|
|
|-------|-------------|-------------|---------|----------|
|
||||||
|0 |`F0` |`F0` |`A0` |`C0` |
|
|0 |`F0` |`F0` |`A0` |`C0` |
|
||||||
|1 |`F1` |`F1` |`A1` |`C1` |
|
|1 |`F1` |`F1` |`A1` |`C1` |
|
||||||
@@ -37,10 +39,86 @@ Then place this include at the top of your code:
|
|||||||
|12 | |`B5` | | |
|
|12 | |`B5` | | |
|
||||||
|13 | |`B6` | | |
|
|13 | |`B6` | | |
|
||||||
|
|
||||||
<sup>\* The ATmega328P possesses two extra ADC channels; however, they are not present on the DIP pinout, and are not shared with GPIO pins. You can use `adc_read()` directly to gain access to these.</sup>
|
<sup>\* The ATmega328/P possesses two extra ADC channels; however, they are not present on the DIP pinout, and are not shared with GPIO pins. You can use `adc_read()` directly to gain access to these.</sup>
|
||||||
|
|
||||||
|
### ARM
|
||||||
|
|
||||||
|
Note that some of these pins are doubled-up on ADCs with the same channel. This is because the pins can be used for either ADC.
|
||||||
|
|
||||||
|
Also note that the F0 and F3 use different numbering schemes. The F0 has a single ADC and the channels are 0-based, whereas the F3 has 4 ADCs and the channels are 1 based. This is because the F0 uses the `ADCv1` implementation of the ADC, whereas the F3 uses the `ADCv3` implementation.
|
||||||
|
|
||||||
|
|ADC|Channel|STM32F0XX|STM32F3XX|
|
||||||
|
|---|-------|---------|---------|
|
||||||
|
|1 |0 |`A0` | |
|
||||||
|
|1 |1 |`A1` |`A0` |
|
||||||
|
|1 |2 |`A2` |`A1` |
|
||||||
|
|1 |3 |`A3` |`A2` |
|
||||||
|
|1 |4 |`A4` |`A3` |
|
||||||
|
|1 |5 |`A5` |`F4` |
|
||||||
|
|1 |6 |`A6` |`C0` |
|
||||||
|
|1 |7 |`A7` |`C1` |
|
||||||
|
|1 |8 |`B0` |`C2` |
|
||||||
|
|1 |9 |`B1` |`C3` |
|
||||||
|
|1 |10 |`C0` |`F2` |
|
||||||
|
|1 |11 |`C1` | |
|
||||||
|
|1 |12 |`C2` | |
|
||||||
|
|1 |13 |`C3` | |
|
||||||
|
|1 |14 |`C4` | |
|
||||||
|
|1 |15 |`C5` | |
|
||||||
|
|1 |16 | | |
|
||||||
|
|2 |1 | |`A4` |
|
||||||
|
|2 |2 | |`A5` |
|
||||||
|
|2 |3 | |`A6` |
|
||||||
|
|2 |4 | |`A7` |
|
||||||
|
|2 |5 | |`C4` |
|
||||||
|
|2 |6 | |`C0` |
|
||||||
|
|2 |7 | |`C1` |
|
||||||
|
|2 |8 | |`C2` |
|
||||||
|
|2 |9 | |`C3` |
|
||||||
|
|2 |10 | |`F2` |
|
||||||
|
|2 |11 | |`C5` |
|
||||||
|
|2 |12 | |`B2` |
|
||||||
|
|2 |13 | | |
|
||||||
|
|2 |14 | | |
|
||||||
|
|2 |15 | | |
|
||||||
|
|2 |16 | | |
|
||||||
|
|3 |1 | |`B1` |
|
||||||
|
|3 |2 | |`E9` |
|
||||||
|
|3 |3 | |`E13` |
|
||||||
|
|3 |4 | | |
|
||||||
|
|3 |5 | | |
|
||||||
|
|3 |6 | |`E8` |
|
||||||
|
|3 |7 | |`D10` |
|
||||||
|
|3 |8 | |`D11` |
|
||||||
|
|3 |9 | |`D12` |
|
||||||
|
|3 |10 | |`D13` |
|
||||||
|
|3 |11 | |`D14` |
|
||||||
|
|3 |12 | |`B0` |
|
||||||
|
|3 |13 | |`E7` |
|
||||||
|
|3 |14 | |`E10` |
|
||||||
|
|3 |15 | |`E11` |
|
||||||
|
|3 |16 | |`E12` |
|
||||||
|
|4 |1 | |`E14` |
|
||||||
|
|4 |2 | |`B12` |
|
||||||
|
|4 |3 | |`B13` |
|
||||||
|
|4 |4 | |`B14` |
|
||||||
|
|4 |5 | |`B15` |
|
||||||
|
|4 |6 | |`E8` |
|
||||||
|
|4 |7 | |`D10` |
|
||||||
|
|4 |8 | |`D11` |
|
||||||
|
|4 |9 | |`D12` |
|
||||||
|
|4 |10 | |`D13` |
|
||||||
|
|4 |11 | |`D14` |
|
||||||
|
|4 |12 | |`D8` |
|
||||||
|
|4 |13 | |`D9` |
|
||||||
|
|4 |14 | | |
|
||||||
|
|4 |15 | | |
|
||||||
|
|4 |16 | | |
|
||||||
|
|
||||||
## Functions
|
## Functions
|
||||||
|
|
||||||
|
### AVR
|
||||||
|
|
||||||
|Function |Description |
|
|Function |Description |
|
||||||
|----------------------------|-------------------------------------------------------------------------------------------------------------------|
|
|----------------------------|-------------------------------------------------------------------------------------------------------------------|
|
||||||
|`analogReference(mode)` |Sets the analog voltage reference source. Must be one of `ADC_REF_EXTERNAL`, `ADC_REF_POWER` or `ADC_REF_INTERNAL`.|
|
|`analogReference(mode)` |Sets the analog voltage reference source. Must be one of `ADC_REF_EXTERNAL`, `ADC_REF_POWER` or `ADC_REF_INTERNAL`.|
|
||||||
@@ -48,3 +126,28 @@ Then place this include at the top of your code:
|
|||||||
|`analogReadPin(pin)` |Reads the value from the specified QMK pin, eg. `F6` for ADC6 on the ATmega32U4. |
|
|`analogReadPin(pin)` |Reads the value from the specified QMK pin, eg. `F6` for ADC6 on the ATmega32U4. |
|
||||||
|`pinToMux(pin)` |Translates a given QMK pin to a mux value. If an unsupported pin is given, returns the mux value for "0V (GND)". |
|
|`pinToMux(pin)` |Translates a given QMK pin to a mux value. If an unsupported pin is given, returns the mux value for "0V (GND)". |
|
||||||
|`adc_read(mux)` |Reads the value from the ADC according to the specified mux. See your MCU's datasheet for more information. |
|
|`adc_read(mux)` |Reads the value from the ADC according to the specified mux. See your MCU's datasheet for more information. |
|
||||||
|
|
||||||
|
### ARM
|
||||||
|
|
||||||
|
Note that care was taken to match all of the functions used for AVR devices, however complications in the ARM platform prevent that from always being possible. For example, the `STM32` chips do not have assigned Arduino pins. We could use the default pin numbers, but those numbers change based on the package type of the device. For this reason, please specify your target pins with their identifiers (`A0`, `F3`, etc.). Also note that there are some variants of functions that accept the target ADC for the pin. Some pins can be used for multiple ADCs, and this specified can help you pick which ADC will be used to interact with that pin.
|
||||||
|
|
||||||
|
|Function |Description |
|
||||||
|
|----------------------------|--------------------------------------------------------------------------------------------------------------------|
|
||||||
|
|`analogReadPin(pin)` |Reads the value from the specified QMK pin, eg. `A0` for channel 0 on the STM32F0 and ADC1 channel 1 on the STM32F3. Note that if a pin can be used for multiple ADCs, it will pick the lower numbered ADC for this function. eg. `C0` will be channel 6 of ADC 1 when it could be used for ADC 2 as well.|
|
||||||
|
|`analogReadPinAdc(pin, adc)`|Reads the value from the specified QMK pin and ADC, eg. `C0, 1` will read from channel 6, ADC 2 instead of ADC 1. Note that the ADCs are 0-indexed for this function.|
|
||||||
|
|`pinToMux(pin)` |Translates a given QMK pin to a channel and ADC combination. If an unsupported pin is given, returns the mux value for "0V (GND)".|
|
||||||
|
|`adc_read(mux)` |Reads the value from the ADC according to the specified pin and adc combination. See your MCU's datasheet for more information.|
|
||||||
|
|
||||||
|
## Configuration
|
||||||
|
|
||||||
|
## ARM
|
||||||
|
|
||||||
|
The ARM implementation of the ADC has a few additional options that you can override in your own keyboards and keymaps to change how it operates.
|
||||||
|
|
||||||
|
|`#define` |Type |Default |Description|
|
||||||
|
|-------------------|------|---------------------|-----------|
|
||||||
|
|ADC_CIRCULAR_BUFFER|`bool`|`false` |If `TRUE`, then the implementation will use a circular buffer.|
|
||||||
|
|ADC_NUM_CHANNELS |`int` |`1` |Sets the number of channels that will be scanned as part of an ADC operation. The current implementation only supports `1`.|
|
||||||
|
|ADC_BUFFER_DEPTH |`int` |`2` |Sets the depth of each result. Since we are only getting a 12-bit result by default, we set this to `2` bytes so we can contain our one value. This could be set to 1 if you opt for a 8-bit or lower result.|
|
||||||
|
|ADC_SAMPLING_RATE |`int` |`ADC_SMPR_SMP_1P5` |Sets the sampling rate of the ADC. By default, it is set to the fastest setting. Please consult the corresponding `hal_adc_lld.h` in ChibiOS for your specific microcontroller for further documentation on your available options.|
|
||||||
|
|ADC_RESOLUTION |`int` |`ADC_CFGR1_RES_12BIT`|The resolution of your result. We choose 12 bit by default, but you can opt for 12, 10, 8, or 6 bit. Please consult the corresponding `hal_adc_lld.h` in ChibiOS for your specific microcontroller for further documentation on your available options.|
|
||||||
+24
-23
@@ -6,27 +6,28 @@ The breaking change period is when we will merge PR's that change QMK in dangero
|
|||||||
|
|
||||||
## What has been included in past Breaking Changes?
|
## What has been included in past Breaking Changes?
|
||||||
|
|
||||||
|
* [2020 May 30](ChangeLog/20200530.md)
|
||||||
* [2020 Feb 29](ChangeLog/20200229.md)
|
* [2020 Feb 29](ChangeLog/20200229.md)
|
||||||
* [2019 Aug 30](ChangeLog/20190830.md)
|
* [2019 Aug 30](ChangeLog/20190830.md)
|
||||||
|
|
||||||
## When is the next Breaking Change?
|
## When is the next Breaking Change?
|
||||||
|
|
||||||
The next Breaking Change is scheduled for May 30, 2020.
|
The next Breaking Change is scheduled for Aug 29, 2020.
|
||||||
|
|
||||||
### Important Dates
|
### Important Dates
|
||||||
|
|
||||||
* [x] 2020 Feb 29 - `future` is created. It will be rebased weekly.
|
* [x] 2020 May 30 - `develop` is created. It will be rebased weekly.
|
||||||
* [ ] 2020 May 2 - `future` closed to new PR's.
|
* [ ] 2020 Aug 1 - `develop` closed to new PR's.
|
||||||
* [ ] 2020 May 2 - Call for testers.
|
* [ ] 2020 Aug 1 - Call for testers.
|
||||||
* [ ] 2020 May 28 - `master` is locked, no PR's merged.
|
* [ ] 2020 Aug 27 - `master` is locked, no PR's merged.
|
||||||
* [ ] 2020 May 30 - Merge `future` to `master`.
|
* [ ] 2020 Aug 29 - Merge `develop` to `master`.
|
||||||
* [ ] 2020 May 30 - `master` is unlocked. PR's can be merged again.
|
* [ ] 2020 Aug 29 - `master` is unlocked. PR's can be merged again.
|
||||||
|
|
||||||
## What changes will be included?
|
## What changes will be included?
|
||||||
|
|
||||||
To see a list of breaking change candidates you can look at the [`breaking_change` label](https://github.com/qmk/qmk_firmware/pulls?q=is%3Aopen+label%3Abreaking_change+is%3Apr). New changes might be added between now and when `future` is closed, and a PR with that label applied is not guaranteed to be merged.
|
To see a list of breaking change candidates you can look at the [`breaking_change` label](https://github.com/qmk/qmk_firmware/pulls?q=is%3Aopen+label%3Abreaking_change+is%3Apr). New changes might be added between now and when `develop` is closed, and a PR with that label applied is not guaranteed to be merged.
|
||||||
|
|
||||||
If you want your breaking change to be included in this round you need to create a PR with the `breaking_change` label and have it accepted before `future` closes. After `future` closes no new breaking changes will be accepted.
|
If you want your breaking change to be included in this round you need to create a PR with the `breaking_change` label and have it accepted before `develop` closes. After `develop` closes no new breaking changes will be accepted.
|
||||||
|
|
||||||
Criteria for acceptance:
|
Criteria for acceptance:
|
||||||
|
|
||||||
@@ -37,9 +38,9 @@ Criteria for acceptance:
|
|||||||
|
|
||||||
This section documents various processes we use when running the Breaking Changes process.
|
This section documents various processes we use when running the Breaking Changes process.
|
||||||
|
|
||||||
## Rebase `future` from `master`
|
## Rebase `develop` from `master`
|
||||||
|
|
||||||
This is run every Friday while `future` is open.
|
This is run every Friday while `develop` is open.
|
||||||
|
|
||||||
Process:
|
Process:
|
||||||
|
|
||||||
@@ -47,31 +48,31 @@ Process:
|
|||||||
cd qmk_firmware
|
cd qmk_firmware
|
||||||
git checkout master
|
git checkout master
|
||||||
git pull --ff-only
|
git pull --ff-only
|
||||||
git checkout future
|
git checkout develop
|
||||||
git rebase master
|
git rebase master
|
||||||
git push --force
|
git push --force
|
||||||
```
|
```
|
||||||
|
|
||||||
## Creating the `future` branch
|
## Creating the `develop` branch
|
||||||
|
|
||||||
This happens immediately after the previous `future` branch is merged.
|
This happens immediately after the previous `develop` branch is merged.
|
||||||
|
|
||||||
* `qmk_firmware` git commands
|
* `qmk_firmware` git commands
|
||||||
* [ ] `git checkout master`
|
* [ ] `git checkout master`
|
||||||
* [ ] `git pull --ff-only`
|
* [ ] `git pull --ff-only`
|
||||||
* [ ] `git checkout -b future`
|
* [ ] `git checkout -b develop`
|
||||||
* [ ] Edit `readme.md`
|
* [ ] Edit `readme.md`
|
||||||
* [ ] Add a big notice at the top that this is a testing branch.
|
* [ ] Add a big notice at the top that this is a testing branch.
|
||||||
* [ ] Include a link to this document
|
* [ ] Include a link to this document
|
||||||
* [ ] `git commit -m 'Branch point for <DATE> Breaking Change'`
|
* [ ] `git commit -m 'Branch point for <DATE> Breaking Change'`
|
||||||
* [ ] `git tag breakpoint_<YYYY>_<MM>_<DD>`
|
* [ ] `git tag breakpoint_<YYYY>_<MM>_<DD>`
|
||||||
* [ ] `git tag <next_version>` # Prevent the breakpoint tag from confusing version incrementing
|
* [ ] `git tag <next_version>` # Prevent the breakpoint tag from confusing version incrementing
|
||||||
* [ ] `git push origin future`
|
* [ ] `git push origin develop`
|
||||||
* [ ] `git push --tags`
|
* [ ] `git push --tags`
|
||||||
|
|
||||||
## 4 Weeks Before Merge
|
## 4 Weeks Before Merge
|
||||||
|
|
||||||
* `future` is now closed to new PR's, only fixes for current PR's may be merged
|
* `develop` is now closed to new PR's, only fixes for current PR's may be merged
|
||||||
* Post call for testers
|
* Post call for testers
|
||||||
* [ ] Discord
|
* [ ] Discord
|
||||||
* [ ] GitHub PR
|
* [ ] GitHub PR
|
||||||
@@ -94,15 +95,15 @@ This happens immediately after the previous `future` branch is merged.
|
|||||||
## Day Of Merge
|
## Day Of Merge
|
||||||
|
|
||||||
* `qmk_firmware` git commands
|
* `qmk_firmware` git commands
|
||||||
* [ ] `git checkout future`
|
* [ ] `git checkout develop`
|
||||||
* [ ] `git pull --ff-only`
|
* [ ] `git pull --ff-only`
|
||||||
* [ ] `git rebase origin/master`
|
* [ ] `git rebase origin/master`
|
||||||
* [ ] Edit `readme.md`
|
* [ ] Edit `readme.md`
|
||||||
* [ ] Remove the notes about `future`
|
* [ ] Remove the notes about `develop`
|
||||||
* [ ] Roll up the ChangeLog into one file.
|
* [ ] Roll up the ChangeLog into one file.
|
||||||
* [ ] `git commit -m 'Merge point for <DATE> Breaking Change'`
|
* [ ] `git commit -m 'Merge point for <DATE> Breaking Change'`
|
||||||
* [ ] `git push origin future`
|
* [ ] `git push origin develop`
|
||||||
* Github Actions
|
* GitHub Actions
|
||||||
* [ ] Create a PR for `future`
|
* [ ] Create a PR for `develop`
|
||||||
* [ ] Make sure travis comes back clean
|
* [ ] Make sure travis comes back clean
|
||||||
* [ ] Merge `future` PR
|
* [ ] Merge `develop` PR
|
||||||
@@ -27,7 +27,7 @@ If you are contributing core code, and the only reason it needs to go through br
|
|||||||
|
|
||||||
We require submissions that go through the Breaking Change process to include a changelog entry. The entry should be a short summary of the changes your pull request makes – [each section here started as a changelog](ChangeLog/20190830.md "n.b. This should link to the 2019 Aug 30 Breaking Changes doc - @noroadsleft").
|
We require submissions that go through the Breaking Change process to include a changelog entry. The entry should be a short summary of the changes your pull request makes – [each section here started as a changelog](ChangeLog/20190830.md "n.b. This should link to the 2019 Aug 30 Breaking Changes doc - @noroadsleft").
|
||||||
|
|
||||||
Your changelog should be located at `docs/ChangeLog/YYYYMMDD/PR####.md`, where `YYYYMMDD` is the date on which QMK's breaking change branch – usually named `future` – will be merged into the `master` branch, and `####` is the number of your pull request.
|
Your changelog should be located at `docs/ChangeLog/YYYYMMDD/PR####.md`, where `YYYYMMDD` is the date on which QMK's breaking change branch – usually named `develop` – will be merged into the `master` branch, and `####` is the number of your pull request.
|
||||||
|
|
||||||
If your submission requires action on the part of users, your changelog should instruct users what action(s) must be taken, or link to a location that does so.
|
If your submission requires action on the part of users, your changelog should instruct users what action(s) must be taken, or link to a location that does so.
|
||||||
|
|
||||||
|
|||||||
+10
-286
@@ -1,45 +1,34 @@
|
|||||||
# QMK CLI
|
# QMK CLI :id=qmk-cli
|
||||||
|
|
||||||
This page describes how to setup and use the QMK CLI.
|
## Overview :id=overview
|
||||||
|
|
||||||
# Overview
|
|
||||||
|
|
||||||
The QMK CLI makes building and working with QMK keyboards easier. We have provided a number of commands to simplify and streamline tasks such as obtaining and compiling the QMK firmware, creating keymaps, and more.
|
The QMK CLI makes building and working with QMK keyboards easier. We have provided a number of commands to simplify and streamline tasks such as obtaining and compiling the QMK firmware, creating keymaps, and more.
|
||||||
|
|
||||||
* [Global CLI](#global-cli)
|
### Requirements :id=requirements
|
||||||
* [Local CLI](#local-cli)
|
|
||||||
* [CLI Commands](#cli-commands)
|
|
||||||
|
|
||||||
# Requirements
|
QMK requires Python 3.6 or greater. We try to keep the number of requirements small but you will also need to install the packages listed in [`requirements.txt`](https://github.com/qmk/qmk_firmware/blob/master/requirements.txt). These are installed automatically when you install the QMK CLI.
|
||||||
|
|
||||||
The CLI requires Python 3.5 or greater. We try to keep the number of requirements small but you will also need to install the packages listed in [`requirements.txt`](https://github.com/qmk/qmk_firmware/blob/master/requirements.txt).
|
### Install Using Homebrew (macOS, some Linux) :id=install-using-homebrew
|
||||||
|
|
||||||
# Global CLI
|
|
||||||
|
|
||||||
QMK provides an installable CLI that can be used to setup your QMK build environment, work with QMK, and which makes working with multiple copies of `qmk_firmware` easier. We recommend installing and updating this periodically.
|
|
||||||
|
|
||||||
## Install Using Homebrew (macOS, some Linux)
|
|
||||||
|
|
||||||
If you have installed [Homebrew](https://brew.sh) you can tap and install QMK:
|
If you have installed [Homebrew](https://brew.sh) you can tap and install QMK:
|
||||||
|
|
||||||
```
|
```
|
||||||
brew tap qmk/qmk
|
brew install qmk/qmk/qmk
|
||||||
brew install qmk
|
|
||||||
export QMK_HOME='~/qmk_firmware' # Optional, set the location for `qmk_firmware`
|
export QMK_HOME='~/qmk_firmware' # Optional, set the location for `qmk_firmware`
|
||||||
qmk setup # This will clone `qmk/qmk_firmware` and optionally set up your build environment
|
qmk setup # This will clone `qmk/qmk_firmware` and optionally set up your build environment
|
||||||
```
|
```
|
||||||
|
|
||||||
## Install Using easy_install or pip
|
### Install Using pip :id=install-using-easy_install-or-pip
|
||||||
|
|
||||||
If your system is not listed above you can install QMK manually. First ensure that you have python 3.5 (or later) installed and have installed pip. Then install QMK with this command:
|
If your system is not listed above you can install QMK manually. First ensure that you have Python 3.6 (or later) installed and have installed pip. Then install QMK with this command:
|
||||||
|
|
||||||
```
|
```
|
||||||
pip3 install qmk
|
python3 -m pip install qmk
|
||||||
export QMK_HOME='~/qmk_firmware' # Optional, set the location for `qmk_firmware`
|
export QMK_HOME='~/qmk_firmware' # Optional, set the location for `qmk_firmware`
|
||||||
qmk setup # This will clone `qmk/qmk_firmware` and optionally set up your build environment
|
qmk setup # This will clone `qmk/qmk_firmware` and optionally set up your build environment
|
||||||
```
|
```
|
||||||
|
|
||||||
## Packaging For Other Operating Systems
|
### Packaging For Other Operating Systems :id=packaging-for-other-operating-systems
|
||||||
|
|
||||||
We are looking for people to create and maintain a `qmk` package for more operating systems. If you would like to create a package for your OS please follow these guidelines:
|
We are looking for people to create and maintain a `qmk` package for more operating systems. If you would like to create a package for your OS please follow these guidelines:
|
||||||
|
|
||||||
@@ -47,268 +36,3 @@ We are looking for people to create and maintain a `qmk` package for more operat
|
|||||||
* Document why in a comment when you do deviate
|
* Document why in a comment when you do deviate
|
||||||
* Install using a virtualenv
|
* Install using a virtualenv
|
||||||
* Instruct the user to set the environment variable `QMK_HOME` to have the firmware source checked out somewhere other than `~/qmk_firmware`.
|
* Instruct the user to set the environment variable `QMK_HOME` to have the firmware source checked out somewhere other than `~/qmk_firmware`.
|
||||||
|
|
||||||
# Local CLI
|
|
||||||
|
|
||||||
If you do not want to use the global CLI there is a local CLI bundled with `qmk_firmware`. You can find it in `qmk_firmware/bin/qmk`. You can run the `qmk` command from any directory and it will always operate on that copy of `qmk_firmware`.
|
|
||||||
|
|
||||||
**Example**:
|
|
||||||
|
|
||||||
```
|
|
||||||
$ ~/qmk_firmware/bin/qmk hello
|
|
||||||
Ψ Hello, World!
|
|
||||||
```
|
|
||||||
|
|
||||||
## Local CLI Limitations
|
|
||||||
|
|
||||||
There are some limitations to the local CLI compared to the global CLI:
|
|
||||||
|
|
||||||
* The local CLI does not support `qmk setup` or `qmk clone`
|
|
||||||
* The local CLI always operates on the same `qmk_firmware` tree, even if you have multiple repositories cloned.
|
|
||||||
* The local CLI does not run in a virtualenv, so it's possible that dependencies will conflict
|
|
||||||
|
|
||||||
# CLI Commands
|
|
||||||
|
|
||||||
## `qmk cformat`
|
|
||||||
|
|
||||||
This command formats C code using clang-format.
|
|
||||||
|
|
||||||
Run it with no arguments to format all core code that has been changed. Default checks `origin/master` with `git diff`, branch can be changed using `-b <branch_name>`
|
|
||||||
|
|
||||||
Run it with `-a` to format all core code, or pass filenames on the command line to run it on specific files.
|
|
||||||
|
|
||||||
**Usage for specified files**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk cformat [file1] [file2] [...] [fileN]
|
|
||||||
```
|
|
||||||
|
|
||||||
**Usage for all core files**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk cformat -a
|
|
||||||
```
|
|
||||||
|
|
||||||
**Usage for only changed files against origin/master**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk cformat
|
|
||||||
```
|
|
||||||
|
|
||||||
**Usage for only changed files against branch_name**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk cformat -b branch_name
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk compile`
|
|
||||||
|
|
||||||
This command allows you to compile firmware from any directory. You can compile JSON exports from <https://config.qmk.fm>, compile keymaps in the repo, or compile the keyboard in the current working directory.
|
|
||||||
|
|
||||||
**Usage for Configurator Exports**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk compile <configuratorExport.json>
|
|
||||||
```
|
|
||||||
|
|
||||||
**Usage for Keymaps**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk compile -kb <keyboard_name> -km <keymap_name>
|
|
||||||
```
|
|
||||||
|
|
||||||
**Usage in Keyboard Directory**:
|
|
||||||
|
|
||||||
Must be in keyboard directory with a default keymap, or in keymap directory for keyboard, or supply one with `--keymap <keymap_name>`
|
|
||||||
```
|
|
||||||
qmk compile
|
|
||||||
```
|
|
||||||
|
|
||||||
**Example**:
|
|
||||||
```
|
|
||||||
$ qmk config compile.keymap=default
|
|
||||||
$ cd ~/qmk_firmware/keyboards/planck/rev6
|
|
||||||
$ qmk compile
|
|
||||||
Ψ Compiling keymap with make planck/rev6:default
|
|
||||||
...
|
|
||||||
```
|
|
||||||
or with optional keymap argument
|
|
||||||
|
|
||||||
```
|
|
||||||
$ cd ~/qmk_firmware/keyboards/clueboard/66/rev4
|
|
||||||
$ qmk compile -km 66_iso
|
|
||||||
Ψ Compiling keymap with make clueboard/66/rev4:66_iso
|
|
||||||
...
|
|
||||||
```
|
|
||||||
or in keymap directory
|
|
||||||
|
|
||||||
```
|
|
||||||
$ cd ~/qmk_firmware/keyboards/gh60/satan/keymaps/colemak
|
|
||||||
$ qmk compile
|
|
||||||
Ψ Compiling keymap with make make gh60/satan:colemak
|
|
||||||
...
|
|
||||||
```
|
|
||||||
|
|
||||||
**Usage in Layout Directory**:
|
|
||||||
|
|
||||||
Must be under `qmk_firmware/layouts/`, and in a keymap folder.
|
|
||||||
```
|
|
||||||
qmk compile -kb <keyboard_name>
|
|
||||||
```
|
|
||||||
|
|
||||||
**Example**:
|
|
||||||
```
|
|
||||||
$ cd ~/qmk_firmware/layouts/community/60_ansi/mechmerlin-ansi
|
|
||||||
$ qmk compile -kb dz60
|
|
||||||
Ψ Compiling keymap with make dz60:mechmerlin-ansi
|
|
||||||
...
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk flash`
|
|
||||||
|
|
||||||
This command is similar to `qmk compile`, but can also target a bootloader. The bootloader is optional, and is set to `:flash` by default.
|
|
||||||
To specify a different bootloader, use `-bl <bootloader>`. Visit the [Flashing Firmware](flashing.md) guide for more details of the available bootloaders.
|
|
||||||
|
|
||||||
**Usage for Configurator Exports**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk flash <configuratorExport.json> -bl <bootloader>
|
|
||||||
```
|
|
||||||
|
|
||||||
**Usage for Keymaps**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk flash -kb <keyboard_name> -km <keymap_name> -bl <bootloader>
|
|
||||||
```
|
|
||||||
|
|
||||||
**Listing the Bootloaders**
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk flash -b
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk config`
|
|
||||||
|
|
||||||
This command lets you configure the behavior of QMK. For the full `qmk config` documentation see [CLI Configuration](cli_configuration.md).
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk config [-ro] [config_token1] [config_token2] [...] [config_tokenN]
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk docs`
|
|
||||||
|
|
||||||
This command starts a local HTTP server which you can use for browsing or improving the docs. Default port is 8936.
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk docs [-p PORT]
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk doctor`
|
|
||||||
|
|
||||||
This command examines your environment and alerts you to potential build or flash problems. It can fix many of them if you want it to.
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk doctor [-y] [-n]
|
|
||||||
```
|
|
||||||
|
|
||||||
**Examples**:
|
|
||||||
|
|
||||||
Check your environment for problems and prompt to fix them:
|
|
||||||
|
|
||||||
qmk doctor
|
|
||||||
|
|
||||||
Check your environment and automatically fix any problems found:
|
|
||||||
|
|
||||||
qmk doctor -y
|
|
||||||
|
|
||||||
Check your environment and report problems only:
|
|
||||||
|
|
||||||
qmk doctor -n
|
|
||||||
|
|
||||||
## `qmk json-keymap`
|
|
||||||
|
|
||||||
Creates a keymap.c from a QMK Configurator export.
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk json-keymap [-o OUTPUT] filename
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk kle2json`
|
|
||||||
|
|
||||||
This command allows you to convert from raw KLE data to QMK Configurator JSON. It accepts either an absolute file path, or a file name in the current directory. By default it will not overwrite `info.json` if it is already present. Use the `-f` or `--force` flag to overwrite.
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk kle2json [-f] <filename>
|
|
||||||
```
|
|
||||||
|
|
||||||
**Examples**:
|
|
||||||
|
|
||||||
```
|
|
||||||
$ qmk kle2json kle.txt
|
|
||||||
☒ File info.json already exists, use -f or --force to overwrite.
|
|
||||||
```
|
|
||||||
|
|
||||||
```
|
|
||||||
$ qmk kle2json -f kle.txt -f
|
|
||||||
Ψ Wrote out to info.json
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk list-keyboards`
|
|
||||||
|
|
||||||
This command lists all the keyboards currently defined in `qmk_firmware`
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk list-keyboards
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk list-keymaps`
|
|
||||||
|
|
||||||
This command lists all the keymaps for a specified keyboard (and revision).
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk list-keymaps -kb planck/ez
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk new-keymap`
|
|
||||||
|
|
||||||
This command creates a new keymap based on a keyboard's existing default keymap.
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk new-keymap [-kb KEYBOARD] [-km KEYMAP]
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk pyformat`
|
|
||||||
|
|
||||||
This command formats python code in `qmk_firmware`.
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk pyformat
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk pytest`
|
|
||||||
|
|
||||||
This command runs the python test suite. If you make changes to python code you should ensure this runs successfully.
|
|
||||||
|
|
||||||
**Usage**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk pytest
|
|
||||||
```
|
|
||||||
@@ -0,0 +1,291 @@
|
|||||||
|
# QMK CLI Commands
|
||||||
|
|
||||||
|
# User Commands
|
||||||
|
|
||||||
|
## `qmk compile`
|
||||||
|
|
||||||
|
This command allows you to compile firmware from any directory. You can compile JSON exports from <https://config.qmk.fm>, compile keymaps in the repo, or compile the keyboard in the current working directory.
|
||||||
|
|
||||||
|
This command is directory aware. It will automatically fill in KEYBOARD and/or KEYMAP if you are in a keyboard or keymap directory.
|
||||||
|
|
||||||
|
**Usage for Configurator Exports**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk compile <configuratorExport.json>
|
||||||
|
```
|
||||||
|
|
||||||
|
**Usage for Keymaps**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk compile -kb <keyboard_name> -km <keymap_name>
|
||||||
|
```
|
||||||
|
|
||||||
|
**Usage in Keyboard Directory**:
|
||||||
|
|
||||||
|
Must be in keyboard directory with a default keymap, or in keymap directory for keyboard, or supply one with `--keymap <keymap_name>`
|
||||||
|
```
|
||||||
|
qmk compile
|
||||||
|
```
|
||||||
|
|
||||||
|
**Usage for building all keyboards that support a specific keymap**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk compile -kb all -km <keymap_name>
|
||||||
|
```
|
||||||
|
|
||||||
|
**Example**:
|
||||||
|
```
|
||||||
|
$ qmk config compile.keymap=default
|
||||||
|
$ cd ~/qmk_firmware/keyboards/planck/rev6
|
||||||
|
$ qmk compile
|
||||||
|
Ψ Compiling keymap with make planck/rev6:default
|
||||||
|
...
|
||||||
|
```
|
||||||
|
or with optional keymap argument
|
||||||
|
|
||||||
|
```
|
||||||
|
$ cd ~/qmk_firmware/keyboards/clueboard/66/rev4
|
||||||
|
$ qmk compile -km 66_iso
|
||||||
|
Ψ Compiling keymap with make clueboard/66/rev4:66_iso
|
||||||
|
...
|
||||||
|
```
|
||||||
|
or in keymap directory
|
||||||
|
|
||||||
|
```
|
||||||
|
$ cd ~/qmk_firmware/keyboards/gh60/satan/keymaps/colemak
|
||||||
|
$ qmk compile
|
||||||
|
Ψ Compiling keymap with make make gh60/satan:colemak
|
||||||
|
...
|
||||||
|
```
|
||||||
|
|
||||||
|
**Usage in Layout Directory**:
|
||||||
|
|
||||||
|
Must be under `qmk_firmware/layouts/`, and in a keymap folder.
|
||||||
|
```
|
||||||
|
qmk compile -kb <keyboard_name>
|
||||||
|
```
|
||||||
|
|
||||||
|
**Example**:
|
||||||
|
```
|
||||||
|
$ cd ~/qmk_firmware/layouts/community/60_ansi/mechmerlin-ansi
|
||||||
|
$ qmk compile -kb dz60
|
||||||
|
Ψ Compiling keymap with make dz60:mechmerlin-ansi
|
||||||
|
...
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk flash`
|
||||||
|
|
||||||
|
This command is similar to `qmk compile`, but can also target a bootloader. The bootloader is optional, and is set to `:flash` by default. To specify a different bootloader, use `-bl <bootloader>`. Visit the [Flashing Firmware](flashing.md) guide for more details of the available bootloaders.
|
||||||
|
|
||||||
|
This command is directory aware. It will automatically fill in KEYBOARD and/or KEYMAP if you are in a keyboard or keymap directory.
|
||||||
|
|
||||||
|
**Usage for Configurator Exports**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk flash <configuratorExport.json> -bl <bootloader>
|
||||||
|
```
|
||||||
|
|
||||||
|
**Usage for Keymaps**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk flash -kb <keyboard_name> -km <keymap_name> -bl <bootloader>
|
||||||
|
```
|
||||||
|
|
||||||
|
**Listing the Bootloaders**
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk flash -b
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk config`
|
||||||
|
|
||||||
|
This command lets you configure the behavior of QMK. For the full `qmk config` documentation see [CLI Configuration](cli_configuration.md).
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk config [-ro] [config_token1] [config_token2] [...] [config_tokenN]
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk doctor`
|
||||||
|
|
||||||
|
This command examines your environment and alerts you to potential build or flash problems. It can fix many of them if you want it to.
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk doctor [-y] [-n]
|
||||||
|
```
|
||||||
|
|
||||||
|
**Examples**:
|
||||||
|
|
||||||
|
Check your environment for problems and prompt to fix them:
|
||||||
|
|
||||||
|
qmk doctor
|
||||||
|
|
||||||
|
Check your environment and automatically fix any problems found:
|
||||||
|
|
||||||
|
qmk doctor -y
|
||||||
|
|
||||||
|
Check your environment and report problems only:
|
||||||
|
|
||||||
|
qmk doctor -n
|
||||||
|
|
||||||
|
## `qmk info`
|
||||||
|
|
||||||
|
Displays information about keyboards and keymaps in QMK. You can use this to get information about a keyboard, show the layouts, display the underlying key matrix, or to pretty-print JSON keymaps.
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk info [-f FORMAT] [-m] [-l] [-km KEYMAP] [-kb KEYBOARD]
|
||||||
|
```
|
||||||
|
|
||||||
|
This command is directory aware. It will automatically fill in KEYBOARD and/or KEYMAP if you are in a keyboard or keymap directory.
|
||||||
|
|
||||||
|
**Examples**:
|
||||||
|
|
||||||
|
Show basic information for a keyboard:
|
||||||
|
|
||||||
|
qmk info -kb planck/rev5
|
||||||
|
|
||||||
|
Show the matrix for a keyboard:
|
||||||
|
|
||||||
|
qmk info -kb ergodox_ez -m
|
||||||
|
|
||||||
|
Show a JSON keymap for a keyboard:
|
||||||
|
|
||||||
|
qmk info -kb clueboard/california -km default
|
||||||
|
|
||||||
|
## `qmk json2c`
|
||||||
|
|
||||||
|
Creates a keymap.c from a QMK Configurator export.
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk json2c [-o OUTPUT] filename
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk list-keyboards`
|
||||||
|
|
||||||
|
This command lists all the keyboards currently defined in `qmk_firmware`
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk list-keyboards
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk list-keymaps`
|
||||||
|
|
||||||
|
This command lists all the keymaps for a specified keyboard (and revision).
|
||||||
|
|
||||||
|
This command is directory aware. It will automatically fill in KEYBOARD if you are in a keyboard directory.
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk list-keymaps -kb planck/ez
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk new-keymap`
|
||||||
|
|
||||||
|
This command creates a new keymap based on a keyboard's existing default keymap.
|
||||||
|
|
||||||
|
This command is directory aware. It will automatically fill in KEYBOARD and/or KEYMAP if you are in a keyboard or keymap directory.
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk new-keymap [-kb KEYBOARD] [-km KEYMAP]
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
# Developer Commands
|
||||||
|
|
||||||
|
## `qmk cformat`
|
||||||
|
|
||||||
|
This command formats C code using clang-format.
|
||||||
|
|
||||||
|
Run it with no arguments to format all core code that has been changed. Default checks `origin/master` with `git diff`, branch can be changed using `-b <branch_name>`
|
||||||
|
|
||||||
|
Run it with `-a` to format all core code, or pass filenames on the command line to run it on specific files.
|
||||||
|
|
||||||
|
**Usage for specified files**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk cformat [file1] [file2] [...] [fileN]
|
||||||
|
```
|
||||||
|
|
||||||
|
**Usage for all core files**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk cformat -a
|
||||||
|
```
|
||||||
|
|
||||||
|
**Usage for only changed files against origin/master**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk cformat
|
||||||
|
```
|
||||||
|
|
||||||
|
**Usage for only changed files against branch_name**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk cformat -b branch_name
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk docs`
|
||||||
|
|
||||||
|
This command starts a local HTTP server which you can use for browsing or improving the docs. Default port is 8936.
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk docs [-p PORT]
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk kle2json`
|
||||||
|
|
||||||
|
This command allows you to convert from raw KLE data to QMK Configurator JSON. It accepts either an absolute file path, or a file name in the current directory. By default it will not overwrite `info.json` if it is already present. Use the `-f` or `--force` flag to overwrite.
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk kle2json [-f] <filename>
|
||||||
|
```
|
||||||
|
|
||||||
|
**Examples**:
|
||||||
|
|
||||||
|
```
|
||||||
|
$ qmk kle2json kle.txt
|
||||||
|
☒ File info.json already exists, use -f or --force to overwrite.
|
||||||
|
```
|
||||||
|
|
||||||
|
```
|
||||||
|
$ qmk kle2json -f kle.txt -f
|
||||||
|
Ψ Wrote out to info.json
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk pyformat`
|
||||||
|
|
||||||
|
This command formats python code in `qmk_firmware`.
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk pyformat
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk pytest`
|
||||||
|
|
||||||
|
This command runs the python test suite. If you make changes to python code you should ensure this runs successfully.
|
||||||
|
|
||||||
|
**Usage**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk pytest
|
||||||
|
```
|
||||||
|
|
||||||
@@ -108,7 +108,7 @@ compile.keymap: skully -> None
|
|||||||
|-----|---------------|-------------|
|
|-----|---------------|-------------|
|
||||||
| user.keyboard | None | The keyboard path (Example: `clueboard/66/rev4`) |
|
| user.keyboard | None | The keyboard path (Example: `clueboard/66/rev4`) |
|
||||||
| user.keymap | None | The keymap name (Example: `default`) |
|
| user.keymap | None | The keymap name (Example: `default`) |
|
||||||
| user.name | None | The user's github username. |
|
| user.name | None | The user's GitHub username. |
|
||||||
|
|
||||||
# All Configuration Options
|
# All Configuration Options
|
||||||
|
|
||||||
+16
-4
@@ -6,6 +6,18 @@ This document has useful information for developers wishing to write new `qmk` s
|
|||||||
|
|
||||||
The QMK CLI operates using the subcommand pattern made famous by git. The main `qmk` script is simply there to setup the environment and pick the correct entrypoint to run. Each subcommand is a self-contained module with an entrypoint (decorated by `@cli.subcommand()`) that performs some action and returns a shell returncode, or None.
|
The QMK CLI operates using the subcommand pattern made famous by git. The main `qmk` script is simply there to setup the environment and pick the correct entrypoint to run. Each subcommand is a self-contained module with an entrypoint (decorated by `@cli.subcommand()`) that performs some action and returns a shell returncode, or None.
|
||||||
|
|
||||||
|
## Developer mode:
|
||||||
|
|
||||||
|
If you intend to maintain keyboards and/or contribute to QMK, you can enable the CLI's "Developer" mode:
|
||||||
|
|
||||||
|
`qmk config user.developer=True`
|
||||||
|
|
||||||
|
This will allow you to see all available subcommands.
|
||||||
|
**Note:** You will have to install additional requirements:
|
||||||
|
```bash
|
||||||
|
python3 -m pip install -r requirements-dev.txt
|
||||||
|
```
|
||||||
|
|
||||||
# Subcommands
|
# Subcommands
|
||||||
|
|
||||||
[MILC](https://github.com/clueboard/milc) is the CLI framework `qmk` uses to handle argument parsing, configuration, logging, and many other features. It lets you focus on writing your tool without wasting your time writing glue code.
|
[MILC](https://github.com/clueboard/milc) is the CLI framework `qmk` uses to handle argument parsing, configuration, logging, and many other features. It lets you focus on writing your tool without wasting your time writing glue code.
|
||||||
@@ -32,7 +44,7 @@ def hello(cli):
|
|||||||
|
|
||||||
First we import the `cli` object from `milc`. This is how we interact with the user and control the script's behavior. We use `@cli.argument()` to define a command line flag, `--name`. This also creates a configuration variable named `hello.name` (and the corresponding `user.name`) which the user can set so they don't have to specify the argument. The `cli.subcommand()` decorator designates this function as a subcommand. The name of the subcommand will be taken from the name of the function.
|
First we import the `cli` object from `milc`. This is how we interact with the user and control the script's behavior. We use `@cli.argument()` to define a command line flag, `--name`. This also creates a configuration variable named `hello.name` (and the corresponding `user.name`) which the user can set so they don't have to specify the argument. The `cli.subcommand()` decorator designates this function as a subcommand. The name of the subcommand will be taken from the name of the function.
|
||||||
|
|
||||||
Once inside our function we find a typical "Hello, World!" program. We use `cli.log` to access the underlying [Logger Object](https://docs.python.org/3.5/library/logging.html#logger-objects), whose behavior is user controllable. We also access the value for name supplied by the user as `cli.config.hello.name`. The value for `cli.config.hello.name` will be determined by looking at the `--name` argument supplied by the user, if not provided it will use the value in the `qmk.ini` config file, and if neither of those is provided it will fall back to the default supplied in the `cli.argument()` decorator.
|
Once inside our function we find a typical "Hello, World!" program. We use `cli.log` to access the underlying [Logger Object](https://docs.python.org/3.6/library/logging.html#logger-objects), whose behavior is user controllable. We also access the value for name supplied by the user as `cli.config.hello.name`. The value for `cli.config.hello.name` will be determined by looking at the `--name` argument supplied by the user, if not provided it will use the value in the `qmk.ini` config file, and if neither of those is provided it will fall back to the default supplied in the `cli.argument()` decorator.
|
||||||
|
|
||||||
# User Interaction
|
# User Interaction
|
||||||
|
|
||||||
@@ -44,13 +56,13 @@ There are two main methods for outputting text in a subcommand- `cli.log` and `c
|
|||||||
|
|
||||||
You can use special tokens to colorize your text, to make it easier to understand the output of your program. See [Colorizing Text](#colorizing-text) below.
|
You can use special tokens to colorize your text, to make it easier to understand the output of your program. See [Colorizing Text](#colorizing-text) below.
|
||||||
|
|
||||||
Both of these methods support built-in string formatting using python's [printf style string format operations](https://docs.python.org/3.5/library/stdtypes.html#old-string-formatting). You can use tokens such as `%s` and `%d` within your text strings then pass the values as arguments. See our Hello, World program above for an example.
|
Both of these methods support built-in string formatting using python's [printf style string format operations](https://docs.python.org/3.6/library/stdtypes.html#old-string-formatting). You can use tokens such as `%s` and `%d` within your text strings then pass the values as arguments. See our Hello, World program above for an example.
|
||||||
|
|
||||||
You should never use the format operator (`%`) directly, always pass values as arguments.
|
You should never use the format operator (`%`) directly, always pass values as arguments.
|
||||||
|
|
||||||
### Logging (`cli.log`)
|
### Logging (`cli.log`)
|
||||||
|
|
||||||
The `cli.log` object gives you access to a [Logger Object](https://docs.python.org/3.5/library/logging.html#logger-objects). We have configured our log output to show the user a nice emoji for each log level (or the log level name if their terminal does not support unicode.) This way the user can tell at a glance which messages are most important when something goes wrong.
|
The `cli.log` object gives you access to a [Logger Object](https://docs.python.org/3.6/library/logging.html#logger-objects). We have configured our log output to show the user a nice emoji for each log level (or the log level name if their terminal does not support unicode.) This way the user can tell at a glance which messages are most important when something goes wrong.
|
||||||
|
|
||||||
The default log level is `INFO`. If the user runs `qmk -v <subcommand>` the default log level will be set to `DEBUG`.
|
The default log level is `INFO`. If the user runs `qmk -v <subcommand>` the default log level will be set to `DEBUG`.
|
||||||
|
|
||||||
@@ -198,7 +210,7 @@ Our tests can be found in `lib/python/qmk/tests/`. You will find both unit and i
|
|||||||
|
|
||||||
If your PR does not include a comprehensive set of tests please add comments like this to your code so that other people know where they can help:
|
If your PR does not include a comprehensive set of tests please add comments like this to your code so that other people know where they can help:
|
||||||
|
|
||||||
# TODO(unassigned/<yourGithubUsername>): Write <unit|integration> tests
|
# TODO(unassigned/<your_github_username>): Write <unit|integration> tests
|
||||||
|
|
||||||
We use [nose2](https://nose2.readthedocs.io/en/latest/getting_started.html) to run our tests. You can refer to the nose2 documentation for more details on what you can do in your test functions.
|
We use [nose2](https://nose2.readthedocs.io/en/latest/getting_started.html) to run our tests. You can refer to the nose2 documentation for more details on what you can do in your test functions.
|
||||||
|
|
||||||
|
|||||||
@@ -20,11 +20,11 @@ Most of our style is pretty easy to pick up on, but right now it's not entirely
|
|||||||
* We accept both forms of preprocessor if's: `#ifdef DEFINED` and `#if defined(DEFINED)`
|
* We accept both forms of preprocessor if's: `#ifdef DEFINED` and `#if defined(DEFINED)`
|
||||||
* If you are not sure which to prefer use the `#if defined(DEFINED)` form.
|
* If you are not sure which to prefer use the `#if defined(DEFINED)` form.
|
||||||
* Do not change existing code from one style to the other, except when moving to a multiple condition `#if`.
|
* Do not change existing code from one style to the other, except when moving to a multiple condition `#if`.
|
||||||
* Do not put whitespace between `#` and `if`.
|
* When deciding how (or if) to indent preprocessor directives, keep these points in mind:
|
||||||
* When deciding how (or if) to indent directives keep these points in mind:
|
* Readability is more important than consistency.
|
||||||
* Readability is more important than consistency.
|
* Follow the file's existing style. If the file is mixed, follow the style that makes sense for the section you are modifying.
|
||||||
* Follow the file's existing style. If the file is mixed follow the style that makes sense for the section you are modifying.
|
* When indenting, keep the hash at the start of the line and add whitespace between `#` and `if`, starting with 4 spaces after the `#`.
|
||||||
* When choosing to indent you can follow the indention level of the surrounding C code, or preprocessor directives can have their own indent level. Choose the style that best communicates the intent of your code.
|
* You can follow the indention level of the surrounding C code, or preprocessor directives can have their own indentation levels. Choose the style that best communicates the intent of your code.
|
||||||
|
|
||||||
Here is an example for easy reference:
|
Here is an example for easy reference:
|
||||||
|
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
Most of our style follows PEP8 with some local modifications to make things less nit-picky.
|
Most of our style follows PEP8 with some local modifications to make things less nit-picky.
|
||||||
|
|
||||||
* We target Python 3.5 for compatability with all supported platforms.
|
* We target Python 3.6 for compatability with all supported platforms.
|
||||||
* We indent using four (4) spaces (soft tabs)
|
* We indent using four (4) spaces (soft tabs)
|
||||||
* We encourage liberal use of comments
|
* We encourage liberal use of comments
|
||||||
* Think of them as a story describing the feature
|
* Think of them as a story describing the feature
|
||||||
@@ -317,7 +317,7 @@ At the time of this writing our tests are not very comprehensive. Looking at the
|
|||||||
|
|
||||||
## Integration Tests
|
## Integration Tests
|
||||||
|
|
||||||
Integration tests can be found in `lib/python/qmk/tests/test_cli_commands.py`. This is where CLI commands are actually run and their overall behavior is verified. We use [`subprocess`](https://docs.python.org/3.5/library/subprocess.html#module-subprocess) to launch each CLI command and a combination of checking output and returncode to determine if the right thing happened.
|
Integration tests can be found in `lib/python/qmk/tests/test_cli_commands.py`. This is where CLI commands are actually run and their overall behavior is verified. We use [`subprocess`](https://docs.python.org/3.6/library/subprocess.html#module-subprocess) to launch each CLI command and a combination of checking output and returncode to determine if the right thing happened.
|
||||||
|
|
||||||
## Unit Tests
|
## Unit Tests
|
||||||
|
|
||||||
|
|||||||
@@ -14,6 +14,7 @@ Certain MCUs which do not have native USB will use [V-USB](https://www.obdev.at/
|
|||||||
|
|
||||||
* [ATmega32A](https://www.microchip.com/wwwproducts/en/ATmega32A)
|
* [ATmega32A](https://www.microchip.com/wwwproducts/en/ATmega32A)
|
||||||
* [ATmega328P](https://www.microchip.com/wwwproducts/en/ATmega328P)
|
* [ATmega328P](https://www.microchip.com/wwwproducts/en/ATmega328P)
|
||||||
|
* [ATmega328](https://www.microchip.com/wwwproducts/en/ATmega328)
|
||||||
|
|
||||||
## ARM
|
## ARM
|
||||||
|
|
||||||
|
|||||||
+17
-7
@@ -115,9 +115,9 @@ If you define these options you will disable the associated feature, which can s
|
|||||||
* `#define NO_ACTION_ONESHOT`
|
* `#define NO_ACTION_ONESHOT`
|
||||||
* disable one-shot modifiers
|
* disable one-shot modifiers
|
||||||
* `#define NO_ACTION_MACRO`
|
* `#define NO_ACTION_MACRO`
|
||||||
* disable old style macro handling: MACRO() & action_get_macro
|
* disable old-style macro handling using `MACRO()`, `action_get_macro()` _(deprecated)_
|
||||||
* `#define NO_ACTION_FUNCTION`
|
* `#define NO_ACTION_FUNCTION`
|
||||||
* disable calling of action_function() from the fn_actions array (deprecated)
|
* disable old-style function handling using `fn_actions`, `action_function()` _(deprecated)_
|
||||||
|
|
||||||
## Features That Can Be Enabled
|
## Features That Can Be Enabled
|
||||||
|
|
||||||
@@ -191,7 +191,14 @@ If you define these options you will enable the associated feature, which may in
|
|||||||
* `#define RGBLIGHT_ANIMATIONS`
|
* `#define RGBLIGHT_ANIMATIONS`
|
||||||
* run RGB animations
|
* run RGB animations
|
||||||
* `#define RGBLIGHT_LAYERS`
|
* `#define RGBLIGHT_LAYERS`
|
||||||
* Lets you define [lighting layers](feature_rgblight.md) that can be toggled on or off. Great for showing the current keyboard layer or caps lock state.
|
* Lets you define [lighting layers](feature_rgblight.md?id=lighting-layers) that can be toggled on or off. Great for showing the current keyboard layer or caps lock state.
|
||||||
|
* `#define RGBLIGHT_MAX_LAYERS`
|
||||||
|
* Defaults to 8. Can be expanded up to 32 if more [lighting layers](feature_rgblight.md?id=lighting-layers) are needed.
|
||||||
|
* Note: Increasing the maximum will increase the firmware size and slow sync on split keyboards.
|
||||||
|
* `#define RGBLIGHT_LAYER_BLINK`
|
||||||
|
* Adds ability to [blink](feature_rgblight.md?id=lighting-layer-blink) a lighting layer for a specified number of milliseconds (e.g. to acknowledge an action).
|
||||||
|
* `#define RGBLIGHT_LAYERS_OVERRIDE_RGB_OFF`
|
||||||
|
* If defined, then [lighting layers](feature_rgblight?id=overriding-rgb-lighting-onoff-status) will be shown even if RGB Light is off.
|
||||||
* `#define RGBLED_NUM 12`
|
* `#define RGBLED_NUM 12`
|
||||||
* number of LEDs
|
* number of LEDs
|
||||||
* `#define RGBLIGHT_SPLIT`
|
* `#define RGBLIGHT_SPLIT`
|
||||||
@@ -243,7 +250,10 @@ There are a few different ways to set handedness for split keyboards (listed in
|
|||||||
* `#define SPLIT_HAND_PIN B7`
|
* `#define SPLIT_HAND_PIN B7`
|
||||||
* For using high/low pin to determine handedness, low = right hand, high = left hand. Replace `B7` with the pin you are using. This is optional, and if you leave `SPLIT_HAND_PIN` undefined, then you can still use the EE_HANDS method or MASTER_LEFT / MASTER_RIGHT defines like the stock Let's Split uses.
|
* For using high/low pin to determine handedness, low = right hand, high = left hand. Replace `B7` with the pin you are using. This is optional, and if you leave `SPLIT_HAND_PIN` undefined, then you can still use the EE_HANDS method or MASTER_LEFT / MASTER_RIGHT defines like the stock Let's Split uses.
|
||||||
|
|
||||||
* `#define EE_HANDS` (only works if `SPLIT_HAND_PIN` is not defined)
|
* `#define SPLIT_HAND_MATRIX_GRID <out_pin>,<in_pin>`
|
||||||
|
* The handedness is determined by using the intersection of the keyswitches in the key matrix, which does not exist. Normally, when this intersection is shorted (level low), it is considered left. If you define `#define SPLIT_HAND_MATRIX_GRID_LOW_IS_RIGHT`, it is determined to be right when the level is low.
|
||||||
|
|
||||||
|
* `#define EE_HANDS` (only works if `SPLIT_HAND_PIN` and `SPLIT_HAND_MATRIX_GRID` are not defined)
|
||||||
* Reads the handedness value stored in the EEPROM after `eeprom-lefthand.eep`/`eeprom-righthand.eep` has been flashed to their respective halves.
|
* Reads the handedness value stored in the EEPROM after `eeprom-lefthand.eep`/`eeprom-righthand.eep` has been flashed to their respective halves.
|
||||||
|
|
||||||
* `#define MASTER_RIGHT`
|
* `#define MASTER_RIGHT`
|
||||||
@@ -317,10 +327,10 @@ This is a [make](https://www.gnu.org/software/make/manual/make.html) file that i
|
|||||||
* `LAYOUTS`
|
* `LAYOUTS`
|
||||||
* A list of [layouts](feature_layouts.md) this keyboard supports.
|
* A list of [layouts](feature_layouts.md) this keyboard supports.
|
||||||
* `LINK_TIME_OPTIMIZATION_ENABLE`
|
* `LINK_TIME_OPTIMIZATION_ENABLE`
|
||||||
* Enables Link Time Optimization (`LTO`) when compiling the keyboard. This makes the process take longer, but can significantly reduce the compiled size (and since the firmware is small, the added time is not noticeable). However, this will automatically disable the old Macros and Functions features automatically, as these break when `LTO` is enabled.
|
* Enables Link Time Optimization (LTO) when compiling the keyboard. This makes the process take longer, but it can significantly reduce the compiled size (and since the firmware is small, the added time is not noticeable).
|
||||||
It does this by automatically defining `NO_ACTION_MACRO` and `NO_ACTION_FUNCTION`
|
However, this will automatically disable the legacy TMK Macros and Functions features, as these break when LTO is enabled. It does this by automatically defining `NO_ACTION_MACRO` and `NO_ACTION_FUNCTION`. (Note: This does not affect QMK [Macros](feature_macros.md) and [Layers](feature_layers.md).)
|
||||||
* `LTO_ENABLE`
|
* `LTO_ENABLE`
|
||||||
* It has the same meaning as LINK_TIME_OPTIMIZATION_ENABLE. You can use `LTO_ENABLE` instead of `LINK_TIME_OPTIMIZATION_ENABLE`.
|
* Has the same meaning as `LINK_TIME_OPTIMIZATION_ENABLE`. You can use `LTO_ENABLE` instead of `LINK_TIME_OPTIMIZATION_ENABLE`.
|
||||||
|
|
||||||
## AVR MCU Options
|
## AVR MCU Options
|
||||||
* `MCU = atmega32u4`
|
* `MCU = atmega32u4`
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ I'll say that again because it's important:
|
|||||||
|
|
||||||
!> **MAKE SURE YOU SELECT THE RIGHT VERSION!**
|
!> **MAKE SURE YOU SELECT THE RIGHT VERSION!**
|
||||||
|
|
||||||
If your keyboard has been advertised to be powered by QMK but is not in the list, chances are a developer hasn't gotten to it yet or we haven't had a chance to merge it in yet. File an issue at [qmk_firmware](https://github.com/qmk/qmk_firmware/issues) requesting to support that particular keyboard, if there is no active [Pull Request](https://github.com/qmk/qmk_firmware/pulls?q=is%3Aopen+is%3Apr+label%3Akeyboard) for it. There are also QMK powered keyboards that are in their manufacturer's own github accounts. Double check for that as well. <!-- FIXME(skullydazed): This feels too wordy and I'm not sure we want to encourage these kinds of issues. Also, should we prompt them to bug the manufacutrer? -->
|
If your keyboard has been advertised to be powered by QMK but is not in the list, chances are a developer hasn't gotten to it yet or we haven't had a chance to merge it in yet. File an issue at [qmk_firmware](https://github.com/qmk/qmk_firmware/issues) requesting to support that particular keyboard, if there is no active [Pull Request](https://github.com/qmk/qmk_firmware/pulls?q=is%3Aopen+is%3Apr+label%3Akeyboard) for it. There are also QMK powered keyboards that are in their manufacturer's own GitHub accounts. Double check for that as well. <!-- FIXME(skullydazed): This feels too wordy and I'm not sure we want to encourage these kinds of issues. Also, should we prompt them to bug the manufacutrer? -->
|
||||||
|
|
||||||
## Step 2: Select Your Keyboard Layout
|
## Step 2: Select Your Keyboard Layout
|
||||||
|
|
||||||
|
|||||||
@@ -57,7 +57,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
|
|||||||
case KC_ENTER:
|
case KC_ENTER:
|
||||||
// Play a tone when enter is pressed
|
// Play a tone when enter is pressed
|
||||||
if (record->event.pressed) {
|
if (record->event.pressed) {
|
||||||
PLAY_NOTE_ARRAY(tone_qwerty);
|
PLAY_SONG(tone_qwerty);
|
||||||
}
|
}
|
||||||
return true; // Let QMK send the enter press/release events
|
return true; // Let QMK send the enter press/release events
|
||||||
default:
|
default:
|
||||||
@@ -438,7 +438,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
|
|||||||
case KC_ENTER:
|
case KC_ENTER:
|
||||||
// Play a tone when enter is pressed
|
// Play a tone when enter is pressed
|
||||||
if (record->event.pressed) {
|
if (record->event.pressed) {
|
||||||
PLAY_NOTE_ARRAY(tone_qwerty);
|
PLAY_SONG(tone_qwerty);
|
||||||
}
|
}
|
||||||
return true; // Let QMK send the enter press/release events
|
return true; // Let QMK send the enter press/release events
|
||||||
case RGB_LYR: // This allows me to use underglow as layer indication, or as normal
|
case RGB_LYR: // This allows me to use underglow as layer indication, or as normal
|
||||||
@@ -486,56 +486,3 @@ And you're done. The RGB layer indication will only work if you want it to. And
|
|||||||
* Keymap: `void eeconfig_init_user(void)`, `uint32_t eeconfig_read_user(void)` and `void eeconfig_update_user(uint32_t val)`
|
* Keymap: `void eeconfig_init_user(void)`, `uint32_t eeconfig_read_user(void)` and `void eeconfig_update_user(uint32_t val)`
|
||||||
|
|
||||||
The `val` is the value of the data that you want to write to EEPROM. And the `eeconfig_read_*` function return a 32 bit (DWORD) value from the EEPROM.
|
The `val` is the value of the data that you want to write to EEPROM. And the `eeconfig_read_*` function return a 32 bit (DWORD) value from the EEPROM.
|
||||||
|
|
||||||
# Custom Tapping Term
|
|
||||||
|
|
||||||
By default, the tapping term and related options (such as `IGNORE_MOD_TAP_INTERRUPT`) are defined globally, and are not configurable by key. For most users, this is perfectly fine. But in some cases, dual function keys would be greatly improved by different timeout behaviors than `LT` keys, or because some keys may be easier to hold than others. Instead of using custom key codes for each, this allows for per key configurable timeout behaviors.
|
|
||||||
|
|
||||||
There are two configurable options to control per-key timeout behaviors:
|
|
||||||
|
|
||||||
- `TAPPING_TERM_PER_KEY`
|
|
||||||
- `IGNORE_MOD_TAP_INTERRUPT_PER_KEY`
|
|
||||||
|
|
||||||
You need to add `#define` lines to your `config.h` for each feature you want.
|
|
||||||
|
|
||||||
```
|
|
||||||
#define TAPPING_TERM_PER_KEY
|
|
||||||
#define IGNORE_MOD_TAP_INTERRUPT_PER_KEY
|
|
||||||
```
|
|
||||||
|
|
||||||
|
|
||||||
## Example `get_tapping_term` Implementation
|
|
||||||
|
|
||||||
To change the `TAPPING_TERM` based on the keycode, you'd want to add something like the following to your `keymap.c` file:
|
|
||||||
|
|
||||||
```c
|
|
||||||
uint16_t get_tapping_term(uint16_t keycode) {
|
|
||||||
switch (keycode) {
|
|
||||||
case SFT_T(KC_SPC):
|
|
||||||
return TAPPING_TERM + 1250;
|
|
||||||
case LT(1, KC_GRV):
|
|
||||||
return 130;
|
|
||||||
default:
|
|
||||||
return TAPPING_TERM;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
## Example `get_ignore_mod_tap_interrupt` Implementation
|
|
||||||
|
|
||||||
To change the `IGNORE_MOD_TAP_INTERRUPT` value based on the keycode, you'd want to add something like the following to your `keymap.c` file:
|
|
||||||
|
|
||||||
```c
|
|
||||||
bool get_ignore_mod_tap_interrupt(uint16_t keycode) {
|
|
||||||
switch (keycode) {
|
|
||||||
case SFT_T(KC_SPC):
|
|
||||||
return true;
|
|
||||||
default:
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
## `get_tapping_term` / `get_ignore_mod_tap_interrupt` Function Documentation
|
|
||||||
|
|
||||||
Unlike many of the other functions here, there isn't a need (or even reason) to have a quantum or keyboard level function. Only user level functions are useful here, so no need to mark them as such.
|
|
||||||
+1
-1
@@ -13,7 +13,7 @@ QMK (*Quantum Mechanical Keyboard*) ist eine Open-Source-Community, welche die Q
|
|||||||
|
|
||||||
## Bezugsquelle für QMK
|
## Bezugsquelle für QMK
|
||||||
|
|
||||||
Wenn Du vorhast, deine Tastatur, Tastaturbelegung oder Features zu QMK beizusteuern, geht das am einfachsten, indem Du das [Repository auf Github](https://github.com/qmk/qmk_firmware#fork-destination-box) forkst, die Änderungen in deinem lokalen Repo vornimmst und anschließend einen [Pull Request](https://github.com/qmk/qmk_firmware/pulls) einreichst.
|
Wenn Du vorhast, deine Tastatur, Tastaturbelegung oder Features zu QMK beizusteuern, geht das am einfachsten, indem Du das [Repository auf GitHub](https://github.com/qmk/qmk_firmware#fork-destination-box) forkst, die Änderungen in deinem lokalen Repo vornimmst und anschließend einen [Pull Request](https://github.com/qmk/qmk_firmware/pulls) einreichst.
|
||||||
|
|
||||||
Ansonsten kannst Du es als [zip](https://github.com/qmk/qmk_firmware/zipball/master) oder [tar](https://github.com/qmk/qmk_firmware/tarball/master) herunterladen, oder es direkt via git klonen (`git clone [email protected]:qmk/qmk_firmware.git` bzw. `git clone https://github.com/qmk/qmk_firmware.git`).
|
Ansonsten kannst Du es als [zip](https://github.com/qmk/qmk_firmware/zipball/master) oder [tar](https://github.com/qmk/qmk_firmware/tarball/master) herunterladen, oder es direkt via git klonen (`git clone [email protected]:qmk/qmk_firmware.git` bzw. `git clone https://github.com/qmk/qmk_firmware.git`).
|
||||||
|
|
||||||
|
|||||||
+2
-1
@@ -11,7 +11,7 @@
|
|||||||
* [QMK CLI](de/cli.md)
|
* [QMK CLI](de/cli.md)
|
||||||
* [QMK CLI Konfiguration](de/cli_configuration.md)
|
* [QMK CLI Konfiguration](de/cli_configuration.md)
|
||||||
* [Zu QMK beitragen](de/contributing.md)
|
* [Zu QMK beitragen](de/contributing.md)
|
||||||
* [Anleitung für Github](de/getting_started_github.md)
|
* [Anleitung für GitHub](de/getting_started_github.md)
|
||||||
* [Nach Hilfe fragen](de/getting_started_getting_help.md)
|
* [Nach Hilfe fragen](de/getting_started_getting_help.md)
|
||||||
|
|
||||||
* [Breaking Changes](de/breaking_changes.md)
|
* [Breaking Changes](de/breaking_changes.md)
|
||||||
@@ -98,6 +98,7 @@
|
|||||||
* [ISP Flashing Guide](de/isp_flashing_guide.md)
|
* [ISP Flashing Guide](de/isp_flashing_guide.md)
|
||||||
* [ARM Debugging Guide](de/arm_debugging.md)
|
* [ARM Debugging Guide](de/arm_debugging.md)
|
||||||
* [I2C Driver](de/i2c_driver.md)
|
* [I2C Driver](de/i2c_driver.md)
|
||||||
|
* [SPI Driver](de/spi_driver.md)
|
||||||
* [GPIO Controls](de/internals_gpio_control.md)
|
* [GPIO Controls](de/internals_gpio_control.md)
|
||||||
* [Proton C Conversion](de/proton_c_conversion.md)
|
* [Proton C Conversion](de/proton_c_conversion.md)
|
||||||
|
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ Git Ressourcen:
|
|||||||
|
|
||||||
* [Gutes allgemeines Tutorial](https://www.codecademy.com/learn/learn-git) (auf Englisch)
|
* [Gutes allgemeines Tutorial](https://www.codecademy.com/learn/learn-git) (auf Englisch)
|
||||||
* [Git spielerisch anhand von Beispielen lernen](https://learngitbranching.js.org/) (auf Englisch)
|
* [Git spielerisch anhand von Beispielen lernen](https://learngitbranching.js.org/) (auf Englisch)
|
||||||
* [Mehr über den allgemeinen Umgang mit Github](getting_started_github.md)
|
* [Mehr über den allgemeinen Umgang mit GitHub](getting_started_github.md)
|
||||||
* [Mehr über Git im Bezug zu QMK](contributing.md)
|
* [Mehr über Git im Bezug zu QMK](contributing.md)
|
||||||
|
|
||||||
Mehr über die Arbeit mit der Befehlszeile:
|
Mehr über die Arbeit mit der Befehlszeile:
|
||||||
|
|||||||
@@ -61,4 +61,4 @@ This page describes my cool feature. You can use my cool feature to make coffee
|
|||||||
|KC_SUGAR||Order Sugar|
|
|KC_SUGAR||Order Sugar|
|
||||||
```
|
```
|
||||||
|
|
||||||
Place your documentation into `docs/feature_<my_cool_feature>.md`, and add that file to the appropriate place in `docs/_sidebar.md`. If you have added any keycodes be sure to add them to `docs/keycodes.md` with a link back to your feature page.
|
Place your documentation into `docs/feature_<my_cool_feature>.md`, and add that file to the appropriate place in `docs/_summary.md`. If you have added any keycodes be sure to add them to `docs/keycodes.md` with a link back to your feature page.
|
||||||
+31
-10
@@ -1,18 +1,25 @@
|
|||||||
# EEPROM Driver Configuration
|
# EEPROM Driver Configuration :id=eeprom-driver-configuration
|
||||||
|
|
||||||
The EEPROM driver can be swapped out depending on the needs of the keyboard, or whether extra hardware is present.
|
The EEPROM driver can be swapped out depending on the needs of the keyboard, or whether extra hardware is present.
|
||||||
|
|
||||||
Driver | Description
|
Driver | Description
|
||||||
--------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
-----------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
||||||
`EEPROM_DRIVER = vendor` | Uses the on-chip driver provided by the chip manufacturer. For AVR, this is provided by avr-libc. This is supported on ARM for a subset of chips -- STM32F3xx, STM32F1xx, and STM32F072xB will be emulated by writing to flash. Other chips will generally act as "transient" below.
|
`EEPROM_DRIVER = vendor` (default) | Uses the on-chip driver provided by the chip manufacturer. For AVR, this is provided by avr-libc. This is supported on ARM for a subset of chips -- STM32F3xx, STM32F1xx, and STM32F072xB will be emulated by writing to flash. STM32L0xx and STM32L1xx will use the onboard dedicated true EEPROM. Other chips will generally act as "transient" below.
|
||||||
`EEPROM_DRIVER = i2c` | Supports writing to I2C-based 24xx EEPROM chips. See the driver section below.
|
`EEPROM_DRIVER = i2c` | Supports writing to I2C-based 24xx EEPROM chips. See the driver section below.
|
||||||
`EEPROM_DRIVER = transient` | Fake EEPROM driver -- supports reading/writing to RAM, and will be discarded when power is lost.
|
`EEPROM_DRIVER = spi` | Supports writing to SPI-based 25xx EEPROM chips. See the driver section below.
|
||||||
|
`EEPROM_DRIVER = transient` | Fake EEPROM driver -- supports reading/writing to RAM, and will be discarded when power is lost.
|
||||||
|
|
||||||
## Vendor Driver Configuration
|
## Vendor Driver Configuration :id=vendor-eeprom-driver-configuration
|
||||||
|
|
||||||
No configurable options are available.
|
#### STM32 L0/L1 Configuration :id=stm32l0l1-eeprom-driver-configuration
|
||||||
|
|
||||||
## I2C Driver Configuration
|
!> Resetting EEPROM using an STM32L0/L1 device takes up to 1 second for every 1kB of internal EEPROM used.
|
||||||
|
|
||||||
|
`config.h` override | Description | Default Value
|
||||||
|
------------------------------------|--------------------------------------------------------------------------------------------------------------------------|----------------------------------------------------------------------------
|
||||||
|
`#define STM32_ONBOARD_EEPROM_SIZE` | The size of the EEPROM to use, in bytes. Erase times can be high, so it's configurable here, if not using the default value. | Minimum required to cover base _eeconfig_ data, or `1024` if VIA is enabled.
|
||||||
|
|
||||||
|
## I2C Driver Configuration :id=i2c-eeprom-driver-configuration
|
||||||
|
|
||||||
Currently QMK supports 24xx-series chips over I2C. As such, requires a working i2c_master driver configuration. You can override the driver configuration via your config.h:
|
Currently QMK supports 24xx-series chips over I2C. As such, requires a working i2c_master driver configuration. You can override the driver configuration via your config.h:
|
||||||
|
|
||||||
@@ -39,7 +46,21 @@ MB85RC256V FRAM | `#define EEPROM_I2C_MB85RC256V` | <https://www.adafruit.com/p
|
|||||||
|
|
||||||
?> If you find that the EEPROM is not cooperating, ensure you've correctly shifted up your EEPROM address by 1. For example, the datasheet might state the address as `0b01010000` -- the correct value of `EXTERNAL_EEPROM_I2C_BASE_ADDRESS` needs to be `0b10100000`.
|
?> If you find that the EEPROM is not cooperating, ensure you've correctly shifted up your EEPROM address by 1. For example, the datasheet might state the address as `0b01010000` -- the correct value of `EXTERNAL_EEPROM_I2C_BASE_ADDRESS` needs to be `0b10100000`.
|
||||||
|
|
||||||
## Transient Driver configuration
|
## SPI Driver Configuration :id=spi-eeprom-driver-configuration
|
||||||
|
|
||||||
|
Currently QMK supports 25xx-series chips over SPI. As such, requires a working spi_master driver configuration. You can override the driver configuration via your config.h:
|
||||||
|
|
||||||
|
`config.h` override | Description | Default Value
|
||||||
|
-----------------------------------------------|--------------------------------------------------------------------------------------|--------------
|
||||||
|
`#define EXTERNAL_EEPROM_SPI_SLAVE_SELECT_PIN` | SPI Slave select pin in order to inform that the EEPROM is currently being addressed | _none_
|
||||||
|
`#define EXTERNAL_EEPROM_SPI_CLOCK_DIVISOR` | Clock divisor used to divide the peripheral clock to derive the SPI frequency | `64`
|
||||||
|
`#define EXTERNAL_EEPROM_BYTE_COUNT` | Total size of the EEPROM in bytes | 8192
|
||||||
|
`#define EXTERNAL_EEPROM_PAGE_SIZE` | Page size of the EEPROM in bytes, as specified in the datasheet | 32
|
||||||
|
`#define EXTERNAL_EEPROM_ADDRESS_SIZE` | The number of bytes to transmit for the memory location within the EEPROM | 2
|
||||||
|
|
||||||
|
!> There's no way to determine if there is an SPI EEPROM actually responding. Generally, this will result in reads of nothing but zero.
|
||||||
|
|
||||||
|
## Transient Driver configuration :id=transient-eeprom-driver-configuration
|
||||||
|
|
||||||
The only configurable item for the transient EEPROM driver is its size:
|
The only configurable item for the transient EEPROM driver is its size:
|
||||||
|
|
||||||
|
|||||||
+1
-1
@@ -13,7 +13,7 @@ QMK (*Quantum Mechanical Keyboard*) es una comunidad open source que mantiene el
|
|||||||
|
|
||||||
## Cómo conseguirlo
|
## Cómo conseguirlo
|
||||||
|
|
||||||
Si estás pensando en contribuir con un keymap, teclado, or característica a QMK, la manera más sencilla es hacer un [fork del repositorio en Github](https://github.com/qmk/qmk_firmware#fork-destination-box), y clonar tu repositorio localmente para hacer los cambios, subirlos, y abir un [Pull Request](https://github.com/qmk/qmk_firmware/pulls) desde tu fork.
|
Si estás pensando en contribuir con un keymap, teclado, or característica a QMK, la manera más sencilla es hacer un [fork del repositorio en GitHub](https://github.com/qmk/qmk_firmware#fork-destination-box), y clonar tu repositorio localmente para hacer los cambios, subirlos, y abir un [Pull Request](https://github.com/qmk/qmk_firmware/pulls) desde tu fork.
|
||||||
|
|
||||||
De cualquier manera, también puedes descargarlo directamente en formatos ([zip](https://github.com/qmk/qmk_firmware/zipball/master), [tar](https://github.com/qmk/qmk_firmware/tarball/master)), o clonarlo via git (`[email protected]:qmk/qmk_firmware.git`), o https (`https://github.com/qmk/qmk_firmware.git`).
|
De cualquier manera, también puedes descargarlo directamente en formatos ([zip](https://github.com/qmk/qmk_firmware/zipball/master), [tar](https://github.com/qmk/qmk_firmware/tarball/master)), o clonarlo via git (`[email protected]:qmk/qmk_firmware.git`), o https (`https://github.com/qmk/qmk_firmware.git`).
|
||||||
|
|
||||||
|
|||||||
+2
-1
@@ -11,7 +11,7 @@
|
|||||||
* [QMK CLI](es/cli.md)
|
* [QMK CLI](es/cli.md)
|
||||||
* [Configuración de QMK CLI](es/cli_configuration.md)
|
* [Configuración de QMK CLI](es/cli_configuration.md)
|
||||||
* [Contribuyendo a QMK](es/contributing.md)
|
* [Contribuyendo a QMK](es/contributing.md)
|
||||||
* [Cómo usar Github](es/getting_started_github.md)
|
* [Cómo usar GitHub](es/getting_started_github.md)
|
||||||
* [Obtener ayuda](es/getting_started_getting_help.md)
|
* [Obtener ayuda](es/getting_started_getting_help.md)
|
||||||
|
|
||||||
* [Cambios incompatibles](es/breaking_changes.md)
|
* [Cambios incompatibles](es/breaking_changes.md)
|
||||||
@@ -98,6 +98,7 @@
|
|||||||
* [Guía de flasheado de ISP](es/isp_flashing_guide.md)
|
* [Guía de flasheado de ISP](es/isp_flashing_guide.md)
|
||||||
* [Guía de depuración de ARM](es/arm_debugging.md)
|
* [Guía de depuración de ARM](es/arm_debugging.md)
|
||||||
* [Driver I2C](es/i2c_driver.md)
|
* [Driver I2C](es/i2c_driver.md)
|
||||||
|
* [Driver SPI](es/spi_driver.md)
|
||||||
* [Controles GPIO](es/internals_gpio_control.md)
|
* [Controles GPIO](es/internals_gpio_control.md)
|
||||||
* [Conversión Proton C](es/proton_c_conversion.md)
|
* [Conversión Proton C](es/proton_c_conversion.md)
|
||||||
|
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ Este documento procura instruir a los novatos en las mejores prácticas para ten
|
|||||||
|
|
||||||
En este documento suponemos un par de cosas:
|
En este documento suponemos un par de cosas:
|
||||||
|
|
||||||
1. Tienes una cuenta de Github, y has hecho un [fork del repo qmk_firmware](getting_started_github.md) en tu cuenta.
|
1. Tienes una cuenta de GitHub, y has hecho un [fork del repo qmk_firmware](getting_started_github.md) en tu cuenta.
|
||||||
2. Has [configurado tu entorno de desarrollo](newbs_getting_started.md?id=environment-setup).
|
2. Has [configurado tu entorno de desarrollo](newbs_getting_started.md?id=environment-setup).
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -21,7 +21,7 @@ Lo diré otra vez porque es importante
|
|||||||
|
|
||||||
!> **ASEGÚRATE DE QUE SELECCIONAS LA VERSIÓN CORRECTA!**
|
!> **ASEGÚRATE DE QUE SELECCIONAS LA VERSIÓN CORRECTA!**
|
||||||
|
|
||||||
Si se ha anunciado que tu teclado funciona con QMK pero no está en la lista, es probable que un desarrollador no se haya encargado de él aún o que todavía no hemos tenido la oportunidad de incluirlo. Abre un issue en [qmk_firmware](https://github.com/qmk/qmk_firmware/issues) solicitando soportar ese teclado un particular, si no hay un [Pull Request](https://github.com/qmk/qmk_firmware/pulls?q=is%3Aopen+is%3Apr+label%3Akeyboard) activo para ello. Hay también teclados que funcionan con QMK que están en las cuentas de github de sus manufacturantes. Acuérdate de comprobar esto también.
|
Si se ha anunciado que tu teclado funciona con QMK pero no está en la lista, es probable que un desarrollador no se haya encargado de él aún o que todavía no hemos tenido la oportunidad de incluirlo. Abre un issue en [qmk_firmware](https://github.com/qmk/qmk_firmware/issues) solicitando soportar ese teclado un particular, si no hay un [Pull Request](https://github.com/qmk/qmk_firmware/pulls?q=is%3Aopen+is%3Apr+label%3Akeyboard) activo para ello. Hay también teclados que funcionan con QMK que están en las cuentas de GitHub de sus manufacturantes. Acuérdate de comprobar esto también.
|
||||||
|
|
||||||
## Eligiendo el layout de tu teclado
|
## Eligiendo el layout de tu teclado
|
||||||
|
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ Recursos de Git:
|
|||||||
|
|
||||||
* [Excelente tutorial general](https://www.codecademy.com/learn/learn-git)
|
* [Excelente tutorial general](https://www.codecademy.com/learn/learn-git)
|
||||||
* [Juego de Git para aprender usando ejemplos](https://learngitbranching.js.org/)
|
* [Juego de Git para aprender usando ejemplos](https://learngitbranching.js.org/)
|
||||||
* [Recursos de Git para aprender más sobre Github](getting_started_github.md)
|
* [Recursos de Git para aprender más sobre GitHub](getting_started_github.md)
|
||||||
* [Recursos de Git dirigidos específicamente a QMK](contributing.md)
|
* [Recursos de Git dirigidos específicamente a QMK](contributing.md)
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
+16
-29
@@ -28,35 +28,32 @@ sudo udevadm trigger
|
|||||||
**/etc/udev/rules.d/50-atmel-dfu.rules:**
|
**/etc/udev/rules.d/50-atmel-dfu.rules:**
|
||||||
```
|
```
|
||||||
# Atmel ATMega32U4
|
# Atmel ATMega32U4
|
||||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="03eb", ATTRS{idProduct}=="2ff4", MODE:="0666"
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="03eb", ATTRS{idProduct}=="2ff4", TAG+="uaccess", RUN{builtin}+="uaccess"
|
||||||
# Atmel USBKEY AT90USB1287
|
# Atmel USBKEY AT90USB1287
|
||||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="03eb", ATTRS{idProduct}=="2ffb", MODE:="0666"
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="03eb", ATTRS{idProduct}=="2ffb", TAG+="uaccess", RUN{builtin}+="uaccess"
|
||||||
# Atmel ATMega32U2
|
# Atmel ATMega32U2
|
||||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="03eb", ATTRS{idProduct}=="2ff0", MODE:="0666"
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="03eb", ATTRS{idProduct}=="2ff0", TAG+="uaccess", RUN{builtin}+="uaccess"
|
||||||
```
|
```
|
||||||
|
|
||||||
**/etc/udev/rules.d/52-tmk-keyboard.rules:**
|
|
||||||
```
|
|
||||||
# tmk keyboard products https://github.com/tmk/tmk_keyboard
|
|
||||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="feed", MODE:="0666"
|
|
||||||
```
|
|
||||||
**/etc/udev/rules.d/54-input-club-keyboard.rules:**
|
**/etc/udev/rules.d/54-input-club-keyboard.rules:**
|
||||||
|
|
||||||
```
|
```
|
||||||
# Input Club keyboard bootloader
|
# Input Club keyboard bootloader
|
||||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="1c11", MODE:="0666"
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="1c11", ATTRS{idProduct}=="b007", TAG+="uaccess", RUN{builtin}+="uaccess"
|
||||||
```
|
```
|
||||||
|
|
||||||
**/etc/udev/rules.d/55-caterina.rules:**
|
**/etc/udev/rules.d/55-caterina.rules:**
|
||||||
```
|
```
|
||||||
# ModemManager should ignore the following devices
|
# ModemManager should ignore the following devices
|
||||||
ATTRS{idVendor}=="2a03", ENV{ID_MM_DEVICE_IGNORE}="1"
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="2a03", ATTRS{idProduct}=="0036", TAG+="uaccess", RUN{builtin}+="uaccess", ENV{ID_MM_DEVICE_IGNORE}="1"
|
||||||
ATTRS{idVendor}=="2341", ENV{ID_MM_DEVICE_IGNORE}="1"
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="2341", ATTRS{idProduct}=="0036", TAG+="uaccess", RUN{builtin}+="uaccess", ENV{ID_MM_DEVICE_IGNORE}="1"
|
||||||
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="1b4f", ATTRS{idProduct}=="9205", TAG+="uaccess", RUN{builtin}+="uaccess", ENV{ID_MM_DEVICE_IGNORE}="1"
|
||||||
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="1b4f", ATTRS{idProduct}=="9203", TAG+="uaccess", RUN{builtin}+="uaccess", ENV{ID_MM_DEVICE_IGNORE}="1"
|
||||||
```
|
```
|
||||||
|
|
||||||
**Note:** ModemManager filtering only works when not in strict mode, the following commands can update that settings:
|
**Note:** With older (before 1.12) ModemManager, filtering only works when not in strict mode, the following commands can update that settings:
|
||||||
```console
|
```console
|
||||||
sudo sed -i 's/--filter-policy=strict/--filter-policy=default/' /lib/systemd/system/ModemManager.service
|
printf '[Service]\nExecStart=\nExecStart=/usr/sbin/ModemManager --filter-policy=default' | sudo tee /etc/systemd/system/ModemManager.service.d/policy.conf
|
||||||
sudo systemctl daemon-reload
|
sudo systemctl daemon-reload
|
||||||
sudo systemctl restart ModemManager
|
sudo systemctl restart ModemManager
|
||||||
```
|
```
|
||||||
@@ -64,15 +61,15 @@ sudo systemctl restart ModemManager
|
|||||||
**/etc/udev/rules.d/56-dfu-util.rules:**
|
**/etc/udev/rules.d/56-dfu-util.rules:**
|
||||||
```
|
```
|
||||||
# stm32duino
|
# stm32duino
|
||||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="1eaf", ATTRS{idProduct}=="0003", MODE:="0666"
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="1eaf", ATTRS{idProduct}=="0003", TAG+="uaccess", RUN{builtin}+="uaccess"
|
||||||
# Generic stm32
|
# Generic stm32
|
||||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="0483", ATTRS{idProduct}=="df11", MODE:="0666"
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="0483", ATTRS{idProduct}=="df11", TAG+="uaccess", RUN{builtin}+="uaccess"
|
||||||
```
|
```
|
||||||
|
|
||||||
**/etc/udev/rules.d/57-bootloadhid.rules:**
|
**/etc/udev/rules.d/57-bootloadhid.rules:**
|
||||||
```
|
```
|
||||||
# bootloadHID
|
# bootloadHID
|
||||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="05df", MODE:="0666"
|
SUBSYSTEMS=="usb", ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="05df", TAG+="uaccess", RUN{builtin}+="uaccess"
|
||||||
```
|
```
|
||||||
|
|
||||||
### Serial device is not detected in bootloader mode on Linux
|
### Serial device is not detected in bootloader mode on Linux
|
||||||
@@ -113,26 +110,16 @@ OPT_DEFS += -DBOOTLOADER_SIZE=2048
|
|||||||
```
|
```
|
||||||
|
|
||||||
## `avr-gcc: internal compiler error: Abort trap: 6 (program cc1)` on MacOS
|
## `avr-gcc: internal compiler error: Abort trap: 6 (program cc1)` on MacOS
|
||||||
|
|
||||||
This is an issue with updating on brew, causing symlinks that avr-gcc depend on getting mangled.
|
This is an issue with updating on brew, causing symlinks that avr-gcc depend on getting mangled.
|
||||||
|
|
||||||
The solution is to remove and reinstall all affected modules.
|
The solution is to remove and reinstall all affected modules.
|
||||||
|
|
||||||
```
|
```
|
||||||
brew rm avr-gcc
|
brew rm avr-gcc avr-gcc@8 dfu-programmer dfu-util gcc-arm-none-eabi arm-gcc-bin@8 avrdude qmk
|
||||||
brew rm avr-gcc@8
|
brew install qmk/qmk/qmk
|
||||||
brew rm dfu-programmer
|
|
||||||
brew rm dfu-util
|
|
||||||
brew rm gcc-arm-none-eabi
|
|
||||||
brew rm arm-gcc-bin@8
|
|
||||||
brew rm avrdude
|
|
||||||
brew install avr-gcc@8
|
|
||||||
brew install dfu-programmer
|
|
||||||
brew install dfu-util
|
|
||||||
brew install arm-gcc-bin@8
|
|
||||||
brew install avrdude
|
|
||||||
brew link --force avr-gcc@8
|
brew link --force avr-gcc@8
|
||||||
brew link --force arm-gcc-bin@8
|
brew link --force arm-gcc-bin@8
|
||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
### `avr-gcc` and LUFA
|
### `avr-gcc` and LUFA
|
||||||
|
|||||||
@@ -160,10 +160,3 @@ As of now root of its cause is not clear but some build options seem to be relat
|
|||||||
|
|
||||||
https://github.com/tmk/tmk_keyboard/issues/266
|
https://github.com/tmk/tmk_keyboard/issues/266
|
||||||
https://geekhack.org/index.php?topic=41989.msg1967778#msg1967778
|
https://geekhack.org/index.php?topic=41989.msg1967778#msg1967778
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
## FLIP Doesn't Work
|
|
||||||
### `AtLibUsbDfu.dll` Not Found
|
|
||||||
Remove current driver and reinstall one FLIP provides from DeviceManager.
|
|
||||||
http://imgur.com/a/bnwzy
|
|
||||||
@@ -1,46 +1,3 @@
|
|||||||
# Switching and Toggling Layers :id=switching-and-toggling-layers
|
|
||||||
|
|
||||||
These functions allow you to activate layers in various ways. Note that layers are not generally independent layouts -- multiple layers can be activated at once, and it's typical for layers to use `KC_TRNS` to allow keypresses to pass through to lower layers. For a detailed explanation of layers, see [Keymap Overview](keymap.md#keymap-and-layers). When using momentary layer switching with MO(), LM(), TT(), or LT(), make sure to leave the key on the above layers transparent or it may not work as intended.
|
|
||||||
|
|
||||||
* `DF(layer)` - switches the default layer. The default layer is the always-active base layer that other layers stack on top of. See below for more about the default layer. This might be used to switch from QWERTY to Dvorak layout. (Note that this is a temporary switch that only persists until the keyboard loses power. To modify the default layer in a persistent way requires deeper customization, such as calling the `set_single_persistent_default_layer` function inside of [process_record_user](custom_quantum_functions.md#programming-the-behavior-of-any-keycode).)
|
|
||||||
* `MO(layer)` - momentarily activates *layer*. As soon as you let go of the key, the layer is deactivated.
|
|
||||||
* `LM(layer, mod)` - Momentarily activates *layer* (like `MO`), but with modifier(s) *mod* active. Only supports layers 0-15 and the left modifiers: `MOD_LCTL`, `MOD_LSFT`, `MOD_LALT`, `MOD_LGUI` (note the use of `MOD_` constants instead of `KC_`). These modifiers can be combined using bitwise OR, e.g. `LM(_RAISE, MOD_LCTL | MOD_LALT)`.
|
|
||||||
* `LT(layer, kc)` - momentarily activates *layer* when held, and sends *kc* when tapped. Only supports layers 0-15.
|
|
||||||
* `OSL(layer)` - momentarily activates *layer* until the next key is pressed. See [One Shot Keys](one_shot_keys.md) for details and additional functionality.
|
|
||||||
* `TG(layer)` - toggles *layer*, activating it if it's inactive and vice versa
|
|
||||||
* `TO(layer)` - activates *layer* and de-activates all other layers (except your default layer). This function is special, because instead of just adding/removing one layer to your active layer stack, it will completely replace your current active layers, uniquely allowing you to replace higher layers with a lower one. This is activated on keydown (as soon as the key is pressed).
|
|
||||||
* `TT(layer)` - Layer Tap-Toggle. If you hold the key down, *layer* is activated, and then is de-activated when you let go (like `MO`). If you repeatedly tap it, the layer will be toggled on or off (like `TG`). It needs 5 taps by default, but you can change this by defining `TAPPING_TOGGLE` -- for example, `#define TAPPING_TOGGLE 2` to toggle on just two taps.
|
|
||||||
|
|
||||||
## Caveats
|
|
||||||
|
|
||||||
Currently, `LT()` and `MT()` are limited to the [Basic Keycode set](keycodes_basic.md), meaning you can't use keycodes like `LCTL()`, `KC_TILD`, or anything greater than `0xFF`. Modifiers specified as part of a Layer Tap or Mod Tap's keycode will be ignored. If you need to apply modifiers to your tapped keycode, [Tap Dance](feature_tap_dance.md#example-5-using-tap-dance-for-advanced-mod-tap-and-layer-tap-keys) can be used to accomplish this.
|
|
||||||
|
|
||||||
Additionally, if at least one right-handed modifier is specified in a Mod Tap or Layer Tap, it will cause all modifiers specified to become right-handed, so it is not possible to mix and match the two.
|
|
||||||
|
|
||||||
# Working with Layers
|
|
||||||
|
|
||||||
Care must be taken when switching layers, it's possible to lock yourself into a layer with no way to deactivate that layer (without unplugging your keyboard.) We've created some guidelines to help users avoid the most common problems.
|
|
||||||
|
|
||||||
## Beginners
|
|
||||||
|
|
||||||
If you are just getting started with QMK you will want to keep everything simple. Follow these guidelines when setting up your layers:
|
|
||||||
|
|
||||||
* Setup layer 0 as your default, "base" layer. This is your normal typing layer, and could be whatever layout you want (qwerty, dvorak, colemak, etc.). It's important to set this as the lowest layer since it will typically have most or all of the keyboard's keys defined, so would block other layers from having any effect if it were above them (i.e., had a higher layer number).
|
|
||||||
* Arrange your layers in a "tree" layout, with layer 0 as the root. Do not try to enter the same layer from more than one other layer.
|
|
||||||
* In a layer's keymap, only reference higher-numbered layers. Because layers are processed from the highest-numbered (topmost) active layer down, modifying the state of lower layers can be tricky and error-prone.
|
|
||||||
|
|
||||||
## Intermediate Users
|
|
||||||
|
|
||||||
Sometimes you need more than one base layer. For example, if you want to switch between QWERTY and Dvorak, switch between layouts for different countries, or switch your layout for different videogames. Your base layers should always be the lowest numbered layers. When you have multiple base layers you should always treat them as mutually exclusive. When one base layer is on the others are off.
|
|
||||||
|
|
||||||
## Advanced Users
|
|
||||||
|
|
||||||
Once you have a good feel for how layers work and what you can do, you can get more creative. The rules listed in the beginner section will help you be successful by avoiding some of the tricker details but they can be constraining, especially for ultra-compact keyboard users. Understanding how layers work will allow you to use them in more advanced ways.
|
|
||||||
|
|
||||||
Layers stack on top of each other in numerical order. When determining what a keypress does, QMK scans the layers from the top down, stopping when it reaches the first active layer that is not set to `KC_TRNS`. As a result if you activate a layer that is numerically lower than your current layer, and your current layer (or another layer that is active and higher than your target layer) has something other than `KC_TRNS`, that is the key that will be sent, not the key on the layer you just activated. This is the cause of most people's "why doesn't my layer get switched" problem.
|
|
||||||
|
|
||||||
Sometimes, you might want to switch between layers in a macro or as part of a tap dance routine. `layer_on` activates a layer, and `layer_off` deactivates it. More layer-related functions can be found in [action_layer.h](https://github.com/qmk/qmk_firmware/blob/master/tmk_core/common/action_layer.h).
|
|
||||||
|
|
||||||
# Modifier Keys :id=modifier-keys
|
# Modifier Keys :id=modifier-keys
|
||||||
|
|
||||||
These allow you to combine a modifier with a keycode. When pressed, the keydown event for the modifier, then `kc` will be sent. On release, the keyup event for `kc`, then the modifier will be sent.
|
These allow you to combine a modifier with a keycode. When pressed, the keydown event for the modifier, then `kc` will be sent. On release, the keyup event for `kc`, then the modifier will be sent.
|
||||||
@@ -49,11 +6,11 @@ These allow you to combine a modifier with a keycode. When pressed, the keydown
|
|||||||
|----------|-------------------------------|----------------------------------------------------|
|
|----------|-------------------------------|----------------------------------------------------|
|
||||||
|`LCTL(kc)`|`C(kc)` |Hold Left Control and press `kc` |
|
|`LCTL(kc)`|`C(kc)` |Hold Left Control and press `kc` |
|
||||||
|`LSFT(kc)`|`S(kc)` |Hold Left Shift and press `kc` |
|
|`LSFT(kc)`|`S(kc)` |Hold Left Shift and press `kc` |
|
||||||
|`LALT(kc)`|`A(kc)` |Hold Left Alt and press `kc` |
|
|`LALT(kc)`|`A(kc)`, `LOPT(kc)` |Hold Left Alt and press `kc` |
|
||||||
|`LGUI(kc)`|`G(kc)`, `LCMD(kc)`, `LWIN(kc)`|Hold Left GUI and press `kc` |
|
|`LGUI(kc)`|`G(kc)`, `LCMD(kc)`, `LWIN(kc)`|Hold Left GUI and press `kc` |
|
||||||
|`RCTL(kc)`| |Hold Right Control and press `kc` |
|
|`RCTL(kc)`| |Hold Right Control and press `kc` |
|
||||||
|`RSFT(kc)`| |Hold Right Shift and press `kc` |
|
|`RSFT(kc)`| |Hold Right Shift and press `kc` |
|
||||||
|`RALT(kc)`|`ALGR(kc)` |Hold Right Alt and press `kc` |
|
|`RALT(kc)`|`ROPT(kc)`, `ALGR(kc)` |Hold Right Alt and press `kc` |
|
||||||
|`RGUI(kc)`|`RCMD(kc)`, `LWIN(kc)` |Hold Right GUI and press `kc` |
|
|`RGUI(kc)`|`RCMD(kc)`, `LWIN(kc)` |Hold Right GUI and press `kc` |
|
||||||
|`SGUI(kc)`|`SCMD(kc)`, `SWIN(kc)` |Hold Left Shift and GUI and press `kc` |
|
|`SGUI(kc)`|`SCMD(kc)`, `SWIN(kc)` |Hold Left Shift and GUI and press `kc` |
|
||||||
|`LCA(kc)` | |Hold Left Control and Alt and press `kc` |
|
|`LCA(kc)` | |Hold Left Control and Alt and press `kc` |
|
||||||
@@ -61,12 +18,16 @@ These allow you to combine a modifier with a keycode. When pressed, the keydown
|
|||||||
|`MEH(kc)` | |Hold Left Control, Shift and Alt and press `kc` |
|
|`MEH(kc)` | |Hold Left Control, Shift and Alt and press `kc` |
|
||||||
|`HYPR(kc)`| |Hold Left Control, Shift, Alt and GUI and press `kc`|
|
|`HYPR(kc)`| |Hold Left Control, Shift, Alt and GUI and press `kc`|
|
||||||
|
|
||||||
You can also chain them, for example `LCTL(LALT(KC_DEL))` makes a key that sends Control+Alt+Delete with a single keypress.
|
You can also chain them, for example `LCTL(LALT(KC_DEL))` or `C(A(KC_DEL))` makes a key that sends Control+Alt+Delete with a single keypress.
|
||||||
|
|
||||||
# Legacy Content
|
# Legacy Content :id=legacy-content
|
||||||
|
|
||||||
This page used to encompass a large set of features. We have moved many sections that used to be part of this page to their own pages. Everything below this point is simply a redirect so that people following old links on the web find what they're looking for.
|
This page used to encompass a large set of features. We have moved many sections that used to be part of this page to their own pages. Everything below this point is simply a redirect so that people following old links on the web find what they're looking for.
|
||||||
|
|
||||||
|
## Layers :id=switching-and-toggling-layers
|
||||||
|
|
||||||
|
* [Layers](feature_layers.md)
|
||||||
|
|
||||||
## Mod-Tap :id=mod-tap
|
## Mod-Tap :id=mod-tap
|
||||||
|
|
||||||
* [Mod-Tap](mod_tap.md)
|
* [Mod-Tap](mod_tap.md)
|
||||||
|
|||||||
+110
-139
@@ -1,4 +1,4 @@
|
|||||||
# Backlighting
|
# Backlighting :id=backlighting
|
||||||
|
|
||||||
Many keyboards support backlit keys by way of individual LEDs placed through or underneath the keyswitches. This feature is distinct from both the [RGB underglow](feature_rgblight.md) and [RGB matrix](feature_rgb_matrix.md) features as it usually allows for only a single colour per switch, though you can obviously install multiple different single coloured LEDs on a keyboard.
|
Many keyboards support backlit keys by way of individual LEDs placed through or underneath the keyswitches. This feature is distinct from both the [RGB underglow](feature_rgblight.md) and [RGB matrix](feature_rgb_matrix.md) features as it usually allows for only a single colour per switch, though you can obviously install multiple different single coloured LEDs on a keyboard.
|
||||||
|
|
||||||
@@ -6,103 +6,106 @@ QMK is able to control the brightness of these LEDs by switching them on and off
|
|||||||
|
|
||||||
The MCU can only supply so much current to its GPIO pins. Instead of powering the backlight directly from the MCU, the backlight pin is connected to a transistor or MOSFET that switches the power to the LEDs.
|
The MCU can only supply so much current to its GPIO pins. Instead of powering the backlight directly from the MCU, the backlight pin is connected to a transistor or MOSFET that switches the power to the LEDs.
|
||||||
|
|
||||||
## Feature Configuration
|
|
||||||
|
|
||||||
Most keyboards have backlighting enabled by default if they support it, but if it is not working for you, check that your `rules.mk` includes the following:
|
Most keyboards have backlighting enabled by default if they support it, but if it is not working for you, check that your `rules.mk` includes the following:
|
||||||
|
|
||||||
```makefile
|
```makefile
|
||||||
BACKLIGHT_ENABLE = yes
|
BACKLIGHT_ENABLE = yes
|
||||||
```
|
```
|
||||||
|
|
||||||
## Keycodes
|
## Keycodes :id=keycodes
|
||||||
Once enabled the following keycodes below can be used to change the backlight level.
|
|
||||||
|
|
||||||
|Key |Description |
|
Once enabled, the following keycodes below can be used to change the backlight level.
|
||||||
|---------|------------------------------------------|
|
|
||||||
|`BL_TOGG`|Turn the backlight on or off |
|
|
||||||
|`BL_STEP`|Cycle through backlight levels |
|
|
||||||
|`BL_ON` |Set the backlight to max brightness |
|
|
||||||
|`BL_OFF` |Turn the backlight off |
|
|
||||||
|`BL_INC` |Increase the backlight level |
|
|
||||||
|`BL_DEC` |Decrease the backlight level |
|
|
||||||
|`BL_BRTG`|Toggle backlight breathing |
|
|
||||||
|
|
||||||
## Backlight Functions
|
|Key |Description |
|
||||||
|
|---------|-----------------------------------|
|
||||||
|
|`BL_TOGG`|Turn the backlight on or off |
|
||||||
|
|`BL_STEP`|Cycle through backlight levels |
|
||||||
|
|`BL_ON` |Set the backlight to max brightness|
|
||||||
|
|`BL_OFF` |Turn the backlight off |
|
||||||
|
|`BL_INC` |Increase the backlight level |
|
||||||
|
|`BL_DEC` |Decrease the backlight level |
|
||||||
|
|`BL_BRTG`|Toggle backlight breathing |
|
||||||
|
|
||||||
|Function |Description |
|
## Functions :id=functions
|
||||||
|----------|-----------------------------------------------------------|
|
|
||||||
|`backlight_toggle()` |Turn the backlight on or off |
|
|
||||||
|`backlight_enable()` |Turn the backlight on |
|
|
||||||
|`backlight_disable()` |Turn the backlight off |
|
|
||||||
|`backlight_step()` |Cycle through backlight levels |
|
|
||||||
|`backlight_increase()` |Increase the backlight level |
|
|
||||||
|`backlight_decrease()` |Decrease the backlight level |
|
|
||||||
|`backlight_level(x)` |Sets the backlight level to specified level |
|
|
||||||
|`get_backlight_level()` |Return the current backlight level |
|
|
||||||
|`is_backlight_enabled()`|Return whether the backlight is currently on |
|
|
||||||
|
|
||||||
### Backlight Breathing Functions
|
These functions can be used to change the backlighting in custom code:
|
||||||
|
|
||||||
|Function |Description |
|
|Function |Description |
|
||||||
|----------|---------------------------------------------------|
|
|------------------------|--------------------------------------------|
|
||||||
|`breathing_toggle()` |Turn the backlight breathing on or off |
|
|`backlight_toggle()` |Turn the backlight on or off |
|
||||||
|`breathing_enable()` |Turns on backlight breathing |
|
|`backlight_enable()` |Turn the backlight on |
|
||||||
|`breathing_disable()` |Turns off backlight breathing |
|
|`backlight_disable()` |Turn the backlight off |
|
||||||
|
|`backlight_step()` |Cycle through backlight levels |
|
||||||
|
|`backlight_increase()` |Increase the backlight level |
|
||||||
|
|`backlight_decrease()` |Decrease the backlight level |
|
||||||
|
|`backlight_level(x)` |Sets the backlight level to specified level |
|
||||||
|
|`get_backlight_level()` |Return the current backlight level |
|
||||||
|
|`is_backlight_enabled()`|Return whether the backlight is currently on|
|
||||||
|
|
||||||
## Driver Configuration
|
If backlight breathing is enabled (see below), the following functions are also available:
|
||||||
|
|
||||||
|
|Function |Description |
|
||||||
|
|---------------------|--------------------------------------|
|
||||||
|
|`breathing_toggle()` |Turn the backlight breathing on or off|
|
||||||
|
|`breathing_enable()` |Turns on backlight breathing |
|
||||||
|
|`breathing_disable()`|Turns off backlight breathing |
|
||||||
|
|
||||||
|
## Configuration :id=configuration
|
||||||
|
|
||||||
To select which driver to use, configure your `rules.mk` with the following:
|
To select which driver to use, configure your `rules.mk` with the following:
|
||||||
|
|
||||||
```makefile
|
```makefile
|
||||||
BACKLIGHT_DRIVER = software # Valid driver values are 'pwm,software,no'
|
BACKLIGHT_DRIVER = software
|
||||||
```
|
```
|
||||||
|
|
||||||
See below for help on individual drivers.
|
Valid driver values are `pwm`, `software`, `custom` or `no`. See below for help on individual drivers.
|
||||||
|
|
||||||
## Common Driver Configuration
|
To configure the backlighting, `#define` these in your `config.h`:
|
||||||
|
|
||||||
To change the behavior of the backlighting, `#define` these in your `config.h`:
|
|Define |Default |Description |
|
||||||
|
|---------------------|-------------|-------------------------------------------------------------------------------------|
|
||||||
|
|`BACKLIGHT_PIN` |*Not defined*|The pin that controls the LED(s) |
|
||||||
|
|`BACKLIGHT_LEVELS` |`3` |The number of brightness levels (maximum 31 excluding off) |
|
||||||
|
|`BACKLIGHT_CAPS_LOCK`|*Not defined*|Enable Caps Lock indicator using backlight (for keyboards without dedicated LED) |
|
||||||
|
|`BACKLIGHT_BREATHING`|*Not defined*|Enable backlight breathing, if supported |
|
||||||
|
|`BREATHING_PERIOD` |`6` |The length of one backlight "breath" in seconds |
|
||||||
|
|`BACKLIGHT_ON_STATE` |`1` |The state of the backlight pin when the backlight is "on" - `1` for high, `0` for low|
|
||||||
|
|
||||||
|Define |Default |Description |
|
Unless you are designing your own keyboard, you generally should not need to change the `BACKLIGHT_PIN` or `BACKLIGHT_ON_STATE`.
|
||||||
|---------------------|-------------|--------------------------------------------------------------------------------------|
|
|
||||||
|`BACKLIGHT_LEVELS` |`3` |The number of brightness levels (maximum 31 excluding off) |
|
|
||||||
|`BACKLIGHT_CAPS_LOCK`|*Not defined*|Enable Caps Lock indicator using backlight (for keyboards without dedicated LED) |
|
|
||||||
|`BACKLIGHT_BREATHING`|*Not defined*|Enable backlight breathing, if supported |
|
|
||||||
|`BREATHING_PERIOD` |`6` |The length of one backlight "breath" in seconds |
|
|
||||||
|`BACKLIGHT_ON_STATE` |`0` |The state of the backlight pin when the backlight is "on" - `1` for high, `0` for low |
|
|
||||||
|
|
||||||
### Backlight On State
|
### Backlight On State :id=backlight-on-state
|
||||||
|
|
||||||
Most backlight circuits are driven by an N-channel MOSFET or NPN transistor. This means that to turn the transistor *on* and light the LEDs, you must drive the backlight pin, connected to the gate or base, *high*.
|
Most backlight circuits are driven by an N-channel MOSFET or NPN transistor. This means that to turn the transistor *on* and light the LEDs, you must drive the backlight pin, connected to the gate or base, *high*.
|
||||||
Sometimes, however, a P-channel MOSFET, or a PNP transistor is used. In this case, when the transistor is on, the pin is driven *low* instead.
|
Sometimes, however, a P-channel MOSFET, or a PNP transistor is used. In this case, when the transistor is on, the pin is driven *low* instead.
|
||||||
|
|
||||||
This functionality is configured at the keyboard level with the `BACKLIGHT_ON_STATE` define.
|
This functionality is configured at the keyboard level with the `BACKLIGHT_ON_STATE` define.
|
||||||
|
|
||||||
## AVR driver
|
### AVR Driver :id=avr-driver
|
||||||
|
|
||||||
|
The `pwm` driver is configured by default, however the equivalent setting within `rules.mk` would be:
|
||||||
|
|
||||||
On AVR boards, the default driver currently sniffs the configuration to pick the best scenario. The driver is configured by default, however the equivalent setting within rules.mk would be:
|
|
||||||
```makefile
|
```makefile
|
||||||
BACKLIGHT_DRIVER = pwm
|
BACKLIGHT_DRIVER = pwm
|
||||||
```
|
```
|
||||||
|
|
||||||
### Caveats
|
#### Caveats :id=avr-caveats
|
||||||
|
|
||||||
Hardware PWM is supported according to the following table:
|
On AVR boards, QMK automatically decides which driver to use according to the following table:
|
||||||
|
|
||||||
|Backlight Pin|AT90USB64/128|ATmega16/32U4|ATmega16/32U2|ATmega32A|ATmega328P|
|
|Backlight Pin|AT90USB64/128|ATmega16/32U4|ATmega16/32U2|ATmega32A|ATmega328/P|
|
||||||
|-------------|-------------|-------------|-------------|---------|----------|
|
|-------------|-------------|-------------|-------------|---------|-----------|
|
||||||
|`B1` | | | | |Timer 1 |
|
|`B1` | | | | |Timer 1 |
|
||||||
|`B2` | | | | |Timer 1 |
|
|`B2` | | | | |Timer 1 |
|
||||||
|`B5` |Timer 1 |Timer 1 | | | |
|
|`B5` |Timer 1 |Timer 1 | | | |
|
||||||
|`B6` |Timer 1 |Timer 1 | | | |
|
|`B6` |Timer 1 |Timer 1 | | | |
|
||||||
|`B7` |Timer 1 |Timer 1 |Timer 1 | | |
|
|`B7` |Timer 1 |Timer 1 |Timer 1 | | |
|
||||||
|`C4` |Timer 3 | | | | |
|
|`C4` |Timer 3 | | | | |
|
||||||
|`C5` |Timer 3 | |Timer 1 | | |
|
|`C5` |Timer 3 | |Timer 1 | | |
|
||||||
|`C6` |Timer 3 |Timer 3 |Timer 1 | | |
|
|`C6` |Timer 3 |Timer 3 |Timer 1 | | |
|
||||||
|`D4` | | | |Timer 1 | |
|
|`D4` | | | |Timer 1 | |
|
||||||
|`D5` | | | |Timer 1 | |
|
|`D5` | | | |Timer 1 | |
|
||||||
|
|
||||||
All other pins will use software PWM. If the [Audio](feature_audio.md) feature is disabled or only using one timer, the backlight PWM can be triggered by a hardware timer:
|
All other pins will use timer-assisted software PWM:
|
||||||
|
|
||||||
|Audio Pin|Audio Timer|Software PWM Timer|
|
|Audio Pin|Audio Timer|Software PWM Timer|
|
||||||
|---------|-----------|------------------|
|
|---------|-----------|------------------|
|
||||||
@@ -113,44 +116,9 @@ All other pins will use software PWM. If the [Audio](feature_audio.md) feature i
|
|||||||
|`B6` |Timer 1 |Timer 3 |
|
|`B6` |Timer 1 |Timer 3 |
|
||||||
|`B7` |Timer 1 |Timer 3 |
|
|`B7` |Timer 1 |Timer 3 |
|
||||||
|
|
||||||
When both timers are in use for Audio, the backlight PWM will not use a hardware timer, but will instead be triggered during the matrix scan. In this case, breathing is not supported, and the backlight might flicker, because the PWM computation may not be called with enough timing precision.
|
When both timers are in use for Audio, the backlight PWM cannot use a hardware timer, and will instead be triggered during the matrix scan. In this case, breathing is not supported, and the backlight might flicker, because the PWM computation may not be called with enough timing precision.
|
||||||
|
|
||||||
### AVR Configuration
|
#### Hardware PWM Implementation :id=hardware-pwm-implementation
|
||||||
|
|
||||||
To change the behavior of the backlighting, `#define` these in your `config.h`:
|
|
||||||
|
|
||||||
|Define |Default |Description |
|
|
||||||
|---------------------|-------------|-------------------------------------------------------------------------------------------------------------|
|
|
||||||
|`BACKLIGHT_PIN` |`B7` |The pin that controls the LEDs. Unless you are designing your own keyboard, you shouldn't need to change this|
|
|
||||||
|`BACKLIGHT_PINS` |*Not defined*|experimental: see below for more information |
|
|
||||||
|`BACKLIGHT_LEVELS` |`3` |The number of brightness levels (maximum 31 excluding off) |
|
|
||||||
|`BACKLIGHT_CAPS_LOCK`|*Not defined*|Enable Caps Lock indicator using backlight (for keyboards without dedicated LED) |
|
|
||||||
|`BACKLIGHT_BREATHING`|*Not defined*|Enable backlight breathing, if supported |
|
|
||||||
|`BREATHING_PERIOD` |`6` |The length of one backlight "breath" in seconds |
|
|
||||||
|`BACKLIGHT_ON_STATE` |`1` |The state of the backlight pin when the backlight is "on" - `1` for high, `0` for low |
|
|
||||||
|
|
||||||
### Backlight On State
|
|
||||||
|
|
||||||
Most backlight circuits are driven by an N-channel MOSFET or NPN transistor. This means that to turn the transistor *on* and light the LEDs, you must drive the backlight pin, connected to the gate or base, *high*.
|
|
||||||
Sometimes, however, a P-channel MOSFET, or a PNP transistor is used. In this case, when the transistor is on, the pin is driven *low* instead.
|
|
||||||
|
|
||||||
This functionality is configured at the keyboard level with the `BACKLIGHT_ON_STATE` define.
|
|
||||||
|
|
||||||
### Multiple backlight pins
|
|
||||||
|
|
||||||
Most keyboards have only one backlight pin which control all backlight LEDs (especially if the backlight is connected to an hardware PWM pin).
|
|
||||||
In software PWM, it is possible to define multiple backlight pins. All those pins will be turned on and off at the same time during the PWM duty cycle.
|
|
||||||
This feature allows to set for instance the Caps Lock LED (or any other controllable LED) brightness at the same level as the other LEDs of the backlight. This is useful if you have mapped LCTRL in place of Caps Lock and you need the Caps Lock LED to be part of the backlight instead of being activated when Caps Lock is on.
|
|
||||||
|
|
||||||
To activate multiple backlight pins, you need to add something like this to your user `config.h`:
|
|
||||||
|
|
||||||
```c
|
|
||||||
#define BACKLIGHT_LED_COUNT 2
|
|
||||||
#undef BACKLIGHT_PIN
|
|
||||||
#define BACKLIGHT_PINS { F5, B2 }
|
|
||||||
```
|
|
||||||
|
|
||||||
### Hardware PWM Implementation
|
|
||||||
|
|
||||||
When using the supported pins for backlighting, QMK will use a hardware timer configured to output a PWM signal. This timer will count up to `ICRx` (by default `0xFFFF`) before resetting to 0.
|
When using the supported pins for backlighting, QMK will use a hardware timer configured to output a PWM signal. This timer will count up to `ICRx` (by default `0xFFFF`) before resetting to 0.
|
||||||
The desired brightness is calculated and stored in the `OCRxx` register. When the counter reaches this value, the backlight pin will go low, and is pulled high again when the counter resets.
|
The desired brightness is calculated and stored in the `OCRxx` register. When the counter reaches this value, the backlight pin will go low, and is pulled high again when the counter resets.
|
||||||
@@ -159,7 +127,7 @@ In this way `OCRxx` essentially controls the duty cycle of the LEDs, and thus th
|
|||||||
The breathing effect is achieved by registering an interrupt handler for `TIMER1_OVF_vect` that is called whenever the counter resets, roughly 244 times per second.
|
The breathing effect is achieved by registering an interrupt handler for `TIMER1_OVF_vect` that is called whenever the counter resets, roughly 244 times per second.
|
||||||
In this handler, the value of an incrementing counter is mapped onto a precomputed brightness curve. To turn off breathing, the interrupt handler is simply disabled, and the brightness reset to the level stored in EEPROM.
|
In this handler, the value of an incrementing counter is mapped onto a precomputed brightness curve. To turn off breathing, the interrupt handler is simply disabled, and the brightness reset to the level stored in EEPROM.
|
||||||
|
|
||||||
### Timer Assisted PWM Implementation
|
#### Timer Assisted PWM Implementation :id=timer-assisted-implementation
|
||||||
|
|
||||||
When `BACKLIGHT_PIN` is not set to a hardware backlight pin, QMK will use a hardware timer configured to trigger software interrupts. This time will count up to `ICRx` (by default `0xFFFF`) before resetting to 0.
|
When `BACKLIGHT_PIN` is not set to a hardware backlight pin, QMK will use a hardware timer configured to trigger software interrupts. This time will count up to `ICRx` (by default `0xFFFF`) before resetting to 0.
|
||||||
When resetting to 0, the CPU will fire an OVF (overflow) interrupt that will turn the LEDs on, starting the duty cycle.
|
When resetting to 0, the CPU will fire an OVF (overflow) interrupt that will turn the LEDs on, starting the duty cycle.
|
||||||
@@ -168,81 +136,84 @@ In this way `OCRxx` essentially controls the duty cycle of the LEDs, and thus th
|
|||||||
|
|
||||||
The breathing effect is the same as in the hardware PWM implementation.
|
The breathing effect is the same as in the hardware PWM implementation.
|
||||||
|
|
||||||
## ARM Driver
|
### ARM Driver :id=arm-configuration
|
||||||
|
|
||||||
|
While still in its early stages, ARM backlight support aims to eventually have feature parity with AVR. The `pwm` driver is configured by default, however the equivalent setting within `rules.mk` would be:
|
||||||
|
|
||||||
While still in its early stages, ARM backlight support aims to eventually have feature parity with AVR. The driver is configured by default, however the equivalent setting within rules.mk would be:
|
|
||||||
```makefile
|
```makefile
|
||||||
BACKLIGHT_DRIVER = pwm
|
BACKLIGHT_DRIVER = pwm
|
||||||
```
|
```
|
||||||
|
|
||||||
### Caveats
|
#### ChibiOS Configuration :id=arm-configuration
|
||||||
|
|
||||||
|
The following `#define`s apply only to ARM-based keyboards:
|
||||||
|
|
||||||
|
|Define |Default|Description |
|
||||||
|
|-----------------------|-------|-----------------------------------|
|
||||||
|
|`BACKLIGHT_PWM_DRIVER` |`PWMD4`|The PWM driver to use |
|
||||||
|
|`BACKLIGHT_PWM_CHANNEL`|`3` |The PWM channel to use |
|
||||||
|
|`BACKLIGHT_PAL_MODE` |`2` |The pin alternative function to use|
|
||||||
|
|
||||||
|
See the ST datasheet for your particular MCU to determine these values. Unless you are designing your own keyboard, you generally should not need to change them.
|
||||||
|
|
||||||
|
#### Caveats :id=arm-caveats
|
||||||
|
|
||||||
Currently only hardware PWM is supported, not timer assisted, and does not provide automatic configuration.
|
Currently only hardware PWM is supported, not timer assisted, and does not provide automatic configuration.
|
||||||
|
|
||||||
?> Backlight support for STMF072 has had limited testing, YMMV. If unsure, set `BACKLIGHT_ENABLE = no` in your rules.mk.
|
?> Backlight support for STM32F072 has had limited testing, so YMMV. If unsure, set `BACKLIGHT_ENABLE = no` in your `rules.mk`.
|
||||||
|
|
||||||
### ARM Configuration
|
### Software PWM Driver :id=software-pwm-driver
|
||||||
|
|
||||||
To change the behavior of the backlighting, `#define` these in your `config.h`:
|
In this mode, PWM is "emulated" while running other keyboard tasks. It offers maximum hardware compatibility without extra platform configuration. The tradeoff is the backlight might jitter when the keyboard is busy. To enable, add this to your `rules.mk`:
|
||||||
|
|
||||||
|Define |Default |Description |
|
|
||||||
|------------------------|-------------|-------------------------------------------------------------------------------------------------------------|
|
|
||||||
|`BACKLIGHT_PIN` |`B7` |The pin that controls the LEDs. Unless you are designing your own keyboard, you shouldn't need to change this|
|
|
||||||
|`BACKLIGHT_PWM_DRIVER` |`PWMD4` |The PWM driver to use, see ST datasheets for pin to PWM timer mapping. Unless you are designing your own keyboard, you shouldn't need to change this|
|
|
||||||
|`BACKLIGHT_PWM_CHANNEL` |`3` |The PWM channel to use, see ST datasheets for pin to PWM channel mapping. Unless you are designing your own keyboard, you shouldn't need to change this|
|
|
||||||
|`BACKLIGHT_PAL_MODE` |`2` |The pin alternative function to use, see ST datasheets for pin AF mapping. Unless you are designing your own keyboard, you shouldn't need to change this|
|
|
||||||
|
|
||||||
## Software PWM Driver :id=software-pwm-driver
|
|
||||||
|
|
||||||
Emulation of PWM while running other keyboard tasks, it offers maximum hardware compatibility without extra platform configuration. The tradeoff is the backlight might jitter when the keyboard is busy. To enable, add this to your rules.mk:
|
|
||||||
```makefile
|
```makefile
|
||||||
BACKLIGHT_DRIVER = software
|
BACKLIGHT_DRIVER = software
|
||||||
```
|
```
|
||||||
|
|
||||||
### Software PWM Configuration
|
#### Multiple Backlight Pins :id=multiple-backlight-pins
|
||||||
|
|
||||||
To change the behavior of the backlighting, `#define` these in your `config.h`:
|
|
||||||
|
|
||||||
|Define |Default |Description |
|
|
||||||
|-----------------|-------------|-------------------------------------------------------------------------------------------------------------|
|
|
||||||
|`BACKLIGHT_PIN` |`B7` |The pin that controls the LEDs. Unless you are designing your own keyboard, you shouldn't need to change this|
|
|
||||||
|`BACKLIGHT_PINS` |*Not defined*|experimental: see below for more information |
|
|
||||||
|
|
||||||
### Multiple backlight pins
|
|
||||||
|
|
||||||
Most keyboards have only one backlight pin which control all backlight LEDs (especially if the backlight is connected to an hardware PWM pin).
|
Most keyboards have only one backlight pin which control all backlight LEDs (especially if the backlight is connected to an hardware PWM pin).
|
||||||
In software PWM, it is possible to define multiple backlight pins. All those pins will be turned on and off at the same time during the PWM duty cycle.
|
In software PWM, it is possible to define multiple backlight pins, which will be turned on and off at the same time during the PWM duty cycle.
|
||||||
This feature allows to set for instance the Caps Lock LED (or any other controllable LED) brightness at the same level as the other LEDs of the backlight. This is useful if you have mapped LCTRL in place of Caps Lock and you need the Caps Lock LED to be part of the backlight instead of being activated when Caps Lock is on.
|
|
||||||
|
|
||||||
To activate multiple backlight pins, you need to add something like this to your user `config.h`:
|
This feature allows to set, for instance, the Caps Lock LED's (or any other controllable LED) brightness at the same level as the other LEDs of the backlight. This is useful if you have mapped Control in place of Caps Lock and you need the Caps Lock LED to be part of the backlight instead of being activated when Caps Lock is on, as it is usually wired to a separate pin from the backlight.
|
||||||
|
|
||||||
|
To activate multiple backlight pins, add something like this to your `config.h`, instead of `BACKLIGHT_PIN`:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
#undef BACKLIGHT_PIN
|
|
||||||
#define BACKLIGHT_PINS { F5, B2 }
|
#define BACKLIGHT_PINS { F5, B2 }
|
||||||
```
|
```
|
||||||
|
|
||||||
## Custom Driver
|
### Custom Driver :id=custom-driver
|
||||||
|
|
||||||
To enable, add this to your rules.mk:
|
If none of the above drivers apply to your board (for example, you are using a separate IC to control the backlight), you can implement a custom backlight driver using this simple API provided by QMK. To enable, add this to your `rules.mk`:
|
||||||
|
|
||||||
```makefile
|
```makefile
|
||||||
BACKLIGHT_DRIVER = custom
|
BACKLIGHT_DRIVER = custom
|
||||||
```
|
```
|
||||||
|
|
||||||
When implementing the custom driver API, the provided keyboard hooks are as follows:
|
Then implement any of these hooks:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
void backlight_init_ports(void) {
|
void backlight_init_ports(void) {
|
||||||
// Optional - Run on startup
|
// Optional - runs on startup
|
||||||
// - usually you want to configure pins here
|
// Usually you want to configure pins here
|
||||||
}
|
}
|
||||||
void backlight_set(uint8_t level) {
|
void backlight_set(uint8_t level) {
|
||||||
// Optional - Run on level change
|
// Optional - runs on level change
|
||||||
// - usually you want to respond to the new value
|
// Usually you want to respond to the new value
|
||||||
}
|
}
|
||||||
|
|
||||||
void backlight_task(void) {
|
void backlight_task(void) {
|
||||||
// Optional - Run periodically
|
// Optional - runs periodically
|
||||||
// - long running actions here can cause performance issues
|
// Note that this is called in the main keyboard loop,
|
||||||
|
// so long running actions here can cause performance issues
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
## Example Schematic
|
||||||
|
|
||||||
|
In this typical example, the backlight LEDs are all connected in parallel towards an N-channel MOSFET. Its gate pin is wired to one of the microcontroller's GPIO pins through a 470Ω resistor to avoid ringing.
|
||||||
|
A pulldown resistor is also placed between the gate pin and ground to keep it at a defined state when it is not otherwise being driven by the MCU.
|
||||||
|
The values of these resistors are not critical - see [this Electronics StackExchange question](https://electronics.stackexchange.com/q/68748) for more information.
|
||||||
|
|
||||||
|

|
||||||
@@ -123,7 +123,7 @@ If you would like to change the hotkey assignments for Bootmagic, `#define` thes
|
|||||||
|
|
||||||
# Bootmagic Lite :id=bootmagic-lite
|
# Bootmagic Lite :id=bootmagic-lite
|
||||||
|
|
||||||
In addition to the full blown Bootmagic feature, is the Bootmagic Lite feature that only handles jumping into the bootloader. This is great for boards that don't have a physical reset button but you need a way to jump into the bootloader, and don't want to deal with the headache that Bootmagic can cause.
|
In addition to the full blown Bootmagic feature, is the Bootmagic Lite feature that only handles jumping into the bootloader. This is great for boards that don't have a physical reset button but you need a way to jump into the bootloader, and don't want to deal with the headache that Bootmagic can cause.
|
||||||
|
|
||||||
To enable this version of Bootmagic, you need to enable it in your `rules.mk` with:
|
To enable this version of Bootmagic, you need to enable it in your `rules.mk` with:
|
||||||
|
|
||||||
@@ -131,7 +131,7 @@ To enable this version of Bootmagic, you need to enable it in your `rules.mk` wi
|
|||||||
BOOTMAGIC_ENABLE = lite
|
BOOTMAGIC_ENABLE = lite
|
||||||
```
|
```
|
||||||
|
|
||||||
Additionally, you may want to specify which key to use. This is especially useful for keyboards that have unusual matrices. To do so, you need to specify the row and column of the key that you want to use. Add these entries to your `config.h` file:
|
Additionally, you may want to specify which key to use. This is especially useful for keyboards that have unusual matrices. To do so, you need to specify the row and column of the key that you want to use. Add these entries to your `config.h` file:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
#define BOOTMAGIC_LITE_ROW 0
|
#define BOOTMAGIC_LITE_ROW 0
|
||||||
@@ -144,9 +144,20 @@ And to trigger the bootloader, you hold this key down when plugging the keyboard
|
|||||||
|
|
||||||
!> Using bootmagic lite will **always reset** the EEPROM, so you will lose any settings that have been saved.
|
!> Using bootmagic lite will **always reset** the EEPROM, so you will lose any settings that have been saved.
|
||||||
|
|
||||||
|
## Split Keyboards
|
||||||
|
|
||||||
|
When handedness is predetermined via an option like `SPLIT_HAND_PIN`, you might need to configure a different key between halves. This To do so, add these entries to your `config.h` file:
|
||||||
|
|
||||||
|
```c
|
||||||
|
#define BOOTMAGIC_LITE_ROW_RIGHT 4
|
||||||
|
#define BOOTMAGIC_LITE_COLUMN_RIGHT 1
|
||||||
|
```
|
||||||
|
|
||||||
|
By default, these values are not set.
|
||||||
|
|
||||||
## Advanced Bootmagic Lite
|
## Advanced Bootmagic Lite
|
||||||
|
|
||||||
The `bootmagic_lite` function is defined weakly, so that you can replace this in your code, if you need. A great example of this is the Zeal60 boards that have some additional handling needed.
|
The `bootmagic_lite` function is defined weakly, so that you can replace this in your code, if you need. A great example of this is the Zeal60 boards that have some additional handling needed.
|
||||||
|
|
||||||
To replace the function, all you need to do is add something like this to your code:
|
To replace the function, all you need to do is add something like this to your code:
|
||||||
|
|
||||||
@@ -163,4 +174,4 @@ void bootmagic_lite(void) {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
You can additional feature here. For instance, resetting the eeprom or requiring additional keys to be pressed to trigger bootmagic. Keep in mind that `bootmagic_lite` is called before a majority of features are initialized in the firmware.
|
You can additional feature here. For instance, resetting the eeprom or requiring additional keys to be pressed to trigger bootmagic. Keep in mind that `bootmagic_lite` is called before a majority of features are initialized in the firmware.
|
||||||
@@ -38,5 +38,6 @@ For use in keyboards where refreshing ```NUM_KEYS``` 8-bit counters is computati
|
|||||||
appropriate for the ErgoDox models; the matrix is rotated 90°, and hence its "rows" are really columns, and each finger only hits a single "row" at a time in normal use.
|
appropriate for the ErgoDox models; the matrix is rotated 90°, and hence its "rows" are really columns, and each finger only hits a single "row" at a time in normal use.
|
||||||
* eager_pk - debouncing per key. On any state change, response is immediate, followed by ```DEBOUNCE``` milliseconds of no further input for that key
|
* eager_pk - debouncing per key. On any state change, response is immediate, followed by ```DEBOUNCE``` milliseconds of no further input for that key
|
||||||
* sym_g - debouncing per keyboard. On any state change, a global timer is set. When ```DEBOUNCE``` milliseconds of no changes has occured, all input changes are pushed.
|
* sym_g - debouncing per keyboard. On any state change, a global timer is set. When ```DEBOUNCE``` milliseconds of no changes has occured, all input changes are pushed.
|
||||||
|
* sym_pk - debouncing per key. On any state change, a per-key timer is set. When ```DEBOUNCE``` milliseconds of no changes have occured on that key, the key status change is pushed.
|
||||||
|
|
||||||
|
|
||||||
@@ -7,9 +7,17 @@ DIP switches are supported by adding this to your `rules.mk`:
|
|||||||
and this to your `config.h`:
|
and this to your `config.h`:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
|
// Connects each switch in the dip switch to the GPIO pin of the MCU
|
||||||
#define DIP_SWITCH_PINS { B14, A15, A10, B9 }
|
#define DIP_SWITCH_PINS { B14, A15, A10, B9 }
|
||||||
```
|
```
|
||||||
|
|
||||||
|
or
|
||||||
|
|
||||||
|
```c
|
||||||
|
// Connect each switch in the DIP switch to an unused intersections in the key matrix.
|
||||||
|
#define DIP_SWITCH_MATRIX_GRID { {0,6}, {1,6}, {2,6} } // List of row and col pairs
|
||||||
|
```
|
||||||
|
|
||||||
## Callbacks
|
## Callbacks
|
||||||
|
|
||||||
The callback functions can be inserted into your `<keyboard>.c`:
|
The callback functions can be inserted into your `<keyboard>.c`:
|
||||||
@@ -87,4 +95,10 @@ void dip_switch_update_mask_user(uint32_t state) {
|
|||||||
|
|
||||||
## Hardware
|
## Hardware
|
||||||
|
|
||||||
|
### Connects each switch in the dip switch to the GPIO pin of the MCU
|
||||||
|
|
||||||
One side of the DIP switch should be wired directly to the pin on the MCU, and the other side to ground. It should not matter which side is connected to which, as it should be functionally the same.
|
One side of the DIP switch should be wired directly to the pin on the MCU, and the other side to ground. It should not matter which side is connected to which, as it should be functionally the same.
|
||||||
|
|
||||||
|
### Connect each switch in the DIP switch to an unused intersections in the key matrix.
|
||||||
|
|
||||||
|
As with the keyswitch, a diode and DIP switch connect the ROW line to the COL line.
|
||||||
@@ -18,7 +18,7 @@ That should be everything necessary.
|
|||||||
|
|
||||||
To start recording the macro, press either `DYN_REC_START1` or `DYN_REC_START2`.
|
To start recording the macro, press either `DYN_REC_START1` or `DYN_REC_START2`.
|
||||||
|
|
||||||
To finish the recording, press the `DYN_REC_STOP` layer button.
|
To finish the recording, press the `DYN_REC_STOP` layer button. You can also press `DYN_REC_START1` or `DYN_REC_START2` again to stop the recording.
|
||||||
|
|
||||||
To replay the macro, press either `DYN_MACRO_PLAY1` or `DYN_MACRO_PLAY2`.
|
To replay the macro, press either `DYN_MACRO_PLAY1` or `DYN_MACRO_PLAY2`.
|
||||||
|
|
||||||
|
|||||||
@@ -26,7 +26,7 @@ If your encoder's clockwise directions are incorrect, you can swap the A & B pad
|
|||||||
#define ENCODER_DIRECTION_FLIP
|
#define ENCODER_DIRECTION_FLIP
|
||||||
```
|
```
|
||||||
|
|
||||||
Additionally, the resolution can be specified in the same file (the default & suggested is 4):
|
Additionally, the resolution, which defines how many pulses the encoder registers between each detent, can be defined with:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
#define ENCODER_RESOLUTION 4
|
#define ENCODER_RESOLUTION 4
|
||||||
@@ -61,7 +61,7 @@ void encoder_update_user(uint8_t index, bool clockwise) {
|
|||||||
} else {
|
} else {
|
||||||
tap_code(KC_PGUP);
|
tap_code(KC_PGUP);
|
||||||
}
|
}
|
||||||
} else if (index == 1) { /* Second encoder */
|
} else if (index == 1) { /* Second encoder */
|
||||||
if (clockwise) {
|
if (clockwise) {
|
||||||
tap_code(KC_DOWN);
|
tap_code(KC_DOWN);
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
# HD44780 LCD Displays
|
# HD44780 LCD Displays
|
||||||
|
|
||||||
This is an integration of Peter Fleury's LCD library. This page will explain the basics. [For in depth documentation visit his page.](http://homepage.hispeed.ch/peterfleury/doxygen/avr-gcc-libraries/group__pfleury__lcd.html)
|
This is an integration of Peter Fleury's LCD library. This page will explain the basics. [For in depth documentation visit his page.](http://www.peterfleury.epizy.com/doxygen/avr-gcc-libraries/group__pfleury__lcd.html)
|
||||||
|
|
||||||
You can enable support for HD44780 Displays by setting the `HD44780_ENABLE` flag in your keyboards `rules.mk` to yes.
|
You can enable support for HD44780 Displays by setting the `HD44780_ENABLE` flag in your keyboards `rules.mk` to yes.
|
||||||
|
|
||||||
@@ -50,8 +50,8 @@ LCD_DISP_ON_CURSOR_BLINK : display on, cursor on flashing
|
|||||||
````
|
````
|
||||||
This is best done in your keyboards `matrix_init_kb` or your keymaps `matrix_init_user`.
|
This is best done in your keyboards `matrix_init_kb` or your keymaps `matrix_init_user`.
|
||||||
It is advised to clear the display before use.
|
It is advised to clear the display before use.
|
||||||
To do so call `lcd_clrsrc()`.
|
To do so call `lcd_clrscr()`.
|
||||||
|
|
||||||
To now print something to your Display you first call `lcd_gotoxy(column, line)`. To go to the start of the first line you would call `lcd_gotoxy(0, 0)` and then print a string with `lcd_puts("example string")`.
|
To now print something to your Display you first call `lcd_gotoxy(column, line)`. To go to the start of the first line you would call `lcd_gotoxy(0, 0)` and then print a string with `lcd_puts("example string")`.
|
||||||
|
|
||||||
There are more methods available to control the display. [For in depth documentation please visit the linked page.](http://homepage.hispeed.ch/peterfleury/doxygen/avr-gcc-libraries/group__pfleury__lcd.html)
|
There are more methods available to control the display. [For in depth documentation please visit the linked page.](http://www.peterfleury.epizy.com/doxygen/avr-gcc-libraries/group__pfleury__lcd.html)
|
||||||
@@ -0,0 +1,94 @@
|
|||||||
|
# Layers :id=layers
|
||||||
|
|
||||||
|
One of the most powerful and well used features of QMK Firmware is the ability to use layers. For most people, this amounts to a function key that allows for different keys, much like what you would see on a laptop or tablet keyboard.
|
||||||
|
|
||||||
|
For a detailed explanation of how the layer stack works, checkout [Keymap Overview](keymap.md#keymap-and-layers).
|
||||||
|
|
||||||
|
## Switching and Toggling Layers :id=switching-and-toggling-layers
|
||||||
|
|
||||||
|
These functions allow you to activate layers in various ways. Note that layers are not generally independent layouts -- multiple layers can be activated at once, and it's typical for layers to use `KC_TRNS` to allow keypresses to pass through to lower layers. When using momentary layer switching with MO(), LM(), TT(), or LT(), make sure to leave the key on the above layers transparent or it may not work as intended.
|
||||||
|
|
||||||
|
* `DF(layer)` - switches the default layer. The default layer is the always-active base layer that other layers stack on top of. See below for more about the default layer. This might be used to switch from QWERTY to Dvorak layout. (Note that this is a temporary switch that only persists until the keyboard loses power. To modify the default layer in a persistent way requires deeper customization, such as calling the `set_single_persistent_default_layer` function inside of [process_record_user](custom_quantum_functions.md#programming-the-behavior-of-any-keycode).)
|
||||||
|
* `MO(layer)` - momentarily activates *layer*. As soon as you let go of the key, the layer is deactivated.
|
||||||
|
* `LM(layer, mod)` - Momentarily activates *layer* (like `MO`), but with modifier(s) *mod* active. Only supports layers 0-15 and the left modifiers: `MOD_LCTL`, `MOD_LSFT`, `MOD_LALT`, `MOD_LGUI` (note the use of `MOD_` constants instead of `KC_`). These modifiers can be combined using bitwise OR, e.g. `LM(_RAISE, MOD_LCTL | MOD_LALT)`.
|
||||||
|
* `LT(layer, kc)` - momentarily activates *layer* when held, and sends *kc* when tapped. Only supports layers 0-15.
|
||||||
|
* `OSL(layer)` - momentarily activates *layer* until the next key is pressed. See [One Shot Keys](one_shot_keys.md) for details and additional functionality.
|
||||||
|
* `TG(layer)` - toggles *layer*, activating it if it's inactive and vice versa
|
||||||
|
* `TO(layer)` - activates *layer* and de-activates all other layers (except your default layer). This function is special, because instead of just adding/removing one layer to your active layer stack, it will completely replace your current active layers, uniquely allowing you to replace higher layers with a lower one. This is activated on keydown (as soon as the key is pressed).
|
||||||
|
* `TT(layer)` - Layer Tap-Toggle. If you hold the key down, *layer* is activated, and then is de-activated when you let go (like `MO`). If you repeatedly tap it, the layer will be toggled on or off (like `TG`). It needs 5 taps by default, but you can change this by defining `TAPPING_TOGGLE` -- for example, `#define TAPPING_TOGGLE 2` to toggle on just two taps.
|
||||||
|
|
||||||
|
### Caveats :id=caveats
|
||||||
|
|
||||||
|
Currently, `LT()` and `MT()` are limited to the [Basic Keycode set](keycodes_basic.md), meaning you can't use keycodes like `LCTL()`, `KC_TILD`, or anything greater than `0xFF`. Specifically, dual function keys like `LT` and `MT` use a 16 bit keycode. 4 bits are used for the function identifier, the next 12 are divided into the parameters. Layer Tap uses 4 bits for the layer (and is why it's limited to layers 0-15, actually), while Mod Tap does the same, 4 bits for the identifier, 4 bits for which mods are used, and all of them use 8 bits for the keycode. Because of this, the keycode used is limited to `0xFF` (0-255), which are the basic keycodes only.
|
||||||
|
|
||||||
|
Expanding this would be complicated, at best. Moving to a 32-bit keycode would solve a lot of this, but would double the amount of space that the keymap matrix uses. And it could potentially cause issues, too. If you need to apply modifiers to your tapped keycode, [Tap Dance](feature_tap_dance.md#example-5-using-tap-dance-for-advanced-mod-tap-and-layer-tap-keys) can be used to accomplish this.
|
||||||
|
|
||||||
|
Additionally, if at least one right-handed modifier is specified in a Mod Tap or Layer Tap, it will cause all modifiers specified to become right-handed, so it is not possible to mix and match the two.
|
||||||
|
|
||||||
|
## Working with Layers :id=working-with-layers
|
||||||
|
|
||||||
|
Care must be taken when switching layers, it's possible to lock yourself into a layer with no way to deactivate that layer (without unplugging your keyboard.) We've created some guidelines to help users avoid the most common problems.
|
||||||
|
|
||||||
|
### Beginners :id=beginners
|
||||||
|
|
||||||
|
If you are just getting started with QMK you will want to keep everything simple. Follow these guidelines when setting up your layers:
|
||||||
|
|
||||||
|
* Setup layer 0 as your default, "base" layer. This is your normal typing layer, and could be whatever layout you want (qwerty, dvorak, colemak, etc.). It's important to set this as the lowest layer since it will typically have most or all of the keyboard's keys defined, so would block other layers from having any effect if it were above them (i.e., had a higher layer number).
|
||||||
|
* Arrange your layers in a "tree" layout, with layer 0 as the root. Do not try to enter the same layer from more than one other layer.
|
||||||
|
* In a layer's keymap, only reference higher-numbered layers. Because layers are processed from the highest-numbered (topmost) active layer down, modifying the state of lower layers can be tricky and error-prone.
|
||||||
|
|
||||||
|
### Intermediate Users :id=intermediate-users
|
||||||
|
|
||||||
|
Sometimes you need more than one base layer. For example, if you want to switch between QWERTY and Dvorak, switch between layouts for different countries, or switch your layout for different videogames. Your base layers should always be the lowest numbered layers. When you have multiple base layers you should always treat them as mutually exclusive. When one base layer is on the others are off.
|
||||||
|
|
||||||
|
### Advanced Users :id=advanced-users
|
||||||
|
|
||||||
|
Once you have a good feel for how layers work and what you can do, you can get more creative. The rules listed in the beginner section will help you be successful by avoiding some of the tricker details but they can be constraining, especially for ultra-compact keyboard users. Understanding how layers work will allow you to use them in more advanced ways.
|
||||||
|
|
||||||
|
Layers stack on top of each other in numerical order. When determining what a keypress does, QMK scans the layers from the top down, stopping when it reaches the first active layer that is not set to `KC_TRNS`. As a result if you activate a layer that is numerically lower than your current layer, and your current layer (or another layer that is active and higher than your target layer) has something other than `KC_TRNS`, that is the key that will be sent, not the key on the layer you just activated. This is the cause of most people's "why doesn't my layer get switched" problem.
|
||||||
|
|
||||||
|
Sometimes, you might want to switch between layers in a macro or as part of a tap dance routine. `layer_on` activates a layer, and `layer_off` deactivates it. More layer-related functions can be found in [action_layer.h](https://github.com/qmk/qmk_firmware/blob/master/tmk_core/common/action_layer.h).
|
||||||
|
|
||||||
|
## Functions :id=functions
|
||||||
|
|
||||||
|
There are a number of functions (and variables) related to how you can use or manipulate the layers.
|
||||||
|
|
||||||
|
|Function |Description |
|
||||||
|
|----------------------------------------------|---------------------------------------------------------------------------------------------------------|
|
||||||
|
| `layer_state_set(layer_mask)` | Directly sets the layer state (recommended, do not use unless you know what you are doing). |
|
||||||
|
| `layer_clear()` | Clears all layers (turns them all off). |
|
||||||
|
| `layer_move(layer)` | Turns specified layer on, and all other layers off. |
|
||||||
|
| `layer_on(layer)` | Turns specified layer on, leaves all other layers in existing state. |
|
||||||
|
| `layer_off(layer)` | Turns specified layer off, leaves all other layers in existing state. |
|
||||||
|
| `layer_invert(layer)` | Interverts/toggles the state of the specified layer |
|
||||||
|
| `layer_or(layer_mask)` | Turns on layers based on matching bits between specifed layer and existing layer state. |
|
||||||
|
| `layer_and(layer_mask)` | Turns on layers based on matching enabled bits between specifed layer and existing layer state. |
|
||||||
|
| `layer_xor(layer_mask)` | Turns on layers based on non-matching bits between specifed layer and existing layer state. |
|
||||||
|
| `layer_debug(layer_mask)` | Prints out the current bit mask and highest active layer to debugger console. |
|
||||||
|
| `default_layer_set(layer_mask)` | Directly sets the default layer state (recommended, do not use unless you know what you are doing). |
|
||||||
|
| `default_layer_or(layer_mask)` | Turns on layers based on matching bits between specifed layer and existing default layer state. |
|
||||||
|
| `default_layer_and(layer_mask)` | Turns on layers based on matching enabled bits between specifed layer and existing default layer state. |
|
||||||
|
| `default_layer_xor(layer_mask)` | Turns on layers based on non-matching bits between specifed layer and existing default layer state. |
|
||||||
|
| `default_layer_debug(layer_mask)` | Prints out the current bit mask and highest active default layer to debugger console. |
|
||||||
|
| [`set_single_persistent_default_layer(layer)`](ref_functions.md#setting-the-persistent-default-layer) | Sets the default layer and writes it to persistent memory (EEPROM). |
|
||||||
|
| [`update_tri_layer(x, y, z)`](ref_functions.md#update_tri_layerx-y-z) | Checks if layers `x` and `y` are both on, and sets `z` based on that (on if both on, otherwise off). |
|
||||||
|
| [`update_tri_layer_state(state, x, y, z)`](ref_functions.md#update_tri_layer_statestate-x-y-z) | Does the same as `update_tri_layer(x, y, z)`, but from `layer_state_set_*` functions. |
|
||||||
|
|
||||||
|
|
||||||
|
In additional to the functions that you can call, there are a number of callback functions that get called every time the layer changes. This passed the layer state to the function, which can be read or modified.
|
||||||
|
|
||||||
|
|Callbacks |Description |
|
||||||
|
|-----------------------------------------------------|----------------------------------------------------------------------------------------|
|
||||||
|
| `layer_state_set_kb(layer_state_t state)` | Callback for layer functions, for keyboard. |
|
||||||
|
| `layer_state_set_user(layer_state_t state)` | Callback for layer functions, for users. |
|
||||||
|
| `default_layer_state_set_kb(layer_state_t state)` | Callback for default layer functions, for keyboard. Called on keyboard initialization. |
|
||||||
|
| `default_layer_state_set_user(layer_state_t state)` | Callback for default layer functions, for users. Called on keyboard initialization. |
|
||||||
|
|
||||||
|
?> For additional details on how you can use these callbacks, check out the [Layer Change Code](custom_quantum_functions.md#layer-change-code) document.
|
||||||
|
|
||||||
|
|Check functions |Description |
|
||||||
|
|-------------------------------------------|------------------------------------------------------------------------------|
|
||||||
|
| `layer_state_cmp(cmp_layer_state, layer)` | This checks the `cmp_layer_state` to see if the specific `layer` is enabled. This is meant for use with the layer callbacks. |
|
||||||
|
| `layer_state_is(layer)` | This checks the layer state to see if the specific `layer` is enabled. (calls `layer_state_cmp` for the global layer state). |
|
||||||
|
|
||||||
|
!> There is `IS_LAYER_ON(layer)` as well, however the `layer_state_cmp` function has some additional handling to ensure that on layer 0 that it returns the correct value. Otherwise, if you check to see if layer 0 is on, you may get an incorrect value returned.
|
||||||
@@ -5,7 +5,7 @@ If you've ever used Vim, you know what a Leader key is. If not, you're about to
|
|||||||
That's what `KC_LEAD` does. Here's an example:
|
That's what `KC_LEAD` does. Here's an example:
|
||||||
|
|
||||||
1. Pick a key on your keyboard you want to use as the Leader key. Assign it the keycode `KC_LEAD`. This key would be dedicated just for this -- it's a single action key, can't be used for anything else.
|
1. Pick a key on your keyboard you want to use as the Leader key. Assign it the keycode `KC_LEAD`. This key would be dedicated just for this -- it's a single action key, can't be used for anything else.
|
||||||
2. Include the line `#define LEADER_TIMEOUT 300` in your `config.h`. This sets the timeout for the `KC_LEAD` key. Specifically, when you press the `KC_LEAD` key, you only have a certain amount of time to complete the Leader Key sequence. The `300` here sets that to 300ms, and you can increase this value to give you more time to hit the sequence. But any keys pressed during this timeout are intercepted and not sent, so you may want to keep this value low. .
|
2. Include the line `#define LEADER_TIMEOUT 300` in your `config.h`. This sets the timeout for the `KC_LEAD` key. Specifically, when you press the `KC_LEAD` key, you only have a certain amount of time to complete the Leader Key sequence. The `300` here sets that to 300ms, and you can increase this value to give you more time to hit the sequence. But any keys pressed during this timeout are intercepted and not sent, so you may want to keep this value low.
|
||||||
* By default, this timeout is how long after pressing `KC_LEAD` to complete your entire sequence. This may be very low for some people. So you may want to increase this timeout. Optionally, you may want to enable the `LEADER_PER_KEY_TIMING` option, which resets the timeout after each key is tapped. This allows you to maintain a low value here, but still be able to use the longer sequences. To enable this option, add `#define LEADER_PER_KEY_TIMING` to your `config.h`.
|
* By default, this timeout is how long after pressing `KC_LEAD` to complete your entire sequence. This may be very low for some people. So you may want to increase this timeout. Optionally, you may want to enable the `LEADER_PER_KEY_TIMING` option, which resets the timeout after each key is tapped. This allows you to maintain a low value here, but still be able to use the longer sequences. To enable this option, add `#define LEADER_PER_KEY_TIMING` to your `config.h`.
|
||||||
3. Within your `matrix_scan_user` function, add something like this:
|
3. Within your `matrix_scan_user` function, add something like this:
|
||||||
|
|
||||||
@@ -74,9 +74,9 @@ SEQ_THREE_KEYS(KC_C, KC_C, KC_C) {
|
|||||||
|
|
||||||
## Strict Key Processing
|
## Strict Key Processing
|
||||||
|
|
||||||
By default, the Leader Key feature will filter the keycode out of [`Mod-Tap`](mod_tap.md) and [`Layer Tap`](feature_advanced_keycodes.md#switching-and-toggling-layers) functions when checking for the Leader sequences. That means if you're using `LT(3, KC_A)`, it will pick this up as `KC_A` for the sequence, rather than `LT(3, KC_A)`, giving a more expected behavior for newer users.
|
By default, the Leader Key feature will filter the keycode out of [`Mod-Tap`](mod_tap.md) and [`Layer Tap`](feature_layers.md#switching-and-toggling-layers) functions when checking for the Leader sequences. That means if you're using `LT(3, KC_A)`, it will pick this up as `KC_A` for the sequence, rather than `LT(3, KC_A)`, giving a more expected behavior for newer users.
|
||||||
|
|
||||||
While, this may be fine for most, if you want to specify the whole keycode (eg, `LT(3, KC_A)` from the example above) in the sequence, you can enable this by added `#define LEADER_KEY_STRICT_KEY_PROCESSING` to your `config.h` file. This well then disable the filtering, and you'll need to specify the whole keycode.
|
While, this may be fine for most, if you want to specify the whole keycode (eg, `LT(3, KC_A)` from the example above) in the sequence, you can enable this by added `#define LEADER_KEY_STRICT_KEY_PROCESSING` to your `config.h` file. This will then disable the filtering, and you'll need to specify the whole keycode.
|
||||||
|
|
||||||
## Customization
|
## Customization
|
||||||
|
|
||||||
|
|||||||
+85
-42
@@ -6,34 +6,34 @@ Macros allow you to send multiple keystrokes when pressing just one key. QMK has
|
|||||||
|
|
||||||
## The New Way: `SEND_STRING()` & `process_record_user`
|
## The New Way: `SEND_STRING()` & `process_record_user`
|
||||||
|
|
||||||
Sometimes you just want a key to type out words or phrases. For the most common situations we've provided `SEND_STRING()`, which will type out your string (i.e. a sequence of characters) for you. All ASCII characters that are easily translated to a keycode are supported (e.g. `\n\t`).
|
Sometimes you want a key to type out words or phrases. For the most common situations, we've provided `SEND_STRING()`, which will type out a string (i.e. a sequence of characters) for you. All ASCII characters that are easily translatable to a keycode are supported (e.g. `qmk 123\n\t`).
|
||||||
|
|
||||||
Here is an example `keymap.c` for a two-key keyboard:
|
Here is an example `keymap.c` for a two-key keyboard:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
enum custom_keycodes {
|
enum custom_keycodes {
|
||||||
QMKBEST = SAFE_RANGE,
|
QMKBEST = SAFE_RANGE,
|
||||||
};
|
};
|
||||||
|
|
||||||
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
|
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
|
||||||
switch (keycode) {
|
switch (keycode) {
|
||||||
case QMKBEST:
|
case QMKBEST:
|
||||||
if (record->event.pressed) {
|
if (record->event.pressed) {
|
||||||
// when keycode QMKBEST is pressed
|
// when keycode QMKBEST is pressed
|
||||||
SEND_STRING("QMK is the best thing ever!");
|
SEND_STRING("QMK is the best thing ever!");
|
||||||
} else {
|
} else {
|
||||||
// when keycode QMKBEST is released
|
// when keycode QMKBEST is released
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
return true;
|
||||||
return true;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
|
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
|
||||||
[0] = {
|
[0] = {
|
||||||
{QMKBEST, KC_ESC}
|
{QMKBEST, KC_ESC},
|
||||||
}
|
// ...
|
||||||
|
},
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -49,45 +49,88 @@ You can do that by adding another keycode and adding another case to the switch
|
|||||||
|
|
||||||
```c
|
```c
|
||||||
enum custom_keycodes {
|
enum custom_keycodes {
|
||||||
QMKBEST = SAFE_RANGE,
|
QMKBEST = SAFE_RANGE,
|
||||||
QMKURL,
|
QMKURL,
|
||||||
MY_OTHER_MACRO
|
MY_OTHER_MACRO,
|
||||||
};
|
};
|
||||||
|
|
||||||
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
|
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
|
||||||
switch (keycode) {
|
switch (keycode) {
|
||||||
case QMKBEST:
|
case QMKBEST:
|
||||||
if (record->event.pressed) {
|
if (record->event.pressed) {
|
||||||
// when keycode QMKBEST is pressed
|
// when keycode QMKBEST is pressed
|
||||||
SEND_STRING("QMK is the best thing ever!");
|
SEND_STRING("QMK is the best thing ever!");
|
||||||
} else {
|
} else {
|
||||||
// when keycode QMKBEST is released
|
// when keycode QMKBEST is released
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case QMKURL:
|
case QMKURL:
|
||||||
if (record->event.pressed) {
|
if (record->event.pressed) {
|
||||||
// when keycode QMKURL is pressed
|
// when keycode QMKURL is pressed
|
||||||
SEND_STRING("https://qmk.fm/\n");
|
SEND_STRING("https://qmk.fm/\n");
|
||||||
} else {
|
} else {
|
||||||
// when keycode QMKURL is released
|
// when keycode QMKURL is released
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MY_OTHER_MACRO:
|
case MY_OTHER_MACRO:
|
||||||
|
if (record->event.pressed) {
|
||||||
|
SEND_STRING(SS_LCTL("ac")); // selects all and copies
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
};
|
||||||
|
|
||||||
|
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
|
||||||
|
[0] = {
|
||||||
|
{MY_CUSTOM_MACRO, MY_OTHER_MACRO},
|
||||||
|
// ...
|
||||||
|
},
|
||||||
|
};
|
||||||
|
```
|
||||||
|
|
||||||
|
### Advanced Macros
|
||||||
|
|
||||||
|
In addition to the `process_record_user()` function, is the `post_process_record_user()` function. This runs after `process_record` and can be used to do things after a keystroke has been sent. This is useful if you want to have a key pressed before and released after a normal key, for instance.
|
||||||
|
|
||||||
|
In this example, we modify most normal keypresses so that `F22` is pressed before the keystroke is normally sent, and release it __only after__ it's been released.
|
||||||
|
|
||||||
|
```c
|
||||||
|
static uint8_t f22_tracker;
|
||||||
|
|
||||||
|
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
|
||||||
|
switch (keycode) {
|
||||||
|
case KC_A ... KC_F21: //notice how it skips over F22
|
||||||
|
case KC_F23 ... KC_EXSEL: //exsel is the last one before the modifier keys
|
||||||
if (record->event.pressed) {
|
if (record->event.pressed) {
|
||||||
SEND_STRING(SS_LCTL("ac")); // selects all and copies
|
register_code(KC_F22); //this means to send F22 down
|
||||||
|
f22_tracker++;
|
||||||
|
register_code(keycode);
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
};
|
}
|
||||||
|
|
||||||
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
|
void post_process_record_user(uint16_t keycode, keyrecord_t *record) {
|
||||||
[0] = {
|
switch (keycode) {
|
||||||
{MY_CUSTOM_MACRO, MY_OTHER_MACRO}
|
case KC_A ... KC_F21: //notice how it skips over F22
|
||||||
|
case KC_F23 ... KC_EXSEL: //exsel is the last one before the modifier keys
|
||||||
|
if (!record->event.pressed) {
|
||||||
|
f22_tracker--;
|
||||||
|
if (!f22_tracker) {
|
||||||
|
unregister_code(KC_F22); //this means to send F22 up
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
};
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
### TAP, DOWN and UP
|
### TAP, DOWN and UP
|
||||||
|
|
||||||
You may want to use keys in your macros that you can't write down, such as `Ctrl` or `Home`.
|
You may want to use keys in your macros that you can't write down, such as `Ctrl` or `Home`.
|
||||||
@@ -121,11 +164,11 @@ There's also a couple of mod shortcuts you can use:
|
|||||||
|
|
||||||
* `SS_LCTL(string)`
|
* `SS_LCTL(string)`
|
||||||
* `SS_LSFT(string)`
|
* `SS_LSFT(string)`
|
||||||
* `SS_LALT(string)`
|
* `SS_LALT(string)` or `SS_LOPT(string)`
|
||||||
* `SS_LGUI(string)`, `SS_LCMD(string)` or `SS_LWIN(string)`
|
* `SS_LGUI(string)`, `SS_LCMD(string)` or `SS_LWIN(string)`
|
||||||
* `SS_RCTL(string)`
|
* `SS_RCTL(string)`
|
||||||
* `SS_RSFT(string)`
|
* `SS_RSFT(string)`
|
||||||
* `SS_RALT(string)` or `SS_ALGR(string)`
|
* `SS_RALT(string)`, `SS_ROPT(string)` or `SS_ALGR(string)`
|
||||||
* `SS_RGUI(string)`, `SS_RCMD(string)` or `SS_RWIN(string)`
|
* `SS_RGUI(string)`, `SS_RCMD(string)` or `SS_RWIN(string)`
|
||||||
|
|
||||||
These press the respective modifier, send the supplied string and then release the modifier.
|
These press the respective modifier, send the supplied string and then release the modifier.
|
||||||
|
|||||||
@@ -58,6 +58,8 @@ This is the default mode. You can adjust the cursor and scrolling acceleration u
|
|||||||
|`MOUSEKEY_INTERVAL` |50 |Time between cursor movements |
|
|`MOUSEKEY_INTERVAL` |50 |Time between cursor movements |
|
||||||
|`MOUSEKEY_MAX_SPEED` |10 |Maximum cursor speed at which acceleration stops |
|
|`MOUSEKEY_MAX_SPEED` |10 |Maximum cursor speed at which acceleration stops |
|
||||||
|`MOUSEKEY_TIME_TO_MAX` |20 |Time until maximum cursor speed is reached |
|
|`MOUSEKEY_TIME_TO_MAX` |20 |Time until maximum cursor speed is reached |
|
||||||
|
|`MOUSEKEY_WHEEL_DELAY` |300 |Delay between pressing a wheel key and wheel movement |
|
||||||
|
|`MOUSEKEY_WHEEL_INTERVAL` |100 |Time between wheel movements |
|
||||||
|`MOUSEKEY_WHEEL_MAX_SPEED` |8 |Maximum number of scroll steps per scroll action |
|
|`MOUSEKEY_WHEEL_MAX_SPEED` |8 |Maximum number of scroll steps per scroll action |
|
||||||
|`MOUSEKEY_WHEEL_TIME_TO_MAX`|40 |Time until maximum scroll speed is reached |
|
|`MOUSEKEY_WHEEL_TIME_TO_MAX`|40 |Time until maximum scroll speed is reached |
|
||||||
|
|
||||||
@@ -66,6 +68,7 @@ Tips:
|
|||||||
* Setting `MOUSEKEY_DELAY` too low makes the cursor unresponsive. Setting it too high makes small movements difficult.
|
* Setting `MOUSEKEY_DELAY` too low makes the cursor unresponsive. Setting it too high makes small movements difficult.
|
||||||
* For smoother cursor movements, lower the value of `MOUSEKEY_INTERVAL`. If the refresh rate of your display is 60Hz, you could set it to `16` (1/60). As this raises the cursor speed significantly, you may want to lower `MOUSEKEY_MAX_SPEED`.
|
* For smoother cursor movements, lower the value of `MOUSEKEY_INTERVAL`. If the refresh rate of your display is 60Hz, you could set it to `16` (1/60). As this raises the cursor speed significantly, you may want to lower `MOUSEKEY_MAX_SPEED`.
|
||||||
* Setting `MOUSEKEY_TIME_TO_MAX` or `MOUSEKEY_WHEEL_TIME_TO_MAX` to `0` will disable acceleration for the cursor or scrolling respectively. This way you can make one of them constant while keeping the other accelerated, which is not possible in constant speed mode.
|
* Setting `MOUSEKEY_TIME_TO_MAX` or `MOUSEKEY_WHEEL_TIME_TO_MAX` to `0` will disable acceleration for the cursor or scrolling respectively. This way you can make one of them constant while keeping the other accelerated, which is not possible in constant speed mode.
|
||||||
|
* Setting `MOUSEKEY_WHEEL_INTERVAL` too low will make scrolling too fast. Setting it too high will make scrolling too slow when the wheel key is held down.
|
||||||
|
|
||||||
Cursor acceleration uses the same algorithm as the X Window System MouseKeysAccel feature. You can read more about it [on Wikipedia](https://en.wikipedia.org/wiki/Mouse_keys).
|
Cursor acceleration uses the same algorithm as the X Window System MouseKeysAccel feature. You can read more about it [on Wikipedia](https://en.wikipedia.org/wiki/Mouse_keys).
|
||||||
|
|
||||||
|
|||||||
@@ -261,12 +261,24 @@ void oled_task(void);
|
|||||||
// Called at the start of oled_task, weak function overridable by the user
|
// Called at the start of oled_task, weak function overridable by the user
|
||||||
void oled_task_user(void);
|
void oled_task_user(void);
|
||||||
|
|
||||||
// Scrolls the entire display right
|
// Set the specific 8 lines rows of the screen to scroll.
|
||||||
|
// 0 is the default for start, and 7 for end, which is the entire
|
||||||
|
// height of the screen. For 128x32 screens, rows 4-7 are not used.
|
||||||
|
void oled_scroll_set_area(uint8_t start_line, uint8_t end_line);
|
||||||
|
|
||||||
|
// Sets scroll speed, 0-7, fastest to slowest. Default is three.
|
||||||
|
// Does not take effect until scrolling is either started or restarted
|
||||||
|
// the ssd1306 supports 8 speeds with the delay
|
||||||
|
// listed below betwen each frame of the scrolling effect
|
||||||
|
// 0=2, 1=3, 2=4, 3=5, 4=25, 5=64, 6=128, 7=256
|
||||||
|
void oled_scroll_set_speed(uint8_t speed);
|
||||||
|
|
||||||
|
// Begin scrolling the entire display right
|
||||||
// Returns true if the screen was scrolling or starts scrolling
|
// Returns true if the screen was scrolling or starts scrolling
|
||||||
// NOTE: display contents cannot be changed while scrolling
|
// NOTE: display contents cannot be changed while scrolling
|
||||||
bool oled_scroll_right(void);
|
bool oled_scroll_right(void);
|
||||||
|
|
||||||
// Scrolls the entire display left
|
// Begin scrolling the entire display left
|
||||||
// Returns true if the screen was scrolling or starts scrolling
|
// Returns true if the screen was scrolling or starts scrolling
|
||||||
// NOTE: display contents cannot be changed while scrolling
|
// NOTE: display contents cannot be changed while scrolling
|
||||||
bool oled_scroll_left(void);
|
bool oled_scroll_left(void);
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
## Pointing Device
|
# Pointing Device :id=pointing-device
|
||||||
|
|
||||||
Pointing Device is a generic name for a feature intended to be generic: moving the system pointer around. There are certainly other options for it - like mousekeys - but this aims to be easily modifiable and lightweight. You can implement custom keys to control functionality, or you can gather information from other peripherals and insert it directly here - let QMK handle the processing for you.
|
Pointing Device is a generic name for a feature intended to be generic: moving the system pointer around. There are certainly other options for it - like mousekeys - but this aims to be easily modifiable and lightweight. You can implement custom keys to control functionality, or you can gather information from other peripherals and insert it directly here - let QMK handle the processing for you.
|
||||||
|
|
||||||
To enable Pointing Device, uncomment the following line in your rules.mk:
|
To enable Pointing Device, uncomment the following line in your rules.mk:
|
||||||
|
|
||||||
```
|
```makefile
|
||||||
POINTING_DEVICE_ENABLE = yes
|
POINTING_DEVICE_ENABLE = yes
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -21,26 +21,28 @@ Keep in mind that a report_mouse_t (here "mouseReport") has the following proper
|
|||||||
* `mouseReport.h` - this is a signed int from -127 to 127 (not 128, this is defined in USB HID spec) representing horizontal scrolling (+ right, - left).
|
* `mouseReport.h` - this is a signed int from -127 to 127 (not 128, this is defined in USB HID spec) representing horizontal scrolling (+ right, - left).
|
||||||
* `mouseReport.buttons` - this is a uint8_t in which the last 5 bits are used. These bits represent the mouse button state - bit 3 is mouse button 5, and bit 7 is mouse button 1.
|
* `mouseReport.buttons` - this is a uint8_t in which the last 5 bits are used. These bits represent the mouse button state - bit 3 is mouse button 5, and bit 7 is mouse button 1.
|
||||||
|
|
||||||
When the mouse report is sent, the x, y, v, and h values are set to 0 (this is done in "pointing_device_send()", which can be overridden to avoid this behavior). This way, button states persist, but movement will only occur once. For further customization, both `pointing_device_init` and `pointing_device_task` can be overridden.
|
Once you have made the necessary changes to the mouse report, you need to send it:
|
||||||
|
|
||||||
|
* `pointing_device_send()` - Sends the mouse report to the host and zeroes out the report.
|
||||||
|
|
||||||
|
When the mouse report is sent, the x, y, v, and h values are set to 0 (this is done in `pointing_device_send()`, which can be overridden to avoid this behavior). This way, button states persist, but movement will only occur once. For further customization, both `pointing_device_init` and `pointing_device_task` can be overridden.
|
||||||
|
|
||||||
In the following example, a custom key is used to click the mouse and scroll 127 units vertically and horizontally, then undo all of that when released - because that's a totally useful function. Listen, this is an example:
|
In the following example, a custom key is used to click the mouse and scroll 127 units vertically and horizontally, then undo all of that when released - because that's a totally useful function. Listen, this is an example:
|
||||||
|
|
||||||
```
|
```c
|
||||||
case MS_SPECIAL:
|
case MS_SPECIAL:
|
||||||
report_mouse_t currentReport = pointing_device_get_report();
|
report_mouse_t currentReport = pointing_device_get_report();
|
||||||
if (record->event.pressed)
|
if (record->event.pressed) {
|
||||||
{
|
|
||||||
currentReport.v = 127;
|
currentReport.v = 127;
|
||||||
currentReport.h = 127;
|
currentReport.h = 127;
|
||||||
currentReport.buttons |= MOUSE_BTN1; //this is defined in report.h
|
currentReport.buttons |= MOUSE_BTN1; // this is defined in report.h
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
currentReport.v = -127;
|
currentReport.v = -127;
|
||||||
currentReport.h = -127;
|
currentReport.h = -127;
|
||||||
currentReport.buttons &= ~MOUSE_BTN1;
|
currentReport.buttons &= ~MOUSE_BTN1;
|
||||||
}
|
}
|
||||||
pointing_device_set_report(currentReport);
|
pointing_device_set_report(currentReport);
|
||||||
|
pointing_device_send();
|
||||||
break;
|
break;
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|||||||
+59
-29
@@ -1,4 +1,4 @@
|
|||||||
## PS/2 Mouse Support
|
# PS/2 Mouse Support :id=ps2-mouse-support
|
||||||
|
|
||||||
Its possible to hook up a PS/2 mouse (for example touchpads or trackpoints) to your keyboard as a composite device.
|
Its possible to hook up a PS/2 mouse (for example touchpads or trackpoints) to your keyboard as a composite device.
|
||||||
|
|
||||||
@@ -6,7 +6,7 @@ To hook up a Trackpoint, you need to obtain a Trackpoint module (i.e. harvest fr
|
|||||||
|
|
||||||
There are three available modes for hooking up PS/2 devices: USART (best), interrupts (better) or busywait (not recommended).
|
There are three available modes for hooking up PS/2 devices: USART (best), interrupts (better) or busywait (not recommended).
|
||||||
|
|
||||||
### The Cirtuitry between Trackpoint and Controller
|
## The Circuitry between Trackpoint and Controller :id=the-circuitry-between-trackpoint-and-controller
|
||||||
|
|
||||||
To get the things working, a 4.7K drag is needed between the two lines DATA and CLK and the line 5+.
|
To get the things working, a 4.7K drag is needed between the two lines DATA and CLK and the line 5+.
|
||||||
|
|
||||||
@@ -24,20 +24,20 @@ MODULE 5+ --------+--+--------- PWR CONTROLLER
|
|||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
### Busywait Version
|
## Busywait Version :id=busywait-version
|
||||||
|
|
||||||
Note: This is not recommended, you may encounter jerky movement or unsent inputs. Please use interrupt or USART version if possible.
|
Note: This is not recommended, you may encounter jerky movement or unsent inputs. Please use interrupt or USART version if possible.
|
||||||
|
|
||||||
In rules.mk:
|
In rules.mk:
|
||||||
|
|
||||||
```
|
```makefile
|
||||||
PS2_MOUSE_ENABLE = yes
|
PS2_MOUSE_ENABLE = yes
|
||||||
PS2_USE_BUSYWAIT = yes
|
PS2_USE_BUSYWAIT = yes
|
||||||
```
|
```
|
||||||
|
|
||||||
In your keyboard config.h:
|
In your keyboard config.h:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#ifdef PS2_USE_BUSYWAIT
|
#ifdef PS2_USE_BUSYWAIT
|
||||||
# define PS2_CLOCK_PORT PORTD
|
# define PS2_CLOCK_PORT PORTD
|
||||||
# define PS2_CLOCK_PIN PIND
|
# define PS2_CLOCK_PIN PIND
|
||||||
@@ -50,20 +50,20 @@ In your keyboard config.h:
|
|||||||
#endif
|
#endif
|
||||||
```
|
```
|
||||||
|
|
||||||
### Interrupt Version
|
## Interrupt Version :id=interrupt-version
|
||||||
|
|
||||||
The following example uses D2 for clock and D5 for data. You can use any INT or PCINT pin for clock, and any pin for data.
|
The following example uses D2 for clock and D5 for data. You can use any INT or PCINT pin for clock, and any pin for data.
|
||||||
|
|
||||||
In rules.mk:
|
In rules.mk:
|
||||||
|
|
||||||
```
|
```makefile
|
||||||
PS2_MOUSE_ENABLE = yes
|
PS2_MOUSE_ENABLE = yes
|
||||||
PS2_USE_INT = yes
|
PS2_USE_INT = yes
|
||||||
```
|
```
|
||||||
|
|
||||||
In your keyboard config.h:
|
In your keyboard config.h:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#ifdef PS2_USE_INT
|
#ifdef PS2_USE_INT
|
||||||
#define PS2_CLOCK_PORT PORTD
|
#define PS2_CLOCK_PORT PORTD
|
||||||
#define PS2_CLOCK_PIN PIND
|
#define PS2_CLOCK_PIN PIND
|
||||||
@@ -88,20 +88,20 @@ In your keyboard config.h:
|
|||||||
#endif
|
#endif
|
||||||
```
|
```
|
||||||
|
|
||||||
### USART Version
|
## USART Version :id=usart-version
|
||||||
|
|
||||||
To use USART on the ATMega32u4, you have to use PD5 for clock and PD2 for data. If one of those are unavailable, you need to use interrupt version.
|
To use USART on the ATMega32u4, you have to use PD5 for clock and PD2 for data. If one of those are unavailable, you need to use interrupt version.
|
||||||
|
|
||||||
In rules.mk:
|
In rules.mk:
|
||||||
|
|
||||||
```
|
```makefile
|
||||||
PS2_MOUSE_ENABLE = yes
|
PS2_MOUSE_ENABLE = yes
|
||||||
PS2_USE_USART = yes
|
PS2_USE_USART = yes
|
||||||
```
|
```
|
||||||
|
|
||||||
In your keyboard config.h:
|
In your keyboard config.h:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#ifdef PS2_USE_USART
|
#ifdef PS2_USE_USART
|
||||||
#define PS2_CLOCK_PORT PORTD
|
#define PS2_CLOCK_PORT PORTD
|
||||||
#define PS2_CLOCK_PIN PIND
|
#define PS2_CLOCK_PIN PIND
|
||||||
@@ -145,13 +145,13 @@ In your keyboard config.h:
|
|||||||
#endif
|
#endif
|
||||||
```
|
```
|
||||||
|
|
||||||
### Additional Settings
|
## Additional Settings :id=additional-settings
|
||||||
|
|
||||||
#### PS/2 Mouse Features
|
### PS/2 Mouse Features :id=ps2-mouse-features
|
||||||
|
|
||||||
These enable settings supported by the PS/2 mouse protocol.
|
These enable settings supported by the PS/2 mouse protocol.
|
||||||
|
|
||||||
```
|
```c
|
||||||
/* Use remote mode instead of the default stream mode (see link) */
|
/* Use remote mode instead of the default stream mode (see link) */
|
||||||
#define PS2_MOUSE_USE_REMOTE_MODE
|
#define PS2_MOUSE_USE_REMOTE_MODE
|
||||||
|
|
||||||
@@ -170,7 +170,7 @@ These enable settings supported by the PS/2 mouse protocol.
|
|||||||
|
|
||||||
You can also call the following functions from ps2_mouse.h
|
You can also call the following functions from ps2_mouse.h
|
||||||
|
|
||||||
```
|
```c
|
||||||
void ps2_mouse_disable_data_reporting(void);
|
void ps2_mouse_disable_data_reporting(void);
|
||||||
|
|
||||||
void ps2_mouse_enable_data_reporting(void);
|
void ps2_mouse_enable_data_reporting(void);
|
||||||
@@ -188,36 +188,36 @@ void ps2_mouse_set_resolution(ps2_mouse_resolution_t resolution);
|
|||||||
void ps2_mouse_set_sample_rate(ps2_mouse_sample_rate_t sample_rate);
|
void ps2_mouse_set_sample_rate(ps2_mouse_sample_rate_t sample_rate);
|
||||||
```
|
```
|
||||||
|
|
||||||
#### Fine Control
|
### Fine Control :id=fine-control
|
||||||
|
|
||||||
Use the following defines to change the sensitivity and speed of the mouse.
|
Use the following defines to change the sensitivity and speed of the mouse.
|
||||||
Note: you can also use `ps2_mouse_set_resolution` for the same effect (not supported on most touchpads).
|
Note: you can also use `ps2_mouse_set_resolution` for the same effect (not supported on most touchpads).
|
||||||
|
|
||||||
```
|
```c
|
||||||
#define PS2_MOUSE_X_MULTIPLIER 3
|
#define PS2_MOUSE_X_MULTIPLIER 3
|
||||||
#define PS2_MOUSE_Y_MULTIPLIER 3
|
#define PS2_MOUSE_Y_MULTIPLIER 3
|
||||||
#define PS2_MOUSE_V_MULTIPLIER 1
|
#define PS2_MOUSE_V_MULTIPLIER 1
|
||||||
```
|
```
|
||||||
|
|
||||||
#### Scroll Button
|
### Scroll Button :id=scroll-button
|
||||||
|
|
||||||
If you're using a trackpoint, you will likely want to be able to use it for scrolling.
|
If you're using a trackpoint, you will likely want to be able to use it for scrolling.
|
||||||
It's possible to enable a "scroll button/s" that when pressed will cause the mouse to scroll instead of moving.
|
It's possible to enable a "scroll button/s" that when pressed will cause the mouse to scroll instead of moving.
|
||||||
To enable the feature, you must set a scroll button mask as follows:
|
To enable the feature, you must set a scroll button mask as follows:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#define PS2_MOUSE_SCROLL_BTN_MASK (1<<PS2_MOUSE_BUTTON_MIDDLE) /* Default */
|
#define PS2_MOUSE_SCROLL_BTN_MASK (1<<PS2_MOUSE_BUTTON_MIDDLE) /* Default */
|
||||||
```
|
```
|
||||||
|
|
||||||
To disable the scroll button feature:
|
To disable the scroll button feature:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#define PS2_MOUSE_SCROLL_BTN_MASK 0
|
#define PS2_MOUSE_SCROLL_BTN_MASK 0
|
||||||
```
|
```
|
||||||
|
|
||||||
The available buttons are:
|
The available buttons are:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#define PS2_MOUSE_BTN_LEFT 0
|
#define PS2_MOUSE_BTN_LEFT 0
|
||||||
#define PS2_MOUSE_BTN_RIGHT 1
|
#define PS2_MOUSE_BTN_RIGHT 1
|
||||||
#define PS2_MOUSE_BTN_MIDDLE 2
|
#define PS2_MOUSE_BTN_MIDDLE 2
|
||||||
@@ -229,27 +229,28 @@ Once you've configured your scroll button mask, you must configure the scroll bu
|
|||||||
This is the interval before which if the scroll buttons were released they would be sent to the host.
|
This is the interval before which if the scroll buttons were released they would be sent to the host.
|
||||||
After this interval, they will cause the mouse to scroll and will not be sent.
|
After this interval, they will cause the mouse to scroll and will not be sent.
|
||||||
|
|
||||||
```
|
```c
|
||||||
#define PS2_MOUSE_SCROLL_BTN_SEND 300 /* Default */
|
#define PS2_MOUSE_SCROLL_BTN_SEND 300 /* Default */
|
||||||
```
|
```
|
||||||
|
|
||||||
To disable sending the scroll buttons:
|
To disable sending the scroll buttons:
|
||||||
```
|
|
||||||
|
```c
|
||||||
#define PS2_MOUSE_SCROLL_BTN_SEND 0
|
#define PS2_MOUSE_SCROLL_BTN_SEND 0
|
||||||
```
|
```
|
||||||
|
|
||||||
Fine control over the scrolling is supported with the following defines:
|
Fine control over the scrolling is supported with the following defines:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#define PS2_MOUSE_SCROLL_DIVISOR_H 2
|
#define PS2_MOUSE_SCROLL_DIVISOR_H 2
|
||||||
#define PS2_MOUSE_SCROLL_DIVISOR_V 2
|
#define PS2_MOUSE_SCROLL_DIVISOR_V 2
|
||||||
```
|
```
|
||||||
|
|
||||||
#### Invert Mouse and Scroll Axes
|
### Invert Mouse and Scroll Axes :id=invert-mouse-and-scroll-axes
|
||||||
|
|
||||||
To invert the X and Y axes you can put:
|
To invert the X and Y axes you can put:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#define PS2_MOUSE_INVERT_X
|
#define PS2_MOUSE_INVERT_X
|
||||||
#define PS2_MOUSE_INVERT_Y
|
#define PS2_MOUSE_INVERT_Y
|
||||||
```
|
```
|
||||||
@@ -258,19 +259,48 @@ into config.h.
|
|||||||
|
|
||||||
To reverse the scroll axes you can put:
|
To reverse the scroll axes you can put:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#define PS2_MOUSE_INVERT_H
|
#define PS2_MOUSE_INVERT_H
|
||||||
#define PS2_MOUSE_INVERT_V
|
#define PS2_MOUSE_INVERT_V
|
||||||
```
|
```
|
||||||
|
|
||||||
into config.h.
|
into config.h.
|
||||||
|
|
||||||
#### Debug Settings
|
### Rotate Mouse Axes :id=rotate-mouse-axes
|
||||||
|
|
||||||
|
Transform the output of the device with a clockwise rotation of 90, 180, or 270
|
||||||
|
degrees.
|
||||||
|
|
||||||
|
When compensating for device orientation, rotate the output the same amount in
|
||||||
|
the opposite direction. E.g. if the normal device orientation is considered to
|
||||||
|
be North-facing, compensate as follows:
|
||||||
|
|
||||||
|
```c
|
||||||
|
#define PS2_MOUSE_ROTATE 270 /* Compensate for East-facing device orientation. */
|
||||||
|
```
|
||||||
|
```c
|
||||||
|
#define PS2_MOUSE_ROTATE 180 /* Compensate for South-facing device orientation. */
|
||||||
|
```
|
||||||
|
```c
|
||||||
|
#define PS2_MOUSE_ROTATE 90 /* Compensate for West-facing device orientation. */
|
||||||
|
```
|
||||||
|
|
||||||
|
### Debug Settings :id=debug-settings
|
||||||
|
|
||||||
To debug the mouse, add `debug_mouse = true` or enable via bootmagic.
|
To debug the mouse, add `debug_mouse = true` or enable via bootmagic.
|
||||||
|
|
||||||
```
|
```c
|
||||||
/* To debug the mouse reports */
|
/* To debug the mouse reports */
|
||||||
#define PS2_MOUSE_DEBUG_HID
|
#define PS2_MOUSE_DEBUG_HID
|
||||||
#define PS2_MOUSE_DEBUG_RAW
|
#define PS2_MOUSE_DEBUG_RAW
|
||||||
```
|
```
|
||||||
|
|
||||||
|
### Movement Hook :id=movement-hook
|
||||||
|
|
||||||
|
Process mouse movement in the keymap before it is sent to the host. Example
|
||||||
|
uses include filtering noise, adding acceleration, and automatically activating
|
||||||
|
a layer. To use, define the following function in your keymap:
|
||||||
|
|
||||||
|
```c
|
||||||
|
void ps2_mouse_moved_user(report_mouse_t *mouse_report);
|
||||||
|
```
|
||||||
@@ -0,0 +1,69 @@
|
|||||||
|
# Raw HID
|
||||||
|
|
||||||
|
Raw HID allows for bidirectional communication between QMK and the host computer over an HID interface. This has many potential use cases, such as switching keymaps on the fly or changing RGB LED colors and modes.
|
||||||
|
|
||||||
|
There are two main components to getting raw HID working with your keyboard.
|
||||||
|
|
||||||
|
## Keyboard firmware
|
||||||
|
|
||||||
|
The implementation is fairly straightforward for the firmware.
|
||||||
|
In your `rules.mk` add:
|
||||||
|
|
||||||
|
```make
|
||||||
|
RAW_ENABLE = yes
|
||||||
|
```
|
||||||
|
|
||||||
|
In your `keymap.c` include `"raw_hid.h"` and implement the following:
|
||||||
|
|
||||||
|
```C
|
||||||
|
void raw_hid_receive(uint8_t *data, uint8_t length) {
|
||||||
|
// Your code goes here. data is the packet received from host.
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
The `"raw_hid.h"` header also declares `void raw_hid_send(uint8_t *data, uint8_t length);` which allows sending packets from keyboard to host. As an example, it can also be used for debugging when building your host application by returning all data back to the host.
|
||||||
|
|
||||||
|
```C
|
||||||
|
void raw_hid_receive(uint8_t *data, uint8_t length) {
|
||||||
|
raw_hid_send(data, length);
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
`raw_hid_receive` can receive variable size packets from host with maximum length `RAW_EPSIZE`. `raw_hid_send` on the other hand can send packets to host of exactly `RAW_EPSIZE` length, therefore it should be used with data of length `RAW_EPSIZE`.
|
||||||
|
|
||||||
|
Make sure to flash raw enabled firmware before proceeding with working on the host side.
|
||||||
|
|
||||||
|
## Host (Windows/macOS/Linux)
|
||||||
|
|
||||||
|
This is the more complicated part as it will require some digging.
|
||||||
|
|
||||||
|
To connect your host computer to your keyboard with raw HID you need four pieces of information about your keyboard:
|
||||||
|
|
||||||
|
1. Vendor ID
|
||||||
|
2. Product ID
|
||||||
|
3. Usage Page
|
||||||
|
4. Usage
|
||||||
|
|
||||||
|
The first two can easily be found in your keyboard's `config.h` in the keyboard's main directory under `VENDOR_ID` and `PRODUCT_ID`.
|
||||||
|
|
||||||
|
The final two can be overridden in your keyboard's `config.h` in the keyboard's main directory by redefining the values: `#define RAW_USAGE_PAGE 0xFF60` and `#define RAW_USAGE_ID 0x61`.
|
||||||
|
|
||||||
|
By default, **Usage Page** is `0xFF60` and **Usage** is `0x61`.
|
||||||
|
|
||||||
|
### Building your host
|
||||||
|
|
||||||
|
You can build your host using any language that has an available HID implementation library if you don't wish to make your own. The ones we know of for popular languages are:
|
||||||
|
|
||||||
|
* Node: [node-hid](https://github.com/node-hid/node-hid).
|
||||||
|
* C: [hidapi](https://github.com/libusb/hidapi).
|
||||||
|
* Java: [purejavahidapi](https://github.com/nyholku/purejavahidapi) and [hid4java](https://github.com/gary-rowe/hid4java).
|
||||||
|
* Python: [pyhidapi](https://pypi.org/project/hid/).
|
||||||
|
|
||||||
|
This is not an exhaustive cross-platform list but should get you started. There are no special requirements for using raw HID so any HID library should work.
|
||||||
|
|
||||||
|
Now that you have all four pieces of information required to open HID interface to your keyboard. All you need to do is use your library's available functions to open the device with its ID parameters.
|
||||||
|
|
||||||
|
Note that Vendor ID and Product ID are not actually required to open the device. They are used only to filter to a specific device out of the many HID devices you have plugged in. Many libraries will give you the option to open the device using Product Name or Manufacturer Name instead, `node-hid` being a prime example. This will create issues for devices with builtin USB Hub or any extra HID interfaces where you will have multiple interfaces with the same name or from the same manufacturer. The Vendor ID together with Product ID create a unique designation to a single interface and will not exhibit this problem. Therefore, even if your library doesn't require you to, it is best to use them to avoid issues.
|
||||||
|
Unlike Vendor ID and Product ID though, Usage Page and Usage are necessary for successful communication.
|
||||||
|
|
||||||
|
It should go without saying that regardless of the library you're using, you should always make sure to close the interface when finished. Depending on the operating system and your particular environment there may be issues connecting to it again afterwards with another client or another instance of the same client if it's not explicitly closed.
|
||||||
+119
-35
@@ -1,22 +1,22 @@
|
|||||||
# RGB Matrix Lighting
|
# RGB Matrix Lighting :id=rgb-matrix-lighting
|
||||||
|
|
||||||
This feature allows you to use RGB LED matrices driven by external drivers. It hooks into the RGBLIGHT system so you can use the same keycodes as RGBLIGHT to control it.
|
This feature allows you to use RGB LED matrices driven by external drivers. It hooks into the RGBLIGHT system so you can use the same keycodes as RGBLIGHT to control it.
|
||||||
|
|
||||||
If you want to use single color LED's you should use the [LED Matrix Subsystem](feature_led_matrix.md) instead.
|
If you want to use single color LED's you should use the [LED Matrix Subsystem](feature_led_matrix.md) instead.
|
||||||
|
|
||||||
## Driver configuration
|
## Driver configuration :id=driver-configuration
|
||||||
---
|
---
|
||||||
### IS31FL3731
|
### IS31FL3731 :id=is31fl3731
|
||||||
|
|
||||||
There is basic support for addressable RGB matrix lighting with the I2C IS31FL3731 RGB controller. To enable it, add this to your `rules.mk`:
|
There is basic support for addressable RGB matrix lighting with the I2C IS31FL3731 RGB controller. To enable it, add this to your `rules.mk`:
|
||||||
|
|
||||||
```C
|
```makefile
|
||||||
RGB_MATRIX_ENABLE = IS31FL3731
|
RGB_MATRIX_ENABLE = IS31FL3731
|
||||||
```
|
```
|
||||||
|
|
||||||
Configure the hardware via your `config.h`:
|
Configure the hardware via your `config.h`:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
// This is a 7-bit address, that gets left-shifted and bit 0
|
// This is a 7-bit address, that gets left-shifted and bit 0
|
||||||
// set to 0 for write, 1 for read (as per I2C protocol)
|
// set to 0 for write, 1 for read (as per I2C protocol)
|
||||||
// The address will vary depending on your wiring:
|
// The address will vary depending on your wiring:
|
||||||
@@ -39,7 +39,7 @@ Currently only 2 drivers are supported, but it would be trivial to support all 4
|
|||||||
|
|
||||||
Define these arrays listing all the LEDs in your `<keyboard>.c`:
|
Define these arrays listing all the LEDs in your `<keyboard>.c`:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
const is31_led g_is31_leds[DRIVER_LED_TOTAL] = {
|
const is31_led g_is31_leds[DRIVER_LED_TOTAL] = {
|
||||||
/* Refer to IS31 manual for these locations
|
/* Refer to IS31 manual for these locations
|
||||||
* driver
|
* driver
|
||||||
@@ -55,19 +55,19 @@ const is31_led g_is31_leds[DRIVER_LED_TOTAL] = {
|
|||||||
Where `Cx_y` is the location of the LED in the matrix defined by [the datasheet](http://www.issi.com/WW/pdf/31FL3731.pdf) and the header file `drivers/issi/is31fl3731.h`. The `driver` is the index of the driver you defined in your `config.h` (`0` or `1` right now).
|
Where `Cx_y` is the location of the LED in the matrix defined by [the datasheet](http://www.issi.com/WW/pdf/31FL3731.pdf) and the header file `drivers/issi/is31fl3731.h`. The `driver` is the index of the driver you defined in your `config.h` (`0` or `1` right now).
|
||||||
|
|
||||||
---
|
---
|
||||||
### IS31FL3733/IS31FL3737
|
### IS31FL3733/IS31FL3737 :id=is31fl3733is31fl3737
|
||||||
|
|
||||||
!> For the IS31FL3737, replace all instances of `IS31FL3733` below with `IS31FL3737`.
|
!> For the IS31FL3737, replace all instances of `IS31FL3733` below with `IS31FL3737`.
|
||||||
|
|
||||||
There is basic support for addressable RGB matrix lighting with the I2C IS31FL3733 RGB controller. To enable it, add this to your `rules.mk`:
|
There is basic support for addressable RGB matrix lighting with the I2C IS31FL3733 RGB controller. To enable it, add this to your `rules.mk`:
|
||||||
|
|
||||||
```C
|
```makefile
|
||||||
RGB_MATRIX_ENABLE = IS31FL3733
|
RGB_MATRIX_ENABLE = IS31FL3733
|
||||||
```
|
```
|
||||||
|
|
||||||
Configure the hardware via your `config.h`:
|
Configure the hardware via your `config.h`:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
// This is a 7-bit address, that gets left-shifted and bit 0
|
// This is a 7-bit address, that gets left-shifted and bit 0
|
||||||
// set to 0 for write, 1 for read (as per I2C protocol)
|
// set to 0 for write, 1 for read (as per I2C protocol)
|
||||||
// The address will vary depending on your wiring:
|
// The address will vary depending on your wiring:
|
||||||
@@ -90,7 +90,7 @@ Currently only a single drivers is supported, but it would be trivial to support
|
|||||||
|
|
||||||
Define these arrays listing all the LEDs in your `<keyboard>.c`:
|
Define these arrays listing all the LEDs in your `<keyboard>.c`:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
const is31_led g_is31_leds[DRIVER_LED_TOTAL] = {
|
const is31_led g_is31_leds[DRIVER_LED_TOTAL] = {
|
||||||
/* Refer to IS31 manual for these locations
|
/* Refer to IS31 manual for these locations
|
||||||
* driver
|
* driver
|
||||||
@@ -107,17 +107,17 @@ Where `X_Y` is the location of the LED in the matrix defined by [the datasheet](
|
|||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
### WS2812
|
### WS2812 :id=ws2812
|
||||||
|
|
||||||
There is basic support for addressable RGB matrix lighting with a WS2811/WS2812{a,b,c} addressable LED strand. To enable it, add this to your `rules.mk`:
|
There is basic support for addressable RGB matrix lighting with a WS2811/WS2812{a,b,c} addressable LED strand. To enable it, add this to your `rules.mk`:
|
||||||
|
|
||||||
```C
|
```makefile
|
||||||
RGB_MATRIX_ENABLE = WS2812
|
RGB_MATRIX_ENABLE = WS2812
|
||||||
```
|
```
|
||||||
|
|
||||||
Configure the hardware via your `config.h`:
|
Configure the hardware via your `config.h`:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
// The pin connected to the data pin of the LEDs
|
// The pin connected to the data pin of the LEDs
|
||||||
#define RGB_DI_PIN D7
|
#define RGB_DI_PIN D7
|
||||||
// The number of LEDs connected
|
// The number of LEDs connected
|
||||||
@@ -128,7 +128,7 @@ Configure the hardware via your `config.h`:
|
|||||||
|
|
||||||
From this point forward the configuration is the same for all the drivers. The `led_config_t` struct provides a key electrical matrix to led index lookup table, what the physical position of each LED is on the board, and what type of key or usage the LED if the LED represents. Here is a brief example:
|
From this point forward the configuration is the same for all the drivers. The `led_config_t` struct provides a key electrical matrix to led index lookup table, what the physical position of each LED is on the board, and what type of key or usage the LED if the LED represents. Here is a brief example:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
const led_config_t g_led_config = { {
|
const led_config_t g_led_config = { {
|
||||||
// Key Matrix to LED Index
|
// Key Matrix to LED Index
|
||||||
{ 5, NO_LED, NO_LED, 0 },
|
{ 5, NO_LED, NO_LED, 0 },
|
||||||
@@ -146,7 +146,7 @@ const led_config_t g_led_config = { {
|
|||||||
|
|
||||||
The first part, `// Key Matrix to LED Index`, tells the system what key this LED represents by using the key's electrical matrix row & col. The second part, `// LED Index to Physical Position` represents the LED's physical `{ x, y }` position on the keyboard. The default expected range of values for `{ x, y }` is the inclusive range `{ 0..224, 0..64 }`. This default expected range is due to effects that calculate the center of the keyboard for their animations. The easiest way to calculate these positions is imagine your keyboard is a grid, and the top left of the keyboard represents `{ x, y }` coordinate `{ 0, 0 }` and the bottom right of your keyboard represents `{ 224, 64 }`. Using this as a basis, you can use the following formula to calculate the physical position:
|
The first part, `// Key Matrix to LED Index`, tells the system what key this LED represents by using the key's electrical matrix row & col. The second part, `// LED Index to Physical Position` represents the LED's physical `{ x, y }` position on the keyboard. The default expected range of values for `{ x, y }` is the inclusive range `{ 0..224, 0..64 }`. This default expected range is due to effects that calculate the center of the keyboard for their animations. The easiest way to calculate these positions is imagine your keyboard is a grid, and the top left of the keyboard represents `{ x, y }` coordinate `{ 0, 0 }` and the bottom right of your keyboard represents `{ 224, 64 }`. Using this as a basis, you can use the following formula to calculate the physical position:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
x = 224 / (NUMBER_OF_COLS - 1) * COL_POSITION
|
x = 224 / (NUMBER_OF_COLS - 1) * COL_POSITION
|
||||||
y = 64 / (NUMBER_OF_ROWS - 1) * ROW_POSITION
|
y = 64 / (NUMBER_OF_ROWS - 1) * ROW_POSITION
|
||||||
```
|
```
|
||||||
@@ -157,7 +157,7 @@ As mentioned earlier, the center of the keyboard by default is expected to be `{
|
|||||||
|
|
||||||
`// LED Index to Flag` is a bitmask, whether or not a certain LEDs is of a certain type. It is recommended that LEDs are set to only 1 type.
|
`// LED Index to Flag` is a bitmask, whether or not a certain LEDs is of a certain type. It is recommended that LEDs are set to only 1 type.
|
||||||
|
|
||||||
## Flags
|
## Flags :id=flags
|
||||||
|
|
||||||
|Define |Description |
|
|Define |Description |
|
||||||
|------------------------------------|-------------------------------------------|
|
|------------------------------------|-------------------------------------------|
|
||||||
@@ -169,7 +169,7 @@ As mentioned earlier, the center of the keyboard by default is expected to be `{
|
|||||||
|`#define LED_FLAG_UNDERGLOW 0x02` |If the LED is for underglow. |
|
|`#define LED_FLAG_UNDERGLOW 0x02` |If the LED is for underglow. |
|
||||||
|`#define LED_FLAG_KEYLIGHT 0x04` |If the LED is for key backlight. |
|
|`#define LED_FLAG_KEYLIGHT 0x04` |If the LED is for key backlight. |
|
||||||
|
|
||||||
## Keycodes
|
## Keycodes :id=keycodes
|
||||||
|
|
||||||
All RGB keycodes are currently shared with the RGBLIGHT system:
|
All RGB keycodes are currently shared with the RGBLIGHT system:
|
||||||
|
|
||||||
@@ -186,14 +186,22 @@ All RGB keycodes are currently shared with the RGBLIGHT system:
|
|||||||
|`RGB_VAD` | |Decrease value (brightness), increase value when Shift is held |
|
|`RGB_VAD` | |Decrease value (brightness), increase value when Shift is held |
|
||||||
|`RGB_SPI` | |Increase effect speed (does not support eeprom yet), decrease speed when Shift is held|
|
|`RGB_SPI` | |Increase effect speed (does not support eeprom yet), decrease speed when Shift is held|
|
||||||
|`RGB_SPD` | |Decrease effect speed (does not support eeprom yet), increase speed when Shift is held|
|
|`RGB_SPD` | |Decrease effect speed (does not support eeprom yet), increase speed when Shift is held|
|
||||||
|
|`RGB_MODE_PLAIN` |`RGB_M_P `|Static (no animation) mode |
|
||||||
|
|`RGB_MODE_BREATHE` |`RGB_M_B` |Breathing animation mode |
|
||||||
|
|`RGB_MODE_RAINBOW` |`RGB_M_R` |Full gradient scrolling left to right (uses the `RGB_MATRIX_CYCLE_LEFT_RIGHT` mode) |
|
||||||
|
|`RGB_MODE_SWIRL` |`RGB_M_SW`|Full gradient spinning pinwheel around center of keyboard (uses `RGB_MATRIX_CYCLE_PINWHEEL` mode) |
|
||||||
|
|
||||||
* `RGB_MODE_*` keycodes will generally work, but are not currently mapped to the correct effects for the RGB Matrix system
|
* `RGB_MODE_*` keycodes will generally work, but not all of the modes are currently mapped to the correct effects for the RGB Matrix system.
|
||||||
|
|
||||||
## RGB Matrix Effects
|
`RGB_MODE_PLAIN`, `RGB_MODE_BREATHE`, `RGB_MODE_RAINBOW`, and `RGB_MATRIX_SWIRL` are the only ones that are mapped properly. The rest don't have a direct equivalent, and are not mapped.
|
||||||
|
|
||||||
|
!> By default, if you have both the [RGB Light](feature_rgblight.md) and the RGB Matrix feature enabled, these keycodes will work for both features, at the same time. You can disable the keycode functionality by defining the `*_DISABLE_KEYCODES` option for the specific feature.
|
||||||
|
|
||||||
|
## RGB Matrix Effects :id=rgb-matrix-effects
|
||||||
|
|
||||||
All effects have been configured to support current configuration values (Hue, Saturation, Value, & Speed) unless otherwise noted below. These are the effects that are currently available:
|
All effects have been configured to support current configuration values (Hue, Saturation, Value, & Speed) unless otherwise noted below. These are the effects that are currently available:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
enum rgb_matrix_effects {
|
enum rgb_matrix_effects {
|
||||||
RGB_MATRIX_NONE = 0,
|
RGB_MATRIX_NONE = 0,
|
||||||
RGB_MATRIX_SOLID_COLOR = 1, // Static single hue, no speed support
|
RGB_MATRIX_SOLID_COLOR = 1, // Static single hue, no speed support
|
||||||
@@ -285,7 +293,7 @@ You can disable a single effect by defining `DISABLE_[EFFECT_NAME]` in your `con
|
|||||||
|`#define DISABLE_RGB_MATRIX_SOLID_MULTISPLASH` |Disables `RGB_MATRIX_SOLID_MULTISPLASH` |
|
|`#define DISABLE_RGB_MATRIX_SOLID_MULTISPLASH` |Disables `RGB_MATRIX_SOLID_MULTISPLASH` |
|
||||||
|
|
||||||
|
|
||||||
## Custom RGB Matrix Effects
|
## Custom RGB Matrix Effects :id=custom-rgb-matrix-effects
|
||||||
|
|
||||||
By setting `RGB_MATRIX_CUSTOM_USER` (and/or `RGB_MATRIX_CUSTOM_KB`) in `rules.mk`, new effects can be defined directly from userspace, without having to edit any QMK core files.
|
By setting `RGB_MATRIX_CUSTOM_USER` (and/or `RGB_MATRIX_CUSTOM_KB`) in `rules.mk`, new effects can be defined directly from userspace, without having to edit any QMK core files.
|
||||||
|
|
||||||
@@ -294,7 +302,7 @@ To declare new effects, create a new `rgb_matrix_user/kb.inc` that looks somethi
|
|||||||
`rgb_matrix_user.inc` should go in the root of the keymap directory.
|
`rgb_matrix_user.inc` should go in the root of the keymap directory.
|
||||||
`rgb_matrix_kb.inc` should go in the root of the keyboard directory.
|
`rgb_matrix_kb.inc` should go in the root of the keyboard directory.
|
||||||
|
|
||||||
```C
|
```c
|
||||||
// !!! DO NOT ADD #pragma once !!! //
|
// !!! DO NOT ADD #pragma once !!! //
|
||||||
|
|
||||||
// Step 1.
|
// Step 1.
|
||||||
@@ -341,7 +349,7 @@ static bool my_cool_effect2(effect_params_t* params) {
|
|||||||
For inspiration and examples, check out the built-in effects under `quantum/rgb_matrix_animation/`
|
For inspiration and examples, check out the built-in effects under `quantum/rgb_matrix_animation/`
|
||||||
|
|
||||||
|
|
||||||
## Colors
|
## Colors :id=colors
|
||||||
|
|
||||||
These are shorthands to popular colors. The `RGB` ones can be passed to the `setrgb` functions, while the `HSV` ones to the `sethsv` functions.
|
These are shorthands to popular colors. The `RGB` ones can be passed to the `setrgb` functions, while the `HSV` ones to the `sethsv` functions.
|
||||||
|
|
||||||
@@ -369,12 +377,13 @@ These are shorthands to popular colors. The `RGB` ones can be passed to the `set
|
|||||||
These are defined in [`rgblight_list.h`](https://github.com/qmk/qmk_firmware/blob/master/quantum/rgblight_list.h). Feel free to add to this list!
|
These are defined in [`rgblight_list.h`](https://github.com/qmk/qmk_firmware/blob/master/quantum/rgblight_list.h). Feel free to add to this list!
|
||||||
|
|
||||||
|
|
||||||
## Additional `config.h` Options
|
## Additional `config.h` Options :id=additional-configh-options
|
||||||
|
|
||||||
```C
|
```c
|
||||||
#define RGB_MATRIX_KEYPRESSES // reacts to keypresses
|
#define RGB_MATRIX_KEYPRESSES // reacts to keypresses
|
||||||
#define RGB_MATRIX_KEYRELEASES // reacts to keyreleases (instead of keypresses)
|
#define RGB_MATRIX_KEYRELEASES // reacts to keyreleases (instead of keypresses)
|
||||||
#define RGB_DISABLE_AFTER_TIMEOUT 0 // number of ticks to wait until disabling effects
|
#define RGB_DISABLE_TIMEOUT 0 // number of milliseconds to wait until rgb automatically turns off
|
||||||
|
#define RGB_DISABLE_AFTER_TIMEOUT 0 // OBSOLETE: number of ticks to wait until disabling effects
|
||||||
#define RGB_DISABLE_WHEN_USB_SUSPENDED false // turn off effects when suspended
|
#define RGB_DISABLE_WHEN_USB_SUSPENDED false // turn off effects when suspended
|
||||||
#define RGB_MATRIX_LED_PROCESS_LIMIT (DRIVER_LED_TOTAL + 4) / 5 // limits the number of LEDs to process in an animation per task run (increases keyboard responsiveness)
|
#define RGB_MATRIX_LED_PROCESS_LIMIT (DRIVER_LED_TOTAL + 4) / 5 // limits the number of LEDs to process in an animation per task run (increases keyboard responsiveness)
|
||||||
#define RGB_MATRIX_LED_FLUSH_LIMIT 16 // limits in milliseconds how frequently an animation will update the LEDs. 16 (16ms) is equivalent to limiting to 60fps (increases keyboard responsiveness)
|
#define RGB_MATRIX_LED_FLUSH_LIMIT 16 // limits in milliseconds how frequently an animation will update the LEDs. 16 (16ms) is equivalent to limiting to 60fps (increases keyboard responsiveness)
|
||||||
@@ -384,30 +393,105 @@ These are defined in [`rgblight_list.h`](https://github.com/qmk/qmk_firmware/blo
|
|||||||
#define RGB_MATRIX_STARTUP_SAT 255 // Sets the default saturation value, if none has been set
|
#define RGB_MATRIX_STARTUP_SAT 255 // Sets the default saturation value, if none has been set
|
||||||
#define RGB_MATRIX_STARTUP_VAL RGB_MATRIX_MAXIMUM_BRIGHTNESS // Sets the default brightness value, if none has been set
|
#define RGB_MATRIX_STARTUP_VAL RGB_MATRIX_MAXIMUM_BRIGHTNESS // Sets the default brightness value, if none has been set
|
||||||
#define RGB_MATRIX_STARTUP_SPD 127 // Sets the default animation speed, if none has been set
|
#define RGB_MATRIX_STARTUP_SPD 127 // Sets the default animation speed, if none has been set
|
||||||
|
#define RGB_MATRIX_DISABLE_KEYCODES // disables control of rgb matrix by keycodes (must use code functions to control the feature)
|
||||||
```
|
```
|
||||||
|
|
||||||
## EEPROM storage
|
## EEPROM storage :id=eeprom-storage
|
||||||
|
|
||||||
The EEPROM for it is currently shared with the RGBLIGHT system (it's generally assumed only one RGB would be used at a time), but could be configured to use its own 32bit address with:
|
The EEPROM for it is currently shared with the RGBLIGHT system (it's generally assumed only one RGB would be used at a time), but could be configured to use its own 32bit address with:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
#define EECONFIG_RGB_MATRIX (uint32_t *)28
|
#define EECONFIG_RGB_MATRIX (uint32_t *)28
|
||||||
```
|
```
|
||||||
|
|
||||||
Where `28` is an unused index from `eeconfig.h`.
|
Where `28` is an unused index from `eeconfig.h`.
|
||||||
|
|
||||||
## Suspended state
|
## Functions :id=functions
|
||||||
|
|
||||||
To use the suspend feature, add this to your `<keyboard>.c`:
|
### Direct Operation :id=direct-operation
|
||||||
|
|Function |Description |
|
||||||
|
|--------------------------------------------|-------------|
|
||||||
|
|`rgb_matrix_set_color_all(r, g, b)` |Set all of the LEDs to the given RGB value, where `r`/`g`/`b` are between 0 and 255 (not written to EEPROM) |
|
||||||
|
|`rgb_matrix_set_color(index, r, g, b)` |Set a single LED to the given RGB value, where `r`/`g`/`b` are between 0 and 255, and `index` is between 0 and `DRIVER_LED_TOTAL` (not written to EEPROM) |
|
||||||
|
|
||||||
```C
|
### Disable/Enable Effects :id=disable-enable-effects
|
||||||
void suspend_power_down_kb(void)
|
|Function |Description |
|
||||||
{
|
|--------------------------------------------|-------------|
|
||||||
|
|`rgb_matrix_toggle()` |Toggle effect range LEDs between on and off |
|
||||||
|
|`rgb_matrix_toggle_noeeprom()` |Toggle effect range LEDs between on and off (not written to EEPROM) |
|
||||||
|
|`rgb_matrix_enable()` |Turn effect range LEDs on, based on their previous state |
|
||||||
|
|`rgb_matrix_enable_noeeprom()` |Turn effect range LEDs on, based on their previous state (not written to EEPROM) |
|
||||||
|
|`rgb_matrix_disable()` |Turn effect range LEDs off |
|
||||||
|
|`rgb_matrix_disable_noeeprom()` |Turn effect range LEDs off (not written to EEPROM) |
|
||||||
|
|
||||||
|
### Change Effect Mode :id=change-effect-mode
|
||||||
|
|Function |Description |
|
||||||
|
|--------------------------------------------|-------------|
|
||||||
|
|`rgb_matrix_mode(mode)` |Set the mode, if RGB animations are enabled |
|
||||||
|
|`rgb_matrix_mode_noeeprom(mode)` |Set the mode, if RGB animations are enabled (not written to EEPROM) |
|
||||||
|
|`rgb_matrix_step()` |Change the mode to the next RGB animation in the list of enabled RGB animations |
|
||||||
|
|`rgb_matrix_step_reverse()` |Change the mode to the previous RGB animation in the list of enabled RGB animations |
|
||||||
|
|`rgb_matrix_increase_speed()` |Increases the speed of the animations |
|
||||||
|
|`rgb_matrix_decrease_speed()` |Decreases the speed of the animations |
|
||||||
|
|
||||||
|
### Change Color :id=change-color
|
||||||
|
|Function |Description |
|
||||||
|
|--------------------------------------------|-------------|
|
||||||
|
|`rgb_matrix_increase_hue()` |Increase the hue for effect range LEDs. This wraps around at maximum hue |
|
||||||
|
|`rgb_matrix_decrease_hue()` |Decrease the hue for effect range LEDs. This wraps around at minimum hue |
|
||||||
|
|`rgb_matrix_increase_sat()` |Increase the saturation for effect range LEDs. This wraps around at maximum saturation |
|
||||||
|
|`rgb_matrix_decrease_sat()` |Decrease the saturation for effect range LEDs. This wraps around at minimum saturation |
|
||||||
|
|`rgb_matrix_increase_val()` |Increase the value for effect range LEDs. This wraps around at maximum value |
|
||||||
|
|`rgb_matrix_decrease_val()` |Decrease the value for effect range LEDs. This wraps around at minimum value |
|
||||||
|
|`rgb_matrix_sethsv(h, s, v)` |Set LEDs to the given HSV value where `h`/`s`/`v` are between 0 and 255 |
|
||||||
|
|`rgb_matrix_sethsv_noeeprom(h, s, v)` |Set LEDs to the given HSV value where `h`/`s`/`v` are between 0 and 255 (not written to EEPROM) |
|
||||||
|
|
||||||
|
### Query Current Status :id=query-current-status
|
||||||
|
|Function |Description |
|
||||||
|
|---------------------------------|---------------------------|
|
||||||
|
|`rgb_matrix_is_enabled()` |Gets current on/off status |
|
||||||
|
|`rgb_matrix_get_mode()` |Gets current mode |
|
||||||
|
|`rgb_matrix_get_hue()` |Gets current hue |
|
||||||
|
|`rgb_matrix_get_sat()` |Gets current sat |
|
||||||
|
|`rgb_matrix_get_val()` |Gets current val |
|
||||||
|
|`rgb_matrix_get_hsv()` |Gets hue, sat, and val and returns a [`HSV` structure](https://github.com/qmk/qmk_firmware/blob/7ba6456c0b2e041bb9f97dbed265c5b8b4b12192/quantum/color.h#L56-L61)|
|
||||||
|
|`rgb_matrix_get_speed()` |Gets current speed |
|
||||||
|
|`rgb_matrix_get_suspend_state()` |Gets current suspend state |
|
||||||
|
|
||||||
|
## Callbacks :id=callbacks
|
||||||
|
|
||||||
|
### Indicators :id=indicators
|
||||||
|
|
||||||
|
If you want to set custom indicators, such as an LED for Caps Lock, or layer indication, you can use the `rgb_matrix_indicators_kb` or `rgb_matrix_indicators_user` function for that:
|
||||||
|
```c
|
||||||
|
void rgb_matrix_indicators_kb(void) {
|
||||||
|
rgb_matrix_set_color(index, red, green, blue);
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### Suspended state :id=suspended-state
|
||||||
|
To use the suspend feature, make sure that `#define RGB_DISABLE_WHEN_USB_SUSPENDED true` is added to the `config.h` file.
|
||||||
|
|
||||||
|
Additionally add this to your `<keyboard>.c`:
|
||||||
|
|
||||||
|
```c
|
||||||
|
void suspend_power_down_kb(void) {
|
||||||
|
rgb_matrix_set_suspend_state(true);
|
||||||
|
suspend_power_down_user();
|
||||||
|
}
|
||||||
|
|
||||||
|
void suspend_wakeup_init_kb(void) {
|
||||||
|
rgb_matrix_set_suspend_state(false);
|
||||||
|
suspend_wakeup_init_user();
|
||||||
|
}
|
||||||
|
```
|
||||||
|
or add this to your `keymap.c`:
|
||||||
|
```c
|
||||||
|
void suspend_power_down_user(void) {
|
||||||
rgb_matrix_set_suspend_state(true);
|
rgb_matrix_set_suspend_state(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
void suspend_wakeup_init_kb(void)
|
void suspend_wakeup_init_user(void) {
|
||||||
{
|
|
||||||
rgb_matrix_set_suspend_state(false);
|
rgb_matrix_set_suspend_state(false);
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
+85
-25
@@ -64,6 +64,9 @@ Changing the **Value** sets the overall brightness.<br>
|
|||||||
|`RGB_MODE_GRADIENT`|`RGB_M_G` |Static gradient animation mode |
|
|`RGB_MODE_GRADIENT`|`RGB_M_G` |Static gradient animation mode |
|
||||||
|`RGB_MODE_RGBTEST` |`RGB_M_T` |Red, Green, Blue test animation mode |
|
|`RGB_MODE_RGBTEST` |`RGB_M_T` |Red, Green, Blue test animation mode |
|
||||||
|
|
||||||
|
!> By default, if you have both the RGB Light and the [RGB Matrix](feature_rgb_matrix.md) feature enabled, these keycodes will work for both features, at the same time. You can disable the keycode functionality by defining the `*_DISABLE_KEYCODES` option for the specific feature.
|
||||||
|
|
||||||
|
|
||||||
## Configuration
|
## Configuration
|
||||||
|
|
||||||
Your RGB lighting can be configured by placing these `#define`s in your `config.h`:
|
Your RGB lighting can be configured by placing these `#define`s in your `config.h`:
|
||||||
@@ -76,6 +79,7 @@ Your RGB lighting can be configured by placing these `#define`s in your `config.
|
|||||||
|`RGBLIGHT_LIMIT_VAL` |`255` |The maximum brightness level |
|
|`RGBLIGHT_LIMIT_VAL` |`255` |The maximum brightness level |
|
||||||
|`RGBLIGHT_SLEEP` |*Not defined*|If defined, the RGB lighting will be switched off when the host goes to sleep|
|
|`RGBLIGHT_SLEEP` |*Not defined*|If defined, the RGB lighting will be switched off when the host goes to sleep|
|
||||||
|`RGBLIGHT_SPLIT` |*Not defined*|If defined, synchronization functionality for split keyboards is added|
|
|`RGBLIGHT_SPLIT` |*Not defined*|If defined, synchronization functionality for split keyboards is added|
|
||||||
|
|`RGBLIGHT_DISABLE_KEYCODES`|*not defined*|If defined, disables the ability to control RGB Light from the keycodes. You must use code functions to control the feature|
|
||||||
|
|
||||||
## Effects and Animations
|
## Effects and Animations
|
||||||
|
|
||||||
@@ -94,6 +98,7 @@ if `RGBLIGHT_EFFECT_xxxx` or `RGBLIGHT_ANIMATIONS` is defined, you also have a n
|
|||||||
|`RGBLIGHT_MODE_STATIC_GRADIENT`| 0,1,..,9 |Static gradient |
|
|`RGBLIGHT_MODE_STATIC_GRADIENT`| 0,1,..,9 |Static gradient |
|
||||||
|`RGBLIGHT_MODE_RGB_TEST` | *None* |RGB Test |
|
|`RGBLIGHT_MODE_RGB_TEST` | *None* |RGB Test |
|
||||||
|`RGBLIGHT_MODE_ALTERNATING` | *None* |Alternating |
|
|`RGBLIGHT_MODE_ALTERNATING` | *None* |Alternating |
|
||||||
|
|`RGBLIGHT_MODE_TWINKLE` | 0,1,2,3,4,5 |Twinkle |
|
||||||
|
|
||||||
Check out [this video](https://youtube.com/watch?v=VKrpPAHlisY) for a demonstration.
|
Check out [this video](https://youtube.com/watch?v=VKrpPAHlisY) for a demonstration.
|
||||||
|
|
||||||
@@ -103,8 +108,8 @@ Note: For versions older than 0.6.117, The mode numbers were written directly. I
|
|||||||
|
|
||||||
Use these defines to add or remove animations from the firmware. When you are running low on flash space, it can be helpful to disable animations you are not using.
|
Use these defines to add or remove animations from the firmware. When you are running low on flash space, it can be helpful to disable animations you are not using.
|
||||||
|
|
||||||
|Define |Default |Description |
|
|Define |Default |Description |
|
||||||
|------------------------------------|-------------|-------------------------------------------------------------------------------------|
|
|------------------------------------|-------------|-------------------------------------------------------------------------|
|
||||||
|`RGBLIGHT_ANIMATIONS` |*Not defined*|Enable all additional animation modes. |
|
|`RGBLIGHT_ANIMATIONS` |*Not defined*|Enable all additional animation modes. |
|
||||||
|`RGBLIGHT_EFFECT_ALTERNATING` |*Not defined*|Enable alternating animation mode. |
|
|`RGBLIGHT_EFFECT_ALTERNATING` |*Not defined*|Enable alternating animation mode. |
|
||||||
|`RGBLIGHT_EFFECT_BREATHING` |*Not defined*|Enable breathing animation mode. |
|
|`RGBLIGHT_EFFECT_BREATHING` |*Not defined*|Enable breathing animation mode. |
|
||||||
@@ -115,6 +120,7 @@ Use these defines to add or remove animations from the firmware. When you are ru
|
|||||||
|`RGBLIGHT_EFFECT_RGB_TEST` |*Not defined*|Enable RGB test animation mode. |
|
|`RGBLIGHT_EFFECT_RGB_TEST` |*Not defined*|Enable RGB test animation mode. |
|
||||||
|`RGBLIGHT_EFFECT_SNAKE` |*Not defined*|Enable snake animation mode. |
|
|`RGBLIGHT_EFFECT_SNAKE` |*Not defined*|Enable snake animation mode. |
|
||||||
|`RGBLIGHT_EFFECT_STATIC_GRADIENT` |*Not defined*|Enable static gradient mode. |
|
|`RGBLIGHT_EFFECT_STATIC_GRADIENT` |*Not defined*|Enable static gradient mode. |
|
||||||
|
|`RGBLIGHT_EFFECT_TWINKLE` |*Not defined*|Enable twinkle animation mode. |
|
||||||
|
|
||||||
### Effect and Animation Settings
|
### Effect and Animation Settings
|
||||||
|
|
||||||
@@ -131,6 +137,8 @@ The following options are used to tweak the various animations:
|
|||||||
|`RGBLIGHT_EFFECT_KNIGHT_OFFSET` |`0` |The number of LEDs to start the "Knight" animation from the start of the strip by |
|
|`RGBLIGHT_EFFECT_KNIGHT_OFFSET` |`0` |The number of LEDs to start the "Knight" animation from the start of the strip by |
|
||||||
|`RGBLIGHT_RAINBOW_SWIRL_RANGE` |`255` |Range adjustment for the rainbow swirl effect to get different swirls |
|
|`RGBLIGHT_RAINBOW_SWIRL_RANGE` |`255` |Range adjustment for the rainbow swirl effect to get different swirls |
|
||||||
|`RGBLIGHT_EFFECT_SNAKE_LENGTH` |`4` |The number of LEDs to light up for the "Snake" animation |
|
|`RGBLIGHT_EFFECT_SNAKE_LENGTH` |`4` |The number of LEDs to light up for the "Snake" animation |
|
||||||
|
|`RGBLIGHT_EFFECT_TWINKLE_LIFE` |`75` |Adjusts how quickly each LED brightens and dims when twinkling (in animation steps) |
|
||||||
|
|`RGBLIGHT_EFFECT_TWINKLE_PROBABILITY`|`1/127` |Adjusts how likely each LED is to twinkle (on each animation step) |
|
||||||
|
|
||||||
### Example Usage to Reduce Memory Footprint
|
### Example Usage to Reduce Memory Footprint
|
||||||
1. Remove `RGBLIGHT_ANIMATIONS` from `config.h`.
|
1. Remove `RGBLIGHT_ANIMATIONS` from `config.h`.
|
||||||
@@ -168,6 +176,9 @@ const uint8_t RGBLED_SNAKE_INTERVALS[] PROGMEM = {100, 50, 20};
|
|||||||
// How long (in milliseconds) to wait between animation steps for each of the "Knight" animations
|
// How long (in milliseconds) to wait between animation steps for each of the "Knight" animations
|
||||||
const uint8_t RGBLED_KNIGHT_INTERVALS[] PROGMEM = {127, 63, 31};
|
const uint8_t RGBLED_KNIGHT_INTERVALS[] PROGMEM = {127, 63, 31};
|
||||||
|
|
||||||
|
// How long (in milliseconds) to wait between animation steps for each of the "Twinkle" animations
|
||||||
|
const uint8_t RGBLED_TWINKLE_INTERVALS[] PROGMEM = {50, 25, 10};
|
||||||
|
|
||||||
// These control which hues are selected for each of the "Static gradient" modes
|
// These control which hues are selected for each of the "Static gradient" modes
|
||||||
const uint8_t RGBLED_GRADIENT_RANGES[] PROGMEM = {255, 170, 127, 85, 64};
|
const uint8_t RGBLED_GRADIENT_RANGES[] PROGMEM = {255, 170, 127, 85, 64};
|
||||||
```
|
```
|
||||||
@@ -175,23 +186,27 @@ const uint8_t RGBLED_GRADIENT_RANGES[] PROGMEM = {255, 170, 127, 85, 64};
|
|||||||
## Lighting Layers
|
## Lighting Layers
|
||||||
|
|
||||||
By including `#define RGBLIGHT_LAYERS` in your `config.h` file you can enable lighting layers. These make
|
By including `#define RGBLIGHT_LAYERS` in your `config.h` file you can enable lighting layers. These make
|
||||||
it easy to use your underglow LEDs as status indicators to show which keyboard layer is currently active, or the state of caps lock, all without disrupting any animations. [Here's a video](https://youtu.be/uLGE1epbmdY) showing an example of what you can do.
|
it easy to use your underglow LEDs as status indicators to show which keyboard layer is currently active, or the state of caps lock, all without disrupting any animations. [Here's a video](https://youtu.be/uLGE1epbmdY) showing an example of what you can do.
|
||||||
|
|
||||||
|
### Defining Lighting Layers :id=defining-lighting-layers
|
||||||
|
|
||||||
|
By default, 8 layers are possible. This can be expanded to as many as 32 by overriding the definition of `RGBLIGHT_MAX_LAYERS` in `config.h` (e.g. `#define RGBLIGHT_MAX_LAYERS 32`). Please note, if you use a split keyboard, you will need to flash both sides of the split after changing this. Also, increasing the maximum will increase the firmware size, and will slow sync on split keyboards.
|
||||||
|
|
||||||
To define a layer, we modify `keymap.c` to list out LED ranges and the colors we want to overlay on them using an array of `rgblight_segment_t` using the `RGBLIGHT_LAYER_SEGMENTS` macro. We can define multiple layers and enable/disable them independently:
|
To define a layer, we modify `keymap.c` to list out LED ranges and the colors we want to overlay on them using an array of `rgblight_segment_t` using the `RGBLIGHT_LAYER_SEGMENTS` macro. We can define multiple layers and enable/disable them independently:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
// Light LEDs 6 to 9 and 12 to 15 red when caps lock is active. Hard to ignore!
|
// Light LEDs 6 to 9 and 12 to 15 red when caps lock is active. Hard to ignore!
|
||||||
const rgblight_segment_t PROGMEM my_capslock_layer[] = RGBLIGHT_LAYER_SEGMENTS(
|
const rgblight_segment_t PROGMEM my_capslock_layer[] = RGBLIGHT_LAYER_SEGMENTS(
|
||||||
{6, 4, HSV_RED}, // Light 4 LEDs, starting with LED 6
|
{6, 4, HSV_RED}, // Light 4 LEDs, starting with LED 6
|
||||||
{12, 4, HSV_RED} // Light 4 LEDs, starting with LED 12
|
{12, 4, HSV_RED} // Light 4 LEDs, starting with LED 12
|
||||||
);
|
);
|
||||||
// Light LEDs 9 & 10 in cyan when keyboard layer 1 is active
|
// Light LEDs 9 & 10 in cyan when keyboard layer 1 is active
|
||||||
const rgblight_segment_t PROGMEM my_layer1_layer[] = RGBLIGHT_LAYER_SEGMENTS(
|
const rgblight_segment_t PROGMEM my_layer1_layer[] = RGBLIGHT_LAYER_SEGMENTS(
|
||||||
{9, 2, HSV_CYAN}
|
{9, 2, HSV_CYAN}
|
||||||
);
|
);
|
||||||
// Light LEDs 11 & 12 in purple when keyboard layer 2 is active
|
// Light LEDs 11 & 12 in purple when keyboard layer 2 is active
|
||||||
const rgblight_segment_t PROGMEM my_layer2_layer[] = RGBLIGHT_LAYER_SEGMENTS(
|
const rgblight_segment_t PROGMEM my_layer2_layer[] = RGBLIGHT_LAYER_SEGMENTS(
|
||||||
{11, 2, HSV_PURPLE},
|
{11, 2, HSV_PURPLE}
|
||||||
);
|
);
|
||||||
// etc..
|
// etc..
|
||||||
```
|
```
|
||||||
@@ -201,33 +216,76 @@ We combine these layers into an array using the `RGBLIGHT_LAYERS_LIST` macro, an
|
|||||||
```c
|
```c
|
||||||
// Now define the array of layers. Later layers take precedence
|
// Now define the array of layers. Later layers take precedence
|
||||||
const rgblight_segment_t* const PROGMEM my_rgb_layers[] = RGBLIGHT_LAYERS_LIST(
|
const rgblight_segment_t* const PROGMEM my_rgb_layers[] = RGBLIGHT_LAYERS_LIST(
|
||||||
my_capslock_layer,
|
my_capslock_layer,
|
||||||
my_layer1_layer, // Overrides caps lock layer
|
my_layer1_layer, // Overrides caps lock layer
|
||||||
my_layer2_layer // Overrides other layers
|
my_layer2_layer // Overrides other layers
|
||||||
);
|
);
|
||||||
|
|
||||||
void keyboard_post_init_user(void) {
|
void keyboard_post_init_user(void) {
|
||||||
// Enable the LED layers
|
// Enable the LED layers
|
||||||
rgblight_layers = my_rgb_layers;
|
rgblight_layers = my_rgb_layers;
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
Note: For split keyboards with two controllers, both sides need to be flashed when updating the contents of rgblight_layers.
|
||||||
|
|
||||||
Finally, we enable and disable the lighting layers whenever the state of the keyboard changes:
|
### Enabling and disabling lighting layers :id=enabling-lighting-layers
|
||||||
|
|
||||||
|
Everything above just configured the definition of each lighting layer.
|
||||||
|
We can now enable and disable the lighting layers whenever the state of the keyboard changes:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
layer_state_t layer_state_set_user(layer_state_t state) {
|
layer_state_t layer_state_set_user(layer_state_t state) {
|
||||||
// Both layers will light up if both kb layers are active
|
// Both layers will light up if both kb layers are active
|
||||||
rgblight_set_layer_state(1, layer_state_cmp(state, 1));
|
rgblight_set_layer_state(1, layer_state_cmp(state, 1));
|
||||||
rgblight_set_layer_state(2, layer_state_cmp(state, 2));
|
rgblight_set_layer_state(2, layer_state_cmp(state, 2));
|
||||||
return state;
|
return state;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool led_update_user(led_t led_state) {
|
bool led_update_user(led_t led_state) {
|
||||||
rgblight_set_layer_state(0, led_state.caps_lock);
|
rgblight_set_layer_state(0, led_state.caps_lock);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
### Lighting layer blink :id=lighting-layer-blink
|
||||||
|
|
||||||
|
By including `#define RGBLIGHT_LAYER_BLINK` in your `config.h` file you can turn a lighting
|
||||||
|
layer on for a specified duration. Once the specified number of milliseconds has elapsed
|
||||||
|
the layer will be turned off. This is useful, e.g., if you want to acknowledge some
|
||||||
|
action (e.g. toggling some setting):
|
||||||
|
|
||||||
|
```c
|
||||||
|
const rgblight_segment_t PROGMEM _yes_layer[] = RGBLIGHT_LAYER_SEGMENTS( {9, 6, HSV_GREEN} );
|
||||||
|
const rgblight_segment_t PROGMEM _no_layer[] = RGBLIGHT_LAYER_SEGMENTS( {9, 6, HSV_RED} );
|
||||||
|
|
||||||
|
const rgblight_segment_t* const PROGMEM _rgb_layers[] =
|
||||||
|
RGBLIGHT_LAYERS_LIST( _yes_layer, _no_layer );
|
||||||
|
|
||||||
|
void keyboard_post_init_user(void) {
|
||||||
|
rgblight_layers = _rgb_layers;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Note we user post_process_record_user because we want the state
|
||||||
|
// after the flag has been flipped...
|
||||||
|
void post_process_record_user(uint16_t keycode, keyrecord_t *record) {
|
||||||
|
switch (keycode) {
|
||||||
|
case DEBUG:
|
||||||
|
rgblight_blink_layer(debug_enable ? 0 : 1, 500);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case NK_TOGG:
|
||||||
|
case NK_ON:
|
||||||
|
case NK_OFF:
|
||||||
|
rgblight_blink_layer(keymap_config.nkro ? 0 : 1, 500);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### Overriding RGB Lighting on/off status
|
||||||
|
|
||||||
|
Normally lighting layers are not shown when RGB Lighting is disabled (e.g. with `RGB_TOG` keycode). If you would like lighting layers to work even when the RGB Lighting is otherwise off, add `#define RGBLIGHT_LAYERS_OVERRIDE_RGB_OFF` to your `config.h`.
|
||||||
|
|
||||||
## Functions
|
## Functions
|
||||||
|
|
||||||
If you need to change your RGB lighting in code, for example in a macro to change the color whenever you switch layers, QMK provides a set of functions to assist you. See [`rgblight.h`](https://github.com/qmk/qmk_firmware/blob/master/quantum/rgblight.h) for the full list, but the most commonly used functions include:
|
If you need to change your RGB lighting in code, for example in a macro to change the color whenever you switch layers, QMK provides a set of functions to assist you. See [`rgblight.h`](https://github.com/qmk/qmk_firmware/blob/master/quantum/rgblight.h) for the full list, but the most commonly used functions include:
|
||||||
@@ -326,12 +384,14 @@ rgblight_sethsv(HSV_GREEN, 2); // led 2
|
|||||||
|`rgblight_set_layer_state(i, is_on)` |Enable or disable lighting layer `i` based on value of `bool is_on` |
|
|`rgblight_set_layer_state(i, is_on)` |Enable or disable lighting layer `i` based on value of `bool is_on` |
|
||||||
|
|
||||||
#### query
|
#### query
|
||||||
|Function |Description |
|
|Function |Description |
|
||||||
|-----------------------|-----------------|
|
|-----------------------|---------------------------|
|
||||||
|`rgblight_get_mode()` |Get current mode |
|
|`rgblight_is_enabled()`|Gets current on/off status |
|
||||||
|`rgblight_get_hue()` |Get current hue |
|
|`rgblight_get_mode()` |Gets current mode |
|
||||||
|`rgblight_get_sat()` |Get current sat |
|
|`rgblight_get_hue()` |Gets current hue |
|
||||||
|`rgblight_get_val()` |Get current val |
|
|`rgblight_get_sat()` |Gets current sat |
|
||||||
|
|`rgblight_get_val()` |Gets current val |
|
||||||
|
|`rgblight_get_speed()` |Gets current speed |
|
||||||
|
|
||||||
## Colors
|
## Colors
|
||||||
|
|
||||||
|
|||||||
@@ -8,9 +8,20 @@ QMK Firmware has a generic implementation that is usable by any board, as well a
|
|||||||
|
|
||||||
For this, we will mostly be talking about the generic implementation used by the Let's Split and other keyboards.
|
For this, we will mostly be talking about the generic implementation used by the Let's Split and other keyboards.
|
||||||
|
|
||||||
!> ARM is not yet supported for Split Keyboards. Progress is being made, but we are not quite there, yet.
|
!> ARM is not yet fully supported for Split Keyboards and has many limitations. Progress is being made, but we have not yet reached 100% feature parity.
|
||||||
|
|
||||||
|
|
||||||
|
## Compatibility Overview
|
||||||
|
|
||||||
|
| Transport | AVR | ARM |
|
||||||
|
|------------------------------|--------------------|--------------------|
|
||||||
|
| ['serial'](serial_driver.md) | :heavy_check_mark: | :white_check_mark: <sup>1</sup> |
|
||||||
|
| I2C | :heavy_check_mark: | |
|
||||||
|
|
||||||
|
Notes:
|
||||||
|
|
||||||
|
1. Both hardware and software limitations are detailed within the [driver documentation](serial_driver.md).
|
||||||
|
|
||||||
## Hardware Configuration
|
## Hardware Configuration
|
||||||
|
|
||||||
This assumes that you're using two Pro Micro-compatible controllers, and are using TRRS jacks to connect to two halves.
|
This assumes that you're using two Pro Micro-compatible controllers, and are using TRRS jacks to connect to two halves.
|
||||||
@@ -79,6 +90,24 @@ You can configure the firmware to read a pin on the controller to determine hand
|
|||||||
|
|
||||||
This will read the specified pin. If it's high, then the controller assumes it is the left hand, and if it's low, it's assumed to be the right side.
|
This will read the specified pin. If it's high, then the controller assumes it is the left hand, and if it's low, it's assumed to be the right side.
|
||||||
|
|
||||||
|
#### Handedness by Matrix Pin
|
||||||
|
|
||||||
|
You can configure the firmware to read key matrix pins on the controller to determine handedness. To do this, add the following to your `config.h` file:
|
||||||
|
|
||||||
|
```c
|
||||||
|
#define SPLIT_HAND_MATRIX_GRID D0, F1
|
||||||
|
```
|
||||||
|
|
||||||
|
The first pin is the output pin and the second is the input pin.
|
||||||
|
|
||||||
|
Some keyboards have unused intersections in the key matrix. This setting uses one of these unused intersections to determine the handness.
|
||||||
|
|
||||||
|
Normally, when a diode is connected to an intersection, it is judged to be left. If you add the following definition, it will be judged to be right.
|
||||||
|
|
||||||
|
```c
|
||||||
|
#define SPLIT_HAND_MATRIX_GRID_LOW_IS_RIGHT
|
||||||
|
```
|
||||||
|
|
||||||
#### Handedness by EEPROM
|
#### Handedness by EEPROM
|
||||||
|
|
||||||
This method sets the keyboard's handedness by setting a flag in the persistent storage (`EEPROM`). This is checked when the controller first starts up, and determines what half the keyboard is, and how to orient the keyboard layout.
|
This method sets the keyboard's handedness by setting a flag in the persistent storage (`EEPROM`). This is checked when the controller first starts up, and determines what half the keyboard is, and how to orient the keyboard layout.
|
||||||
|
|||||||
+15
-15
@@ -1,16 +1,16 @@
|
|||||||
# Stenography in QMK
|
# Stenography in QMK :id=stenography-in-qmk
|
||||||
|
|
||||||
[Stenography](https://en.wikipedia.org/wiki/Stenotype) is a method of writing most often used by court reports, closed-captioning, and real-time transcription for the deaf. In stenography words are chorded syllable by syllable with a mixture of spelling, phonetic, and shortcut (briefs) strokes. Professional stenographers can reach 200-300 WPM without any of the strain usually found in standard typing and with far fewer errors (>99.9% accuracy).
|
[Stenography](https://en.wikipedia.org/wiki/Stenotype) is a method of writing most often used by court reports, closed-captioning, and real-time transcription for the deaf. In stenography words are chorded syllable by syllable with a mixture of spelling, phonetic, and shortcut (briefs) strokes. Professional stenographers can reach 200-300 WPM without any of the strain usually found in standard typing and with far fewer errors (>99.9% accuracy).
|
||||||
|
|
||||||
The [Open Steno Project](http://www.openstenoproject.org/) has built an open-source program called Plover that provides real-time translation of steno strokes into words and commands. It has an established dictionary and supports
|
The [Open Steno Project](http://www.openstenoproject.org/) has built an open-source program called Plover that provides real-time translation of steno strokes into words and commands. It has an established dictionary and supports
|
||||||
|
|
||||||
## Plover with QWERTY Keyboard
|
## Plover with QWERTY Keyboard :id=plover-with-qwerty-keyboard
|
||||||
|
|
||||||
Plover can work with any standard QWERTY keyboard, although it is more efficient if the keyboard supports NKRO (n-key rollover) to allow Plover to see all the pressed keys at once. An example keymap for Plover can be found in `planck/keymaps/default`. Switching to the `PLOVER` layer adjusts the position of the keyboard to support the number bar.
|
Plover can work with any standard QWERTY keyboard, although it is more efficient if the keyboard supports NKRO (n-key rollover) to allow Plover to see all the pressed keys at once. An example keymap for Plover can be found in `planck/keymaps/default`. Switching to the `PLOVER` layer adjusts the position of the keyboard to support the number bar.
|
||||||
|
|
||||||
To use Plover with QMK just enable NKRO and optionally adjust your layout if you have anything other than a standard layout. You may also want to purchase some steno-friendly keycaps to make it easier to hit multiple keys.
|
To use Plover with QMK just enable NKRO and optionally adjust your layout if you have anything other than a standard layout. You may also want to purchase some steno-friendly keycaps to make it easier to hit multiple keys.
|
||||||
|
|
||||||
## Plover with Steno Protocol
|
## Plover with Steno Protocol :id=plover-with-steno-protocol
|
||||||
|
|
||||||
Plover also understands the language of several steno machines. QMK can speak a couple of these languages, TX Bolt and GeminiPR. An example layout can be found in `planck/keymaps/steno`.
|
Plover also understands the language of several steno machines. QMK can speak a couple of these languages, TX Bolt and GeminiPR. An example layout can be found in `planck/keymaps/steno`.
|
||||||
|
|
||||||
@@ -20,26 +20,26 @@ In this mode Plover expects to speak with a steno machine over a serial port so
|
|||||||
|
|
||||||
> Note: Due to hardware limitations you may not be able to run both a virtual serial port and mouse emulation at the same time.
|
> Note: Due to hardware limitations you may not be able to run both a virtual serial port and mouse emulation at the same time.
|
||||||
|
|
||||||
### TX Bolt
|
### TX Bolt :id=tx-bolt
|
||||||
|
|
||||||
TX Bolt communicates the status of 24 keys over a very simple protocol in variable-sized (1-5 byte) packets.
|
TX Bolt communicates the status of 24 keys over a very simple protocol in variable-sized (1-5 byte) packets.
|
||||||
|
|
||||||
### GeminiPR
|
### GeminiPR :id=geminipr
|
||||||
|
|
||||||
GeminiPR encodes 42 keys into a 6-byte packet. While TX Bolt contains everything that is necessary for standard stenography, GeminiPR opens up many more options, including supporting non-English theories.
|
GeminiPR encodes 42 keys into a 6-byte packet. While TX Bolt contains everything that is necessary for standard stenography, GeminiPR opens up many more options, including supporting non-English theories.
|
||||||
|
|
||||||
## Configuring QMK for Steno
|
## Configuring QMK for Steno :id=configuring-qmk-for-steno
|
||||||
|
|
||||||
Firstly, enable steno in your keymap's Makefile. You may also need disable mousekeys, extra keys, or another USB endpoint to prevent conflicts. The builtin USB stack for some processors only supports a certain number of USB endpoints and the virtual serial port needed for steno fills 3 of them.
|
Firstly, enable steno in your keymap's Makefile. You may also need disable mousekeys, extra keys, or another USB endpoint to prevent conflicts. The builtin USB stack for some processors only supports a certain number of USB endpoints and the virtual serial port needed for steno fills 3 of them.
|
||||||
|
|
||||||
```Makefile
|
```makefile
|
||||||
STENO_ENABLE = yes
|
STENO_ENABLE = yes
|
||||||
MOUSEKEY_ENABLE = no
|
MOUSEKEY_ENABLE = no
|
||||||
```
|
```
|
||||||
|
|
||||||
In your keymap create a new layer for Plover. You will need to include `keymap_steno.h`. See `planck/keymaps/steno/keymap.c` for an example. Remember to create a key to switch to the layer as well as a key for exiting the layer. If you would like to switch modes on the fly you can use the keycodes `QK_STENO_BOLT` and `QK_STENO_GEMINI`. If you only want to use one of the protocols you may set it up in your initialization function:
|
In your keymap create a new layer for Plover. You will need to include `keymap_steno.h`. See `planck/keymaps/steno/keymap.c` for an example. Remember to create a key to switch to the layer as well as a key for exiting the layer. If you would like to switch modes on the fly you can use the keycodes `QK_STENO_BOLT` and `QK_STENO_GEMINI`. If you only want to use one of the protocols you may set it up in your initialization function:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
void matrix_init_user() {
|
void matrix_init_user() {
|
||||||
steno_set_mode(STENO_MODE_GEMINI); // or STENO_MODE_BOLT
|
steno_set_mode(STENO_MODE_GEMINI); // or STENO_MODE_BOLT
|
||||||
}
|
}
|
||||||
@@ -49,37 +49,37 @@ Once you have your keyboard flashed launch Plover. Click the 'Configure...' butt
|
|||||||
|
|
||||||
On the display tab click 'Open stroke display'. With Plover disabled you should be able to hit keys on your keyboard and see them show up in the stroke display window. Use this to make sure you have set up your keymap correctly. You are now ready to steno!
|
On the display tab click 'Open stroke display'. With Plover disabled you should be able to hit keys on your keyboard and see them show up in the stroke display window. Use this to make sure you have set up your keymap correctly. You are now ready to steno!
|
||||||
|
|
||||||
## Learning Stenography
|
## Learning Stenography :id=learning-stenography
|
||||||
|
|
||||||
* [Learn Plover!](https://sites.google.com/site/ploverdoc/)
|
* [Learn Plover!](https://sites.google.com/site/learnplover/)
|
||||||
* [QWERTY Steno](http://qwertysteno.com/Home/)
|
* [QWERTY Steno](http://qwertysteno.com/Home/)
|
||||||
* [Steno Jig](https://joshuagrams.github.io/steno-jig/)
|
* [Steno Jig](https://joshuagrams.github.io/steno-jig/)
|
||||||
* More resources at the Plover [Learning Stenography](https://github.com/openstenoproject/plover/wiki/Learning-Stenography) wiki
|
* More resources at the Plover [Learning Stenography](https://github.com/openstenoproject/plover/wiki/Learning-Stenography) wiki
|
||||||
|
|
||||||
## Interfacing with the code
|
## Interfacing with the code :id=interfacing-with-the-code
|
||||||
|
|
||||||
The steno code has three interceptible hooks. If you define these functions, they will be called at certain points in processing; if they return true, processing continues, otherwise it's assumed you handled things.
|
The steno code has three interceptible hooks. If you define these functions, they will be called at certain points in processing; if they return true, processing continues, otherwise it's assumed you handled things.
|
||||||
|
|
||||||
```C
|
```c
|
||||||
bool send_steno_chord_user(steno_mode_t mode, uint8_t chord[6]);
|
bool send_steno_chord_user(steno_mode_t mode, uint8_t chord[6]);
|
||||||
```
|
```
|
||||||
|
|
||||||
This function is called when a chord is about to be sent. Mode will be one of `STENO_MODE_BOLT` or `STENO_MODE_GEMINI`. This represents the actual chord that would be sent via whichever protocol. You can modify the chord provided to alter what gets sent. Remember to return true if you want the regular sending process to happen.
|
This function is called when a chord is about to be sent. Mode will be one of `STENO_MODE_BOLT` or `STENO_MODE_GEMINI`. This represents the actual chord that would be sent via whichever protocol. You can modify the chord provided to alter what gets sent. Remember to return true if you want the regular sending process to happen.
|
||||||
|
|
||||||
```C
|
```c
|
||||||
bool process_steno_user(uint16_t keycode, keyrecord_t *record) { return true; }
|
bool process_steno_user(uint16_t keycode, keyrecord_t *record) { return true; }
|
||||||
```
|
```
|
||||||
|
|
||||||
This function is called when a keypress has come in, before it is processed. The keycode should be one of `QK_STENO_BOLT`, `QK_STENO_GEMINI`, or one of the `STN_*` key values.
|
This function is called when a keypress has come in, before it is processed. The keycode should be one of `QK_STENO_BOLT`, `QK_STENO_GEMINI`, or one of the `STN_*` key values.
|
||||||
|
|
||||||
```C
|
```c
|
||||||
bool postprocess_steno_user(uint16_t keycode, keyrecord_t *record, steno_mode_t mode, uint8_t chord[6], int8_t pressed);
|
bool postprocess_steno_user(uint16_t keycode, keyrecord_t *record, steno_mode_t mode, uint8_t chord[6], int8_t pressed);
|
||||||
```
|
```
|
||||||
|
|
||||||
This function is called after a key has been processed, but before any decision about whether or not to send a chord. If `IS_PRESSED(record->event)` is false, and `pressed` is 0 or 1, the chord will be sent shortly, but has not yet been sent. This is where to put hooks for things like, say, live displays of steno chords or keys.
|
This function is called after a key has been processed, but before any decision about whether or not to send a chord. If `IS_PRESSED(record->event)` is false, and `pressed` is 0 or 1, the chord will be sent shortly, but has not yet been sent. This is where to put hooks for things like, say, live displays of steno chords or keys.
|
||||||
|
|
||||||
|
|
||||||
## Keycode Reference
|
## Keycode Reference :id=keycode-reference
|
||||||
|
|
||||||
As defined in `keymap_steno.h`.
|
As defined in `keymap_steno.h`.
|
||||||
|
|
||||||
|
|||||||
@@ -28,3 +28,4 @@ Note that the array indices are reversed same as the matrix and the values are o
|
|||||||
|`SH_MOFF` |Momentarily turns off swap. |
|
|`SH_MOFF` |Momentarily turns off swap. |
|
||||||
|`SH_TG` |Toggles swap on and off with every key press. |
|
|`SH_TG` |Toggles swap on and off with every key press. |
|
||||||
|`SH_TT` |Toggles with a tap; momentary when held. |
|
|`SH_TT` |Toggles with a tap; momentary when held. |
|
||||||
|
|`SH_OS` |One shot swap hands: toggles while pressed or until next key press. |
|
||||||
+261
-273
@@ -1,31 +1,24 @@
|
|||||||
# Tap Dance: A Single Key Can Do 3, 5, or 100 Different Things
|
# Tap Dance: A Single Key Can Do 3, 5, or 100 Different Things
|
||||||
|
|
||||||
## Introduction
|
## Introduction :id=introduction
|
||||||
|
|
||||||
Hit the semicolon key once, send a semicolon. Hit it twice, rapidly -- send a colon. Hit it three times, and your keyboard's LEDs do a wild dance. That's just one example of what Tap Dance can do. It's one of the nicest community-contributed features in the firmware, conceived and created by [algernon](https://github.com/algernon) in [#451](https://github.com/qmk/qmk_firmware/pull/451). Here's how algernon describes the feature:
|
Hit the semicolon key once, send a semicolon. Hit it twice, rapidly -- send a colon. Hit it three times, and your keyboard's LEDs do a wild dance. That's just one example of what Tap Dance can do. It's one of the nicest community-contributed features in the firmware, conceived and created by [algernon](https://github.com/algernon) in [#451](https://github.com/qmk/qmk_firmware/pull/451). Here's how algernon describes the feature:
|
||||||
|
|
||||||
With this feature one can specify keys that behave differently, based on the amount of times they have been tapped, and when interrupted, they get handled before the interrupter.
|
With this feature one can specify keys that behave differently, based on the amount of times they have been tapped, and when interrupted, they get handled before the interrupter.
|
||||||
|
|
||||||
## Explanatory Comparison with `ACTION_FUNCTION_TAP`
|
## How to Use Tap Dance :id=how-to-use
|
||||||
`ACTION_FUNCTION_TAP` can offer similar functionality to Tap Dance, but it's worth noting some important differences. To do this, let's explore a certain setup! We want one key to send `Space` on single-tap, but `Enter` on double-tap.
|
|
||||||
|
|
||||||
With `ACTION_FUNCTION_TAP`, it is quite a rain-dance to set this up, and has the problem that when the sequence is interrupted, the interrupting key will be sent first. Thus, `SPC a` will result in `a SPC` being sent, if `SPC` and `a` are both typed within `TAPPING_TERM`. With the Tap Dance feature, that'll come out correctly as `SPC a` (even if both `SPC` and `a` are typed within the `TAPPING_TERM`.
|
First, you will need `TAP_DANCE_ENABLE = yes` in your `rules.mk`, because the feature is disabled by default. This adds a little less than 1k to the firmware size.
|
||||||
|
|
||||||
To achieve this correct handling of interrupts, the implementation of Tap Dance hooks into two parts of the system: `process_record_quantum()`, and the matrix scan. These two parts are explained below, but for now the point to note is that we need the latter to be able to time out a tap sequence even when a key is not being pressed. That way, `SPC` alone will time out and register after `TAPPING_TERM` time.
|
|
||||||
|
|
||||||
## How to Use Tap Dance
|
|
||||||
But enough of the generalities; lets look at how to actually use Tap Dance!
|
|
||||||
|
|
||||||
First, you will need `TAP_DANCE_ENABLE=yes` in your `rules.mk`, because the feature is disabled by default. This adds a little less than 1k to the firmware size.
|
|
||||||
|
|
||||||
Optionally, you might want to set a custom `TAPPING_TERM` time by adding something like this in you `config.h`:
|
Optionally, you might want to set a custom `TAPPING_TERM` time by adding something like this in you `config.h`:
|
||||||
|
|
||||||
```
|
```c
|
||||||
#define TAPPING_TERM 175
|
#define TAPPING_TERM 175
|
||||||
```
|
```
|
||||||
|
|
||||||
The `TAPPING_TERM` time is the maximum time allowed between taps of your Tap Dance key, and is measured in milliseconds. For example, if you used the above `#define` statement and set up a Tap Dance key that sends `Space` on single-tap and `Enter` on double-tap, then this key will send `ENT` only if you tap this key twice in less than 175ms. If you tap the key, wait more than 175ms, and tap the key again you'll end up sending `SPC SPC` instead.
|
The `TAPPING_TERM` time is the maximum time allowed between taps of your Tap Dance key, and is measured in milliseconds. For example, if you used the above `#define` statement and set up a Tap Dance key that sends `Space` on single-tap and `Enter` on double-tap, then this key will send `ENT` only if you tap this key twice in less than 175ms. If you tap the key, wait more than 175ms, and tap the key again you'll end up sending `SPC SPC` instead.
|
||||||
|
|
||||||
Next, you will want to define some tap-dance keys, which is easiest to do with the `TD()` macro, that - similar to `F()` - takes a number, which will later be used as an index into the `tap_dance_actions` array.
|
Next, you will want to define some tap-dance keys, which is easiest to do with the `TD()` macro, that takes a number which will later be used as an index into the `tap_dance_actions` array.
|
||||||
|
|
||||||
After this, you'll want to use the `tap_dance_actions` array to specify what actions shall be taken when a tap-dance key is in action. Currently, there are five possible options:
|
After this, you'll want to use the `tap_dance_actions` array to specify what actions shall be taken when a tap-dance key is in action. Currently, there are five possible options:
|
||||||
|
|
||||||
@@ -43,11 +36,12 @@ The first option is enough for a lot of cases, that just want dual roles. For ex
|
|||||||
|
|
||||||
Similar to the first option, the second option is good for simple layer-switching cases.
|
Similar to the first option, the second option is good for simple layer-switching cases.
|
||||||
|
|
||||||
For more complicated cases, use the third or fourth options (examples of each are listed below).
|
For more complicated cases, use the third or fourth options (examples of each are listed below).
|
||||||
|
|
||||||
Finally, the fifth option is particularly useful if your non-Tap-Dance keys start behaving weirdly after adding the code for your Tap Dance keys. The likely problem is that you changed the `TAPPING_TERM` time to make your Tap Dance keys easier for you to use, and that this has changed the way your other keys handle interrupts.
|
Finally, the fifth option is particularly useful if your non-Tap-Dance keys start behaving weirdly after adding the code for your Tap Dance keys. The likely problem is that you changed the `TAPPING_TERM` time to make your Tap Dance keys easier for you to use, and that this has changed the way your other keys handle interrupts.
|
||||||
|
|
||||||
## Implementation Details
|
## Implementation Details :id=implementation
|
||||||
|
|
||||||
Well, that's the bulk of it! You should now be able to work through the examples below, and to develop your own Tap Dance functionality. But if you want a deeper understanding of what's going on behind the scenes, then read on for the explanation of how it all works!
|
Well, that's the bulk of it! You should now be able to work through the examples below, and to develop your own Tap Dance functionality. But if you want a deeper understanding of what's going on behind the scenes, then read on for the explanation of how it all works!
|
||||||
|
|
||||||
The main entry point is `process_tap_dance()`, called from `process_record_quantum()`, which is run for every keypress, and our handler gets to run early. This function checks whether the key pressed is a tap-dance key. If it is not, and a tap-dance was in action, we handle that first, and enqueue the newly pressed key. If it is a tap-dance key, then we check if it is the same as the already active one (if there's one active, that is). If it is not, we fire off the old one first, then register the new one. If it was the same, we increment the counter and reset the timer.
|
The main entry point is `process_tap_dance()`, called from `process_record_quantum()`, which is run for every keypress, and our handler gets to run early. This function checks whether the key pressed is a tap-dance key. If it is not, and a tap-dance was in action, we handle that first, and enqueue the newly pressed key. If it is a tap-dance key, then we check if it is the same as the already active one (if there's one active, that is). If it is not, we fire off the old one first, then register the new one. If it was the same, we increment the counter and reset the timer.
|
||||||
@@ -58,9 +52,9 @@ Our next stop is `matrix_scan_tap_dance()`. This handles the timeout of tap-danc
|
|||||||
|
|
||||||
For the sake of flexibility, tap-dance actions can be either a pair of keycodes, or a user function. The latter allows one to handle higher tap counts, or do extra things, like blink the LEDs, fiddle with the backlighting, and so on. This is accomplished by using an union, and some clever macros.
|
For the sake of flexibility, tap-dance actions can be either a pair of keycodes, or a user function. The latter allows one to handle higher tap counts, or do extra things, like blink the LEDs, fiddle with the backlighting, and so on. This is accomplished by using an union, and some clever macros.
|
||||||
|
|
||||||
# Examples
|
## Examples :id=examples
|
||||||
|
|
||||||
## Simple Example
|
### Simple Example :id=simple-example
|
||||||
|
|
||||||
Here's a simple example for a single definition:
|
Here's a simple example for a single definition:
|
||||||
|
|
||||||
@@ -69,23 +63,26 @@ Here's a simple example for a single definition:
|
|||||||
3. In your `keymap.c` file, define the variables and definitions, then add to your keymap:
|
3. In your `keymap.c` file, define the variables and definitions, then add to your keymap:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
//Tap Dance Declarations
|
// Tap Dance declarations
|
||||||
enum {
|
enum {
|
||||||
TD_ESC_CAPS = 0
|
TD_ESC_CAPS,
|
||||||
};
|
};
|
||||||
|
|
||||||
//Tap Dance Definitions
|
// Tap Dance definitions
|
||||||
qk_tap_dance_action_t tap_dance_actions[] = {
|
qk_tap_dance_action_t tap_dance_actions[] = {
|
||||||
//Tap once for Esc, twice for Caps Lock
|
// Tap once for Escape, twice for Caps Lock
|
||||||
[TD_ESC_CAPS] = ACTION_TAP_DANCE_DOUBLE(KC_ESC, KC_CAPS)
|
[TD_ESC_CAPS] = ACTION_TAP_DANCE_DOUBLE(KC_ESC, KC_CAPS),
|
||||||
// Other declarations would go here, separated by commas, if you have them
|
|
||||||
};
|
};
|
||||||
|
|
||||||
//In Layer declaration, add tap dance item in place of a key code
|
// Add tap dance item in place of a key code
|
||||||
TD(TD_ESC_CAPS)
|
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
|
||||||
|
// ...
|
||||||
|
TD(TD_ESC_CAPS)
|
||||||
|
// ...
|
||||||
|
};
|
||||||
```
|
```
|
||||||
|
|
||||||
## Complex Examples
|
### Complex Examples :id=complex-examples
|
||||||
|
|
||||||
This section details several complex tap dance examples.
|
This section details several complex tap dance examples.
|
||||||
All the enums used in the examples are declared like this:
|
All the enums used in the examples are declared like this:
|
||||||
@@ -93,104 +90,105 @@ All the enums used in the examples are declared like this:
|
|||||||
```c
|
```c
|
||||||
// Enums defined for all examples:
|
// Enums defined for all examples:
|
||||||
enum {
|
enum {
|
||||||
CT_SE = 0,
|
CT_SE,
|
||||||
CT_CLN,
|
CT_CLN,
|
||||||
CT_EGG,
|
CT_EGG,
|
||||||
CT_FLSH,
|
CT_FLSH,
|
||||||
X_TAP_DANCE
|
X_TAP_DANCE
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
### Example 1: Send `:` on Single Tap, `;` on Double Tap
|
|
||||||
|
#### Example 1: Send `:` on Single Tap, `;` on Double Tap :id=example-1
|
||||||
|
|
||||||
```c
|
```c
|
||||||
void dance_cln_finished (qk_tap_dance_state_t *state, void *user_data) {
|
void dance_cln_finished(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
if (state->count == 1) {
|
if (state->count == 1) {
|
||||||
register_code (KC_RSFT);
|
register_code16(KC_COLN);
|
||||||
register_code (KC_SCLN);
|
} else {
|
||||||
} else {
|
register_code(KC_SCLN);
|
||||||
register_code (KC_SCLN);
|
}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void dance_cln_reset (qk_tap_dance_state_t *state, void *user_data) {
|
void dance_cln_reset(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
if (state->count == 1) {
|
if (state->count == 1) {
|
||||||
unregister_code (KC_RSFT);
|
unregister_code16(KC_COLN);
|
||||||
unregister_code (KC_SCLN);
|
} else {
|
||||||
} else {
|
unregister_code(KC_SCLN);
|
||||||
unregister_code (KC_SCLN);
|
}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//All tap dance functions would go here. Only showing this one.
|
// All tap dance functions would go here. Only showing this one.
|
||||||
qk_tap_dance_action_t tap_dance_actions[] = {
|
qk_tap_dance_action_t tap_dance_actions[] = {
|
||||||
[CT_CLN] = ACTION_TAP_DANCE_FN_ADVANCED (NULL, dance_cln_finished, dance_cln_reset)
|
[CT_CLN] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, dance_cln_finished, dance_cln_reset),
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
### Example 2: Send "Safety Dance!" After 100 Taps
|
|
||||||
|
#### Example 2: Send "Safety Dance!" After 100 Taps :id=example-2
|
||||||
|
|
||||||
```c
|
```c
|
||||||
void dance_egg (qk_tap_dance_state_t *state, void *user_data) {
|
void dance_egg(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
if (state->count >= 100) {
|
if (state->count >= 100) {
|
||||||
SEND_STRING ("Safety dance!");
|
SEND_STRING("Safety dance!");
|
||||||
reset_tap_dance (state);
|
reset_tap_dance(state);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
qk_tap_dance_action_t tap_dance_actions[] = {
|
qk_tap_dance_action_t tap_dance_actions[] = {
|
||||||
[CT_EGG] = ACTION_TAP_DANCE_FN (dance_egg)
|
[CT_EGG] = ACTION_TAP_DANCE_FN(dance_egg),
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
|
|
||||||
### Example 3: Turn LED Lights On Then Off, One at a Time
|
#### Example 3: Turn LED Lights On Then Off, One at a Time :id=example-3
|
||||||
|
|
||||||
```c
|
```c
|
||||||
// on each tap, light up one led, from right to left
|
// On each tap, light up one LED, from right to left
|
||||||
// on the forth tap, turn them off from right to left
|
// On the fourth tap, turn them off from right to left
|
||||||
void dance_flsh_each(qk_tap_dance_state_t *state, void *user_data) {
|
void dance_flsh_each(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
switch (state->count) {
|
switch (state->count) {
|
||||||
case 1:
|
case 1:
|
||||||
ergodox_right_led_3_on();
|
ergodox_right_led_3_on();
|
||||||
break;
|
break;
|
||||||
case 2:
|
case 2:
|
||||||
ergodox_right_led_2_on();
|
ergodox_right_led_2_on();
|
||||||
break;
|
break;
|
||||||
case 3:
|
case 3:
|
||||||
ergodox_right_led_1_on();
|
ergodox_right_led_1_on();
|
||||||
break;
|
break;
|
||||||
case 4:
|
case 4:
|
||||||
ergodox_right_led_3_off();
|
ergodox_right_led_3_off();
|
||||||
_delay_ms(50);
|
wait_ms(50);
|
||||||
ergodox_right_led_2_off();
|
ergodox_right_led_2_off();
|
||||||
_delay_ms(50);
|
wait_ms(50);
|
||||||
ergodox_right_led_1_off();
|
ergodox_right_led_1_off();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// on the fourth tap, set the keyboard on flash state
|
// On the fourth tap, set the keyboard on flash state
|
||||||
void dance_flsh_finished(qk_tap_dance_state_t *state, void *user_data) {
|
void dance_flsh_finished(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
if (state->count >= 4) {
|
if (state->count >= 4) {
|
||||||
reset_keyboard();
|
reset_keyboard();
|
||||||
reset_tap_dance(state);
|
}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// if the flash state didn't happen, then turn off LEDs, left to right
|
// If the flash state didn't happen, then turn off LEDs, left to right
|
||||||
void dance_flsh_reset(qk_tap_dance_state_t *state, void *user_data) {
|
void dance_flsh_reset(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
ergodox_right_led_1_off();
|
ergodox_right_led_1_off();
|
||||||
_delay_ms(50);
|
wait_ms(50);
|
||||||
ergodox_right_led_2_off();
|
ergodox_right_led_2_off();
|
||||||
_delay_ms(50);
|
wait_ms(50);
|
||||||
ergodox_right_led_3_off();
|
ergodox_right_led_3_off();
|
||||||
}
|
}
|
||||||
|
|
||||||
//All tap dances now put together. Example 3 is "CT_FLASH"
|
// All tap dances now put together. Example 3 is "CT_FLASH"
|
||||||
qk_tap_dance_action_t tap_dance_actions[] = {
|
qk_tap_dance_action_t tap_dance_actions[] = {
|
||||||
[CT_SE] = ACTION_TAP_DANCE_DOUBLE (KC_SPC, KC_ENT)
|
[CT_SE] = ACTION_TAP_DANCE_DOUBLE(KC_SPC, KC_ENT),
|
||||||
,[CT_CLN] = ACTION_TAP_DANCE_FN_ADVANCED (NULL, dance_cln_finished, dance_cln_reset)
|
[CT_CLN] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, dance_cln_finished, dance_cln_reset),
|
||||||
,[CT_EGG] = ACTION_TAP_DANCE_FN (dance_egg)
|
[CT_EGG] = ACTION_TAP_DANCE_FN(dance_egg),
|
||||||
,[CT_FLSH] = ACTION_TAP_DANCE_FN_ADVANCED (dance_flsh_each, dance_flsh_finished, dance_flsh_reset)
|
[CT_FLSH] = ACTION_TAP_DANCE_FN_ADVANCED(dance_flsh_each, dance_flsh_finished, dance_flsh_reset)
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
|
|
||||||
### Example 4: 'Quad Function Tap-Dance'
|
#### Example 4: 'Quad Function Tap-Dance' :id=example-4
|
||||||
|
|
||||||
By [DanielGGordon](https://github.com/danielggordon)
|
By [DanielGGordon](https://github.com/danielggordon)
|
||||||
|
|
||||||
@@ -201,40 +199,37 @@ Below is a specific example:
|
|||||||
* Double Tap = Send `Escape`
|
* Double Tap = Send `Escape`
|
||||||
* Double Tap and Hold = Send `Alt`
|
* Double Tap and Hold = Send `Alt`
|
||||||
|
|
||||||
## Setup
|
|
||||||
|
|
||||||
You will need a few things that can be used for 'Quad Function Tap-Dance'.
|
You will need a few things that can be used for 'Quad Function Tap-Dance'.
|
||||||
|
|
||||||
You'll need to add these to the top of your `keymap.c` file, before your keymap.
|
You'll need to add these to the top of your `keymap.c` file, before your keymap.
|
||||||
|
|
||||||
```c
|
```c
|
||||||
typedef struct {
|
typedef struct {
|
||||||
bool is_press_action;
|
bool is_press_action;
|
||||||
int state;
|
uint8_t state;
|
||||||
} tap;
|
} tap;
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
SINGLE_TAP = 1,
|
SINGLE_TAP = 1,
|
||||||
SINGLE_HOLD = 2,
|
SINGLE_HOLD,
|
||||||
DOUBLE_TAP = 3,
|
DOUBLE_TAP,
|
||||||
DOUBLE_HOLD = 4,
|
DOUBLE_HOLD,
|
||||||
DOUBLE_SINGLE_TAP = 5, //send two single taps
|
DOUBLE_SINGLE_TAP, // Send two single taps
|
||||||
TRIPLE_TAP = 6,
|
TRIPLE_TAP,
|
||||||
TRIPLE_HOLD = 7
|
TRIPLE_HOLD
|
||||||
};
|
};
|
||||||
|
|
||||||
//Tap dance enums
|
// Tap dance enums
|
||||||
enum {
|
enum {
|
||||||
X_CTL = 0,
|
X_CTL,
|
||||||
SOME_OTHER_DANCE
|
SOME_OTHER_DANCE
|
||||||
};
|
};
|
||||||
|
|
||||||
int cur_dance (qk_tap_dance_state_t *state);
|
uint8_t cur_dance(qk_tap_dance_state_t *state);
|
||||||
|
|
||||||
//for the x tap dance. Put it here so it can be used in any keymap
|
|
||||||
void x_finished (qk_tap_dance_state_t *state, void *user_data);
|
|
||||||
void x_reset (qk_tap_dance_state_t *state, void *user_data);
|
|
||||||
|
|
||||||
|
// For the x tap dance. Put it here so it can be used in any keymap
|
||||||
|
void x_finished(qk_tap_dance_state_t *state, void *user_data);
|
||||||
|
void x_reset(qk_tap_dance_state_t *state, void *user_data);
|
||||||
```
|
```
|
||||||
|
|
||||||
Now, at the bottom of your `keymap.c` file, you'll need to add the following:
|
Now, at the bottom of your `keymap.c` file, you'll need to add the following:
|
||||||
@@ -267,65 +262,62 @@ Now, at the bottom of your `keymap.c` file, you'll need to add the following:
|
|||||||
* For the third point, there does exist the 'DOUBLE_SINGLE_TAP', however this is not fully tested
|
* For the third point, there does exist the 'DOUBLE_SINGLE_TAP', however this is not fully tested
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
int cur_dance (qk_tap_dance_state_t *state) {
|
uint8_t cur_dance(qk_tap_dance_state_t *state) {
|
||||||
if (state->count == 1) {
|
if (state->count == 1) {
|
||||||
if (state->interrupted || !state->pressed) return SINGLE_TAP;
|
if (state->interrupted || !state->pressed) return SINGLE_TAP;
|
||||||
//key has not been interrupted, but they key is still held. Means you want to send a 'HOLD'.
|
// Key has not been interrupted, but the key is still held. Means you want to send a 'HOLD'.
|
||||||
else return SINGLE_HOLD;
|
else return SINGLE_HOLD;
|
||||||
}
|
} else if (state->count == 2) {
|
||||||
else if (state->count == 2) {
|
// DOUBLE_SINGLE_TAP is to distinguish between typing "pepper", and actually wanting a double tap
|
||||||
/*
|
// action when hitting 'pp'. Suggested use case for this return value is when you want to send two
|
||||||
* DOUBLE_SINGLE_TAP is to distinguish between typing "pepper", and actually wanting a double tap
|
// keystrokes of the key, and not the 'double tap' action/macro.
|
||||||
* action when hitting 'pp'. Suggested use case for this return value is when you want to send two
|
if (state->interrupted) return DOUBLE_SINGLE_TAP;
|
||||||
* keystrokes of the key, and not the 'double tap' action/macro.
|
else if (state->pressed) return DOUBLE_HOLD;
|
||||||
*/
|
else return DOUBLE_TAP;
|
||||||
if (state->interrupted) return DOUBLE_SINGLE_TAP;
|
}
|
||||||
else if (state->pressed) return DOUBLE_HOLD;
|
|
||||||
else return DOUBLE_TAP;
|
// Assumes no one is trying to type the same letter three times (at least not quickly).
|
||||||
}
|
// If your tap dance key is 'KC_W', and you want to type "www." quickly - then you will need to add
|
||||||
//Assumes no one is trying to type the same letter three times (at least not quickly).
|
// an exception here to return a 'TRIPLE_SINGLE_TAP', and define that enum just like 'DOUBLE_SINGLE_TAP'
|
||||||
//If your tap dance key is 'KC_W', and you want to type "www." quickly - then you will need to add
|
if (state->count == 3) {
|
||||||
//an exception here to return a 'TRIPLE_SINGLE_TAP', and define that enum just like 'DOUBLE_SINGLE_TAP'
|
if (state->interrupted || !state->pressed) return TRIPLE_TAP;
|
||||||
if (state->count == 3) {
|
else return TRIPLE_HOLD;
|
||||||
if (state->interrupted || !state->pressed) return TRIPLE_TAP;
|
} else return 8; // Magic number. At some point this method will expand to work for more presses
|
||||||
else return TRIPLE_HOLD;
|
|
||||||
}
|
|
||||||
else return 8; //magic number. At some point this method will expand to work for more presses
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//instanalize an instance of 'tap' for the 'x' tap dance.
|
// Create an instance of 'tap' for the 'x' tap dance.
|
||||||
static tap xtap_state = {
|
static tap xtap_state = {
|
||||||
.is_press_action = true,
|
.is_press_action = true,
|
||||||
.state = 0
|
.state = 0
|
||||||
};
|
};
|
||||||
|
|
||||||
void x_finished (qk_tap_dance_state_t *state, void *user_data) {
|
void x_finished(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
xtap_state.state = cur_dance(state);
|
xtap_state.state = cur_dance(state);
|
||||||
switch (xtap_state.state) {
|
switch (xtap_state.state) {
|
||||||
case SINGLE_TAP: register_code(KC_X); break;
|
case SINGLE_TAP: register_code(KC_X); break;
|
||||||
case SINGLE_HOLD: register_code(KC_LCTRL); break;
|
case SINGLE_HOLD: register_code(KC_LCTRL); break;
|
||||||
case DOUBLE_TAP: register_code(KC_ESC); break;
|
case DOUBLE_TAP: register_code(KC_ESC); break;
|
||||||
case DOUBLE_HOLD: register_code(KC_LALT); break;
|
case DOUBLE_HOLD: register_code(KC_LALT); break;
|
||||||
case DOUBLE_SINGLE_TAP: register_code(KC_X); unregister_code(KC_X); register_code(KC_X);
|
// Last case is for fast typing. Assuming your key is `f`:
|
||||||
//Last case is for fast typing. Assuming your key is `f`:
|
// For example, when typing the word `buffer`, and you want to make sure that you send `ff` and not `Esc`.
|
||||||
//For example, when typing the word `buffer`, and you want to make sure that you send `ff` and not `Esc`.
|
// In order to type `ff` when typing fast, the next character will have to be hit within the `TAPPING_TERM`, which by default is 200ms.
|
||||||
//In order to type `ff` when typing fast, the next character will have to be hit within the `TAPPING_TERM`, which by default is 200ms.
|
case DOUBLE_SINGLE_TAP: tap_code(KC_X); register_code(KC_X);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void x_reset (qk_tap_dance_state_t *state, void *user_data) {
|
void x_reset(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
switch (xtap_state.state) {
|
switch (xtap_state.state) {
|
||||||
case SINGLE_TAP: unregister_code(KC_X); break;
|
case SINGLE_TAP: unregister_code(KC_X); break;
|
||||||
case SINGLE_HOLD: unregister_code(KC_LCTRL); break;
|
case SINGLE_HOLD: unregister_code(KC_LCTRL); break;
|
||||||
case DOUBLE_TAP: unregister_code(KC_ESC); break;
|
case DOUBLE_TAP: unregister_code(KC_ESC); break;
|
||||||
case DOUBLE_HOLD: unregister_code(KC_LALT);
|
case DOUBLE_HOLD: unregister_code(KC_LALT);
|
||||||
case DOUBLE_SINGLE_TAP: unregister_code(KC_X);
|
case DOUBLE_SINGLE_TAP: unregister_code(KC_X);
|
||||||
}
|
}
|
||||||
xtap_state.state = 0;
|
xtap_state.state = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
qk_tap_dance_action_t tap_dance_actions[] = {
|
qk_tap_dance_action_t tap_dance_actions[] = {
|
||||||
[X_CTL] = ACTION_TAP_DANCE_FN_ADVANCED(NULL,x_finished, x_reset)
|
[X_CTL] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, x_finished, x_reset)
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -335,90 +327,91 @@ If you want to implement this in your userspace, then you may want to check out
|
|||||||
|
|
||||||
> In this configuration "hold" takes place **after** tap dance timeout (see `ACTION_TAP_DANCE_FN_ADVANCED_TIME`). To achieve instant hold, remove `state->interrupted` checks in conditions. As a result you may use comfortable longer tapping periods to have more time for taps and not to wait too long for holds (try starting with doubled `TAPPING_TERM`).
|
> In this configuration "hold" takes place **after** tap dance timeout (see `ACTION_TAP_DANCE_FN_ADVANCED_TIME`). To achieve instant hold, remove `state->interrupted` checks in conditions. As a result you may use comfortable longer tapping periods to have more time for taps and not to wait too long for holds (try starting with doubled `TAPPING_TERM`).
|
||||||
|
|
||||||
### Example 5: Using tap dance for advanced mod-tap and layer-tap keys :id=example-5-using-tap-dance-for-advanced-mod-tap-and-layer-tap-keys
|
#### Example 5: Using tap dance for advanced mod-tap and layer-tap keys :id=example-5
|
||||||
|
|
||||||
Tap dance can be used to emulate `MT()` and `LT()` behavior when the tapped code is not a basic keycode. This is useful to send tapped keycodes that normally require `Shift`, such as parentheses or curly braces—or other modified keycodes, such as `Control + X`.
|
Tap dance can be used to emulate `MT()` and `LT()` behavior when the tapped code is not a basic keycode. This is useful to send tapped keycodes that normally require `Shift`, such as parentheses or curly braces—or other modified keycodes, such as `Control + X`.
|
||||||
|
|
||||||
Below your layers and custom keycodes, add the following:
|
Below your layers and custom keycodes, add the following:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
// tapdance keycodes
|
// Tap Dance keycodes
|
||||||
enum td_keycodes {
|
enum td_keycodes {
|
||||||
ALT_LP // Our example key: `LALT` when held, `(` when tapped. Add additional keycodes for each tapdance.
|
ALT_LP // Our example key: `LALT` when held, `(` when tapped. Add additional keycodes for each tapdance.
|
||||||
};
|
};
|
||||||
|
|
||||||
// define a type containing as many tapdance states as you need
|
// Define a type containing as many tapdance states as you need
|
||||||
typedef enum {
|
typedef enum {
|
||||||
SINGLE_TAP,
|
SINGLE_TAP,
|
||||||
SINGLE_HOLD,
|
SINGLE_HOLD,
|
||||||
DOUBLE_SINGLE_TAP
|
DOUBLE_SINGLE_TAP
|
||||||
} td_state_t;
|
} td_state_t;
|
||||||
|
|
||||||
// create a global instance of the tapdance state type
|
// Create a global instance of the tapdance state type
|
||||||
static td_state_t td_state;
|
static td_state_t td_state;
|
||||||
|
|
||||||
// declare your tapdance functions:
|
// Declare your tapdance functions:
|
||||||
|
|
||||||
// function to determine the current tapdance state
|
// Function to determine the current tapdance state
|
||||||
int cur_dance (qk_tap_dance_state_t *state);
|
uint8_t cur_dance(qk_tap_dance_state_t *state);
|
||||||
|
|
||||||
// `finished` and `reset` functions for each tapdance keycode
|
// `finished` and `reset` functions for each tapdance keycode
|
||||||
void altlp_finished (qk_tap_dance_state_t *state, void *user_data);
|
void altlp_finished(qk_tap_dance_state_t *state, void *user_data);
|
||||||
void altlp_reset (qk_tap_dance_state_t *state, void *user_data);
|
void altlp_reset(qk_tap_dance_state_t *state, void *user_data);
|
||||||
```
|
```
|
||||||
|
|
||||||
Below your `LAYOUT`, define each of the tapdance functions:
|
Below your `LAYOUT`, define each of the tapdance functions:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
// determine the tapdance state to return
|
// Determine the tapdance state to return
|
||||||
int cur_dance (qk_tap_dance_state_t *state) {
|
uint8_t cur_dance(qk_tap_dance_state_t *state) {
|
||||||
if (state->count == 1) {
|
if (state->count == 1) {
|
||||||
if (state->interrupted || !state->pressed) { return SINGLE_TAP; }
|
if (state->interrupted || !state->pressed) return SINGLE_TAP;
|
||||||
else { return SINGLE_HOLD; }
|
else return SINGLE_HOLD;
|
||||||
}
|
}
|
||||||
if (state->count == 2) { return DOUBLE_SINGLE_TAP; }
|
|
||||||
else { return 3; } // any number higher than the maximum state value you return above
|
|
||||||
}
|
|
||||||
|
|
||||||
// handle the possible states for each tapdance keycode you define:
|
|
||||||
|
|
||||||
void altlp_finished (qk_tap_dance_state_t *state, void *user_data) {
|
if (state->count == 2) return DOUBLE_SINGLE_TAP;
|
||||||
td_state = cur_dance(state);
|
else return 3; // Any number higher than the maximum state value you return above
|
||||||
switch (td_state) {
|
|
||||||
case SINGLE_TAP:
|
|
||||||
register_code16(KC_LPRN);
|
|
||||||
break;
|
|
||||||
case SINGLE_HOLD:
|
|
||||||
register_mods(MOD_BIT(KC_LALT)); // for a layer-tap key, use `layer_on(_MY_LAYER)` here
|
|
||||||
break;
|
|
||||||
case DOUBLE_SINGLE_TAP: // allow nesting of 2 parens `((` within tapping term
|
|
||||||
tap_code16(KC_LPRN);
|
|
||||||
register_code16(KC_LPRN);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void altlp_reset (qk_tap_dance_state_t *state, void *user_data) {
|
// Handle the possible states for each tapdance keycode you define:
|
||||||
switch (td_state) {
|
|
||||||
case SINGLE_TAP:
|
void altlp_finished(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
unregister_code16(KC_LPRN);
|
td_state = cur_dance(state);
|
||||||
break;
|
switch (td_state) {
|
||||||
case SINGLE_HOLD:
|
case SINGLE_TAP:
|
||||||
unregister_mods(MOD_BIT(KC_LALT)); // for a layer-tap key, use `layer_off(_MY_LAYER)` here
|
register_code16(KC_LPRN);
|
||||||
break;
|
break;
|
||||||
case DOUBLE_SINGLE_TAP:
|
case SINGLE_HOLD:
|
||||||
unregister_code16(KC_LPRN);
|
register_mods(MOD_BIT(KC_LALT)); // For a layer-tap key, use `layer_on(_MY_LAYER)` here
|
||||||
}
|
break;
|
||||||
|
case DOUBLE_SINGLE_TAP: // Allow nesting of 2 parens `((` within tapping term
|
||||||
|
tap_code16(KC_LPRN);
|
||||||
|
register_code16(KC_LPRN);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// define `ACTION_TAP_DANCE_FN_ADVANCED()` for each tapdance keycode, passing in `finished` and `reset` functions
|
void altlp_reset(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
|
switch (td_state) {
|
||||||
|
case SINGLE_TAP:
|
||||||
|
unregister_code16(KC_LPRN);
|
||||||
|
break;
|
||||||
|
case SINGLE_HOLD:
|
||||||
|
unregister_mods(MOD_BIT(KC_LALT)); // For a layer-tap key, use `layer_off(_MY_LAYER)` here
|
||||||
|
break;
|
||||||
|
case DOUBLE_SINGLE_TAP:
|
||||||
|
unregister_code16(KC_LPRN);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Define `ACTION_TAP_DANCE_FN_ADVANCED()` for each tapdance keycode, passing in `finished` and `reset` functions
|
||||||
qk_tap_dance_action_t tap_dance_actions[] = {
|
qk_tap_dance_action_t tap_dance_actions[] = {
|
||||||
[ALT_LP] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, altlp_finished, altlp_reset)
|
[ALT_LP] = ACTION_TAP_DANCE_FN_ADVANCED(NULL, altlp_finished, altlp_reset)
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
|
|
||||||
Wrap each tapdance keycode in `TD()` when including it in your keymap, e.g. `TD(ALT_LP)`.
|
Wrap each tapdance keycode in `TD()` when including it in your keymap, e.g. `TD(ALT_LP)`.
|
||||||
|
|
||||||
### Example 6: Using tap dance for momentary-layer-switch and layer-toggle keys
|
#### Example 6: Using tap dance for momentary-layer-switch and layer-toggle keys :id=example-6
|
||||||
|
|
||||||
Tap Dance can be used to mimic MO(layer) and TG(layer) functionality. For this example, we will set up a key to function as `KC_QUOT` on single-tap, as `MO(_MY_LAYER)` on single-hold, and `TG(_MY_LAYER)` on double-tap.
|
Tap Dance can be used to mimic MO(layer) and TG(layer) functionality. For this example, we will set up a key to function as `KC_QUOT` on single-tap, as `MO(_MY_LAYER)` on single-hold, and `TG(_MY_LAYER)` on double-tap.
|
||||||
|
|
||||||
@@ -426,97 +419,92 @@ The first step is to include the following code towards the beginning of your `k
|
|||||||
|
|
||||||
```c
|
```c
|
||||||
typedef struct {
|
typedef struct {
|
||||||
bool is_press_action;
|
bool is_press_action;
|
||||||
int state;
|
uint8_t state;
|
||||||
} tap;
|
} tap;
|
||||||
|
|
||||||
//Define a type for as many tap dance states as you need
|
// Define a type for as many tap dance states as you need
|
||||||
enum {
|
enum {
|
||||||
SINGLE_TAP = 1,
|
SINGLE_TAP = 1,
|
||||||
SINGLE_HOLD = 2,
|
SINGLE_HOLD,
|
||||||
DOUBLE_TAP = 3
|
DOUBLE_TAP
|
||||||
};
|
};
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
QUOT_LAYR = 0 //Our custom tap dance key; add any other tap dance keys to this enum
|
QUOT_LAYR, // Our custom tap dance key; add any other tap dance keys to this enum
|
||||||
};
|
};
|
||||||
|
|
||||||
//Declare the functions to be used with your tap dance key(s)
|
// Declare the functions to be used with your tap dance key(s)
|
||||||
|
|
||||||
//Function associated with all tap dances
|
// Function associated with all tap dances
|
||||||
int cur_dance (qk_tap_dance_state_t *state);
|
uint8_t cur_dance(qk_tap_dance_state_t *state);
|
||||||
|
|
||||||
//Functions associated with individual tap dances
|
// Functions associated with individual tap dances
|
||||||
void ql_finished (qk_tap_dance_state_t *state, void *user_data);
|
void ql_finished(qk_tap_dance_state_t *state, void *user_data);
|
||||||
void ql_reset (qk_tap_dance_state_t *state, void *user_data);
|
void ql_reset(qk_tap_dance_state_t *state, void *user_data);
|
||||||
```
|
```
|
||||||
|
|
||||||
Towards the bottom of your `keymap.c`, include the following code:
|
Towards the bottom of your `keymap.c`, include the following code:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
//Determine the current tap dance state
|
// Determine the current tap dance state
|
||||||
int cur_dance (qk_tap_dance_state_t *state) {
|
uint8_t cur_dance(qk_tap_dance_state_t *state) {
|
||||||
if (state->count == 1) {
|
if (state->count == 1) {
|
||||||
if (!state->pressed) {
|
if (!state->pressed) return SINGLE_TAP;
|
||||||
return SINGLE_TAP;
|
else return SINGLE_HOLD;
|
||||||
} else {
|
} else if (state->count == 2) return DOUBLE_TAP;
|
||||||
return SINGLE_HOLD;
|
else return 8;
|
||||||
}
|
|
||||||
} else if (state->count == 2) {
|
|
||||||
return DOUBLE_TAP;
|
|
||||||
}
|
|
||||||
else return 8;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//Initialize tap structure associated with example tap dance key
|
// Initialize tap structure associated with example tap dance key
|
||||||
static tap ql_tap_state = {
|
static tap ql_tap_state = {
|
||||||
.is_press_action = true,
|
.is_press_action = true,
|
||||||
.state = 0
|
.state = 0
|
||||||
};
|
};
|
||||||
|
|
||||||
//Functions that control what our tap dance key does
|
// Functions that control what our tap dance key does
|
||||||
void ql_finished (qk_tap_dance_state_t *state, void *user_data) {
|
void ql_finished(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
ql_tap_state.state = cur_dance(state);
|
ql_tap_state.state = cur_dance(state);
|
||||||
switch (ql_tap_state.state) {
|
switch (ql_tap_state.state) {
|
||||||
case SINGLE_TAP:
|
case SINGLE_TAP:
|
||||||
tap_code(KC_QUOT);
|
tap_code(KC_QUOT);
|
||||||
break;
|
break;
|
||||||
case SINGLE_HOLD:
|
case SINGLE_HOLD:
|
||||||
layer_on(_MY_LAYER);
|
layer_on(_MY_LAYER);
|
||||||
break;
|
break;
|
||||||
case DOUBLE_TAP:
|
case DOUBLE_TAP:
|
||||||
//check to see if the layer is already set
|
// Check to see if the layer is already set
|
||||||
if (layer_state_is(_MY_LAYER)) {
|
if (layer_state_is(_MY_LAYER)) {
|
||||||
//if already set, then switch it off
|
// If already set, then switch it off
|
||||||
|
layer_off(_MY_LAYER);
|
||||||
|
} else {
|
||||||
|
// If not already set, then switch the layer on
|
||||||
|
layer_on(_MY_LAYER);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void ql_reset(qk_tap_dance_state_t *state, void *user_data) {
|
||||||
|
// If the key was held down and now is released then switch off the layer
|
||||||
|
if (ql_tap_state.state == SINGLE_HOLD) {
|
||||||
layer_off(_MY_LAYER);
|
layer_off(_MY_LAYER);
|
||||||
} else {
|
}
|
||||||
//if not already set, then switch the layer on
|
ql_tap_state.state = 0;
|
||||||
layer_on(_MY_LAYER);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void ql_reset (qk_tap_dance_state_t *state, void *user_data) {
|
// Associate our tap dance key with its functionality
|
||||||
//if the key was held down and now is released then switch off the layer
|
|
||||||
if (ql_tap_state.state==SINGLE_HOLD) {
|
|
||||||
layer_off(_MY_LAYER);
|
|
||||||
}
|
|
||||||
ql_tap_state.state = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
//Associate our tap dance key with its functionality
|
|
||||||
qk_tap_dance_action_t tap_dance_actions[] = {
|
qk_tap_dance_action_t tap_dance_actions[] = {
|
||||||
[QUOT_LAYR] = ACTION_TAP_DANCE_FN_ADVANCED_TIME(NULL, ql_finished, ql_reset, 275)
|
[QUOT_LAYR] = ACTION_TAP_DANCE_FN_ADVANCED_TIME(NULL, ql_finished, ql_reset, 275)
|
||||||
};
|
};
|
||||||
```
|
```
|
||||||
|
|
||||||
The above code is similar to that used in previous examples. The one point to note is that we need to be able to check which layers are active at any time so we can toggle them if needed. To do this we use the `layer_state_is( layer )` function which returns `true` if the given `layer` is active.
|
The above code is similar to that used in previous examples. The one point to note is that we need to be able to check which layers are active at any time so we can toggle them if needed. To do this we use the `layer_state_is(layer)` function which returns `true` if the given `layer` is active.
|
||||||
|
|
||||||
The use of `cur_dance()` and `ql_tap_state` mirrors the above examples.
|
The use of `cur_dance()` and `ql_tap_state` mirrors the above examples.
|
||||||
|
|
||||||
The `case:SINGLE_TAP` in `ql_finished` is similar to the above examples. The `case:SINGLE_HOLD` works in conjunction with `ql_reset()` to switch to `_MY_LAYER` while the tap dance key is held, and to switch away from `_MY_LAYER` when the key is released. This mirrors the use of `MO(_MY_LAYER)`. The `case:DOUBLE_TAP` works by checking whether `_MY_LAYER` is the active layer, and toggling it on or off accordingly. This mirrors the use of `TG(_MY_LAYER)`.
|
The `case:SINGLE_TAP` in `ql_finished` is similar to the above examples. The `SINGLE_HOLD` case works in conjunction with `ql_reset()` to switch to `_MY_LAYER` while the tap dance key is held, and to switch away from `_MY_LAYER` when the key is released. This mirrors the use of `MO(_MY_LAYER)`. The `DOUBLE_TAP` case works by checking whether `_MY_LAYER` is the active layer, and toggling it on or off accordingly. This mirrors the use of `TG(_MY_LAYER)`.
|
||||||
|
|
||||||
`tap_dance_actions[]` works similar to the above examples. Note that I used `ACTION_TAP_DANCE_FN_ADVANCED_TIME()` instead of `ACTION_TAP_DANCE_FN_ADVANCED()`. This is because I like my `TAPPING_TERM` to be short (~175ms) for my non-tap-dance keys but find that this is too quick for me to reliably complete tap dance actions - thus the increased time of 275ms here.
|
`tap_dance_actions[]` works similar to the above examples. Note that I used `ACTION_TAP_DANCE_FN_ADVANCED_TIME()` instead of `ACTION_TAP_DANCE_FN_ADVANCED()`. This is because I like my `TAPPING_TERM` to be short (\~175ms) for my non-tap-dance keys but find that this is too quick for me to reliably complete tap dance actions - thus the increased time of 275ms here.
|
||||||
|
|
||||||
Finally, to get this tap dance key working, be sure to include `TD(QUOT_LAYR)` in your `keymaps[]`.
|
Finally, to get this tap dance key working, be sure to include `TD(QUOT_LAYR)` in your `keymaps[]`.
|
||||||
+106
-78
@@ -2,11 +2,25 @@
|
|||||||
|
|
||||||
Unicode characters can be input straight from your keyboard! There are some limitations, however.
|
Unicode characters can be input straight from your keyboard! There are some limitations, however.
|
||||||
|
|
||||||
QMK has three different methods for enabling Unicode input and defining keycodes:
|
In order to enable Unicode support on your keyboard, you will need to do the following:
|
||||||
|
|
||||||
## Basic Unicode
|
1. Choose one of three supported Unicode implementations: [Basic Unicode](#basic-unicode), [Unicode Map](#unicode-map), [UCIS](#ucis).
|
||||||
|
2. Find which [input mode](#input-modes) is the best match for your operating system and setup.
|
||||||
|
3. [Set](#setting-the-input-mode) the appropriate input mode (or modes) in your configuration.
|
||||||
|
4. Add Unicode keycodes to your keymap.
|
||||||
|
|
||||||
This method supports Unicode code points up to `0x7FFF`. This covers characters for most modern languages, as well as symbols, but it doesn't cover emoji.
|
|
||||||
|
## 1. Methods :id=methods
|
||||||
|
|
||||||
|
QMK supports three different methods for enabling Unicode input and adding Unicode characters to your keymap. Each has its pros and cons in terms of flexibility and ease of use. Choose the one that best fits your use case.
|
||||||
|
|
||||||
|
The Basic method should be enough for most users. However, if you need a wider range of supported characters (including emoji, rare symbols etc.), you should use Unicode Map.
|
||||||
|
|
||||||
|
<br>
|
||||||
|
|
||||||
|
### 1.1. Basic Unicode :id=basic-unicode
|
||||||
|
|
||||||
|
The easiest to use method, albeit somewhat limited. It stores Unicode characters as keycodes in the keymap itself, so it only supports code points up to `0x7FFF`. This covers characters for most modern languages (including East Asian), as well as symbols, but it doesn't cover emoji.
|
||||||
|
|
||||||
Add the following to your `rules.mk`:
|
Add the following to your `rules.mk`:
|
||||||
|
|
||||||
@@ -14,11 +28,13 @@ Add the following to your `rules.mk`:
|
|||||||
UNICODE_ENABLE = yes
|
UNICODE_ENABLE = yes
|
||||||
```
|
```
|
||||||
|
|
||||||
Then add `UC(c)` keycodes to your keymap, where _c_ is the code point (preferably in hexadecimal, up to 4 digits long). For example: `UC(0x45B)`, `UC(0x30C4)`.
|
Then add `UC(c)` keycodes to your keymap, where _c_ is the code point of the desired character (preferably in hexadecimal, up to 4 digits long). For example, `UC(0x40B)` will output [Ћ](https://unicode-table.com/en/040B/), and `UC(0x30C4)` will output [ツ](https://unicode-table.com/en/30C4).
|
||||||
|
|
||||||
## Unicode Map
|
<br>
|
||||||
|
|
||||||
This method supports all possible code points (up to `0x10FFFF`); however, you need to maintain a separate mapping table in your keymap file, which may contain at most 16384 entries.
|
### 1.2. Unicode Map :id=unicode-map
|
||||||
|
|
||||||
|
In addition to standard character ranges, this method also covers emoji, ancient scripts, rare symbols etc. In fact, all possible code points (up to `0x10FFFF`) are supported. Here, Unicode characters are stored in a separate mapping table. You need to maintain a `unicode_map` array in your keymap file, which may contain at most 16384 entries.
|
||||||
|
|
||||||
Add the following to your `rules.mk`:
|
Add the following to your `rules.mk`:
|
||||||
|
|
||||||
@@ -26,7 +42,7 @@ Add the following to your `rules.mk`:
|
|||||||
UNICODEMAP_ENABLE = yes
|
UNICODEMAP_ENABLE = yes
|
||||||
```
|
```
|
||||||
|
|
||||||
Then add `X(i)` keycodes to your keymap, where _i_ is an array index into the mapping table:
|
Then add `X(i)` keycodes to your keymap, where _i_ is the desired character's index in the mapping table. This can be a numeric value, but it's recommended to keep the indices in an enum and access them by name.
|
||||||
|
|
||||||
```c
|
```c
|
||||||
enum unicode_names {
|
enum unicode_names {
|
||||||
@@ -44,15 +60,17 @@ const uint32_t PROGMEM unicode_map[] = {
|
|||||||
|
|
||||||
Then you can use `X(BANG)`, `X(SNEK)` etc. in your keymap.
|
Then you can use `X(BANG)`, `X(SNEK)` etc. in your keymap.
|
||||||
|
|
||||||
### Lower and Upper Case
|
#### Lower and Upper Case
|
||||||
|
|
||||||
Characters often come in lower and upper case pairs, such as å and Å. To make inputting these characters easier, you can use `XP(i, j)` in your keymap, where _i_ and _j_ are the mapping table indices of the lower and upper case character, respectively. If you're holding down Shift or have Caps Lock turned on when you press the key, the second (upper case) character will be inserted; otherwise, the first (lower case) version will appear.
|
Characters often come in lower and upper case pairs, such as å and Å. To make inputting these characters easier, you can use `XP(i, j)` in your keymap, where _i_ and _j_ are the mapping table indices of the lower and upper case character, respectively. If you're holding down Shift or have Caps Lock turned on when you press the key, the second (upper case) character will be inserted; otherwise, the first (lower case) version will appear.
|
||||||
|
|
||||||
This is most useful when creating a keymap for an international layout with special characters. Instead of having to put the lower and upper case versions of a character on separate keys, you can have them both on the same key by using `XP()`. This helps blend Unicode keys in with regular alphas.
|
This is most useful when creating a keymap for an international layout with special characters. Instead of having to put the lower and upper case versions of a character on separate keys, you can have them both on the same key by using `XP()`. This helps blend Unicode keys in with regular alphas.
|
||||||
|
|
||||||
Due to keycode size constraints, _i_ and _j_ can each only refer to one of the first 128 characters in your `unicode_map`. In other words, 0 ≤ _i_ ≤ 127 and 0 ≤ _j_ ≤ 127. This is enough for most use cases, but if you'd like to customize the index calculation, you can override the [`unicodemap_index()`](https://github.com/qmk/qmk_firmware/blob/71f640d47ee12c862c798e1f56392853c7b1c1a8/quantum/process_keycode/process_unicodemap.c#L40) function. This also allows you to, say, check Ctrl instead of Shift/Caps.
|
Due to keycode size constraints, _i_ and _j_ can each only refer to one of the first 128 characters in your `unicode_map`. In other words, 0 ≤ _i_ ≤ 127 and 0 ≤ _j_ ≤ 127. This is enough for most use cases, but if you'd like to customize the index calculation, you can override the [`unicodemap_index()`](https://github.com/qmk/qmk_firmware/blob/71f640d47ee12c862c798e1f56392853c7b1c1a8/quantum/process_keycode/process_unicodemap.c#L36) function. This also allows you to, say, check Ctrl instead of Shift/Caps.
|
||||||
|
|
||||||
## UCIS
|
<br>
|
||||||
|
|
||||||
|
### 1.3. UCIS :id=ucis
|
||||||
|
|
||||||
This method also supports all possible code points. As with the Unicode Map method, you need to maintain a mapping table in your keymap file. However, there are no built-in keycodes for this feature — you have to create a custom keycode or function that invokes this functionality.
|
This method also supports all possible code points. As with the Unicode Map method, you need to maintain a mapping table in your keymap file. However, there are no built-in keycodes for this feature — you have to create a custom keycode or function that invokes this functionality.
|
||||||
|
|
||||||
@@ -66,15 +84,18 @@ Then define a table like this in your keymap file:
|
|||||||
|
|
||||||
```c
|
```c
|
||||||
const qk_ucis_symbol_t ucis_symbol_table[] = UCIS_TABLE(
|
const qk_ucis_symbol_t ucis_symbol_table[] = UCIS_TABLE(
|
||||||
UCIS_SYM("poop", 0x1F4A9), // 💩
|
UCIS_SYM("poop", 0x1F4A9), // 💩
|
||||||
UCIS_SYM("rofl", 0x1F923), // 🤣
|
UCIS_SYM("rofl", 0x1F923), // 🤣
|
||||||
UCIS_SYM("kiss", 0x1F619) // 😙
|
UCIS_SYM("cuba", 0x1F1E8, 0x1F1FA), // 🇨🇺
|
||||||
|
UCIS_SYM("look", 0x0CA0, 0x005F, 0x0CA0), // ಠ_ಠ
|
||||||
);
|
);
|
||||||
```
|
```
|
||||||
|
|
||||||
To use it, call `qk_ucis_start()`. Then, type the mnemonic for the character (such as "rofl"), and hit Space or Enter. QMK should erase the "rofl" text and insert the laughing emoji.
|
By default, each table entry may be up to 3 code points long. This number can be changed by adding `#define UCIS_MAX_CODE_POINTS n` to your `config.h` file.
|
||||||
|
|
||||||
### Customization
|
To use UCIS input, call `qk_ucis_start()`. Then, type the mnemonic for the character (such as "rofl") and hit Space, Enter or Esc. QMK should erase the "rofl" text and insert the laughing emoji.
|
||||||
|
|
||||||
|
#### Customization
|
||||||
|
|
||||||
There are several functions that you can define in your keymap to customize the functionality of this feature.
|
There are several functions that you can define in your keymap to customize the functionality of this feature.
|
||||||
|
|
||||||
@@ -84,145 +105,155 @@ There are several functions that you can define in your keymap to customize the
|
|||||||
|
|
||||||
You can find the default implementations of these functions in [`process_ucis.c`](https://github.com/qmk/qmk_firmware/blob/master/quantum/process_keycode/process_ucis.c).
|
You can find the default implementations of these functions in [`process_ucis.c`](https://github.com/qmk/qmk_firmware/blob/master/quantum/process_keycode/process_ucis.c).
|
||||||
|
|
||||||
## Input Modes
|
|
||||||
|
## 2. Input Modes :id=input-modes
|
||||||
|
|
||||||
Unicode input in QMK works by inputting a sequence of characters to the OS, sort of like a macro. Unfortunately, the way this is done differs for each platform. Specifically, each platform requires a different combination of keys to trigger Unicode input. Therefore, a corresponding input mode has to be set in QMK.
|
Unicode input in QMK works by inputting a sequence of characters to the OS, sort of like a macro. Unfortunately, the way this is done differs for each platform. Specifically, each platform requires a different combination of keys to trigger Unicode input. Therefore, a corresponding input mode has to be set in QMK.
|
||||||
|
|
||||||
The following input modes are available:
|
The following input modes are available:
|
||||||
|
|
||||||
* **`UC_OSX`**: macOS built-in Unicode hex input. Supports code points up to `0xFFFF` (`0x10FFFF` with Unicode Map).
|
* **`UC_MAC`**: macOS built-in Unicode hex input. Supports code points up to `0x10FFFF` (all possible code points).
|
||||||
|
|
||||||
To enable, go to _System Preferences > Keyboard > Input Sources_, add _Unicode Hex Input_ to the list (it's under _Other_), then activate it from the input dropdown in the Menu Bar.
|
To enable, go to _System Preferences > Keyboard > Input Sources_, add _Unicode Hex Input_ to the list (it's under _Other_), then activate it from the input dropdown in the Menu Bar.
|
||||||
By default, this mode uses the left Option key (`KC_LALT`) for Unicode input, but this can be changed by defining [`UNICODE_KEY_OSX`](#input-key-configuration) with another keycode.
|
By default, this mode uses the left Option key (`KC_LALT`) for Unicode input, but this can be changed by defining [`UNICODE_KEY_MAC`](#input-key-configuration) with a different keycode.
|
||||||
|
|
||||||
!> Using the _Unicode Hex Input_ input source may disable some Option based shortcuts, such as Option + Left Arrow and Option + Right Arrow.
|
!> Using the _Unicode Hex Input_ input source may disable some Option-based shortcuts, such as Option+Left and Option+Right.
|
||||||
|
|
||||||
|
!> `UC_OSX` is a deprecated alias of `UC_MAC` that will be removed in future versions of QMK. All new keymaps should use `UC_MAC`.
|
||||||
|
|
||||||
* **`UC_LNX`**: Linux built-in IBus Unicode input. Supports code points up to `0x10FFFF` (all possible code points).
|
* **`UC_LNX`**: Linux built-in IBus Unicode input. Supports code points up to `0x10FFFF` (all possible code points).
|
||||||
|
|
||||||
Enabled by default and works almost anywhere on IBus-enabled distros. Without IBus, this mode works under GTK apps, but rarely anywhere else.
|
Enabled by default and works almost anywhere on IBus-enabled distros. Without IBus, this mode works under GTK apps, but rarely anywhere else.
|
||||||
By default, this mode uses Ctrl+Shift+U (`LCTL(LSFT(KC_U))`) to start Unicode input, but this can be changed by defining [`UNICODE_KEY_LNX`](#input-key-configuration) with another keycode. This might be required for IBus versions ≥1.5.15, where Ctrl+Shift+U behavior is consolidated into Ctrl+Shift+E.
|
By default, this mode uses Ctrl+Shift+U (`LCTL(LSFT(KC_U))`) to start Unicode input, but this can be changed by defining [`UNICODE_KEY_LNX`](#input-key-configuration) with a different keycode. This might be required for IBus versions ≥1.5.15, where Ctrl+Shift+U behavior is consolidated into Ctrl+Shift+E.
|
||||||
|
|
||||||
* **`UC_WIN`**: _(not recommended)_ Windows built-in hex numpad Unicode input. Supports code points up to `0xFFFF`.
|
* **`UC_WIN`**: _(not recommended)_ Windows built-in hex numpad Unicode input. Supports code points up to `0xFFFF`.
|
||||||
|
|
||||||
To enable, create a registry key under `HKEY_CURRENT_USER\Control Panel\Input Method\EnableHexNumpad` of type `REG_SZ` called `EnableHexNumpad` and set its value to `1`. This can be done from the Command Prompt by running `reg add "HKCU\Control Panel\Input Method" -v EnableHexNumpad -t REG_SZ -d 1` with administrator privileges. Reboot afterwards.
|
To enable, create a registry key under `HKEY_CURRENT_USER\Control Panel\Input Method` of type `REG_SZ` called `EnableHexNumpad` and set its value to `1`. This can be done from the Command Prompt by running `reg add "HKCU\Control Panel\Input Method" -v EnableHexNumpad -t REG_SZ -d 1` with administrator privileges. Reboot afterwards.
|
||||||
This mode is not recommended because of reliability and compatibility issues; use the `UC_WINC` mode instead.
|
This mode is not recommended because of reliability and compatibility issues; use the `UC_WINC` mode instead.
|
||||||
|
|
||||||
* **`UC_BSD`**: _(non implemented)_ Unicode input under BSD. Not implemented at this time. If you're a BSD user and want to help add support for it, please [open an issue on GitHub](https://github.com/qmk/qmk_firmware/issues).
|
* **`UC_BSD`**: _(non implemented)_ Unicode input under BSD. Not implemented at this time. If you're a BSD user and want to help add support for it, please [open an issue on GitHub](https://github.com/qmk/qmk_firmware/issues).
|
||||||
|
|
||||||
* **`UC_WINC`**: Windows Unicode input using [WinCompose](https://github.com/samhocevar/wincompose). As of v0.9.0, supports code points up to `0x10FFFF` (all possible code points).
|
* **`UC_WINC`**: Windows Unicode input using [WinCompose](https://github.com/samhocevar/wincompose). As of v0.9.0, supports code points up to `0x10FFFF` (all possible code points).
|
||||||
|
|
||||||
To enable, install the [latest release](https://github.com/samhocevar/wincompose/releases/latest). Once installed, WinCompose will automatically run on startup. Works reliably under all version of Windows supported by the app.
|
To enable, install the [latest release](https://github.com/samhocevar/wincompose/releases/latest). Once installed, WinCompose will automatically run on startup. This mode works reliably under all version of Windows supported by the app.
|
||||||
By default, this mode uses right Alt (`KC_RALT`) as the Compose key, but this can be changed in the WinCompose settings and by defining [`UNICODE_KEY_WINC`](#input-key-configuration) with another keycode.
|
By default, this mode uses right Alt (`KC_RALT`) as the Compose key, but this can be changed in the WinCompose settings and by defining [`UNICODE_KEY_WINC`](#input-key-configuration) with a different keycode.
|
||||||
|
|
||||||
### Switching Input Modes
|
|
||||||
|
|
||||||
There are two ways to set the input mode for Unicode: by keycode or by function. Keep in mind that both methods write to persistent storage (EEPROM), and are loaded each time the keyboard starts. So once you've set it the first time, you don't need to set it again unless you want to change it, or you've reset the EEPROM settings.
|
## 3. Setting the Input Mode :id=setting-the-input-mode
|
||||||
|
|
||||||
You can switch the input mode at any time by using one of the following keycodes. The easiest way is to add the ones you use to your keymap.
|
To set your desired input mode, add the following define to your `config.h`:
|
||||||
|
|
||||||
|Keycode |Alias |Input Mode |Description |
|
|
||||||
|----------------------|---------|------------|--------------------------------------------------------------|
|
|
||||||
|`UNICODE_MODE_FORWARD`|`UC_MOD` |Next in list|[Cycle](#input-mode-cycling) through selected modes |
|
|
||||||
|`UNICODE_MODE_REVERSE`|`UC_RMOD`|Prev in list|[Cycle](#input-mode-cycling) through selected modes in reverse|
|
|
||||||
|`UNICODE_MODE_OSX` |`UC_M_OS`|`UC_OSX` |Switch to macOS input |
|
|
||||||
|`UNICODE_MODE_LNX` |`UC_M_LN`|`UC_LNX` |Switch to Linux input |
|
|
||||||
|`UNICODE_MODE_WIN` |`UC_M_WI`|`UC_WIN` |Switch to Windows input |
|
|
||||||
|`UNICODE_MODE_BSD` |`UC_M_BS`|`UC_BSD` |Switch to BSD input (not implemented) |
|
|
||||||
|`UNICODE_MODE_WINC` |`UC_M_WC`|`UC_WINC` |Switch to Windows input using WinCompose |
|
|
||||||
|
|
||||||
You can also switch the input mode by calling `set_unicode_input_mode(x)` in your code, where _x_ is one of the above input mode constants (e.g. `UC_LNX`). Since the function only needs to be called once, it's recommended that you do it in `eeconfig_init_user()` (or a similar function). For example:
|
|
||||||
|
|
||||||
```c
|
```c
|
||||||
void eeconfig_init_user(void) {
|
#define UNICODE_SELECTED_MODES UC_LNX
|
||||||
set_unicode_input_mode(UC_LNX);
|
|
||||||
}
|
|
||||||
```
|
```
|
||||||
|
|
||||||
### Audio Feedback
|
This example sets the board's default input mode to `UC_LNX`. You can replace this with `UC_MAC`, `UC_WINC`, or any of the other modes listed [above](#input-modes). The board will automatically use the selected mode on startup, unless you manually switch to another mode (see [below](#keycodes)).
|
||||||
|
|
||||||
|
You can also select multiple input modes, which allows you to easily cycle through them using the `UC_MOD`/`UC_RMOD` keycodes.
|
||||||
|
|
||||||
|
```c
|
||||||
|
#define UNICODE_SELECTED_MODES UC_MAC, UC_LNX, UC_WINC
|
||||||
|
```
|
||||||
|
|
||||||
|
Note that the values are separated by commas. The board will remember the last used input mode and will continue using it on next power-up. You can disable this and force it to always start with the first mode in the list by adding `#define UNICODE_CYCLE_PERSIST false` to your `config.h`.
|
||||||
|
|
||||||
|
#### Keycodes
|
||||||
|
|
||||||
|
You can switch the input mode at any time by using the following keycodes. Adding these to your keymap allows you to quickly switch to a specific input mode, including modes not listed in `UNICODE_SELECTED_MODES`.
|
||||||
|
|
||||||
|
|Keycode |Alias |Input Mode |Description |
|
||||||
|
|----------------------|---------|------------|-----------------------------------------------------------------------------|
|
||||||
|
|`UNICODE_MODE_FORWARD`|`UC_MOD` |Next in list|Cycle through selected modes, reverse direction when Shift is held |
|
||||||
|
|`UNICODE_MODE_REVERSE`|`UC_RMOD`|Prev in list|Cycle through selected modes in reverse, forward direction when Shift is held|
|
||||||
|
|`UNICODE_MODE_MAC` |`UC_M_MA`|`UC_MAC` |Switch to macOS input |
|
||||||
|
|`UNICODE_MODE_LNX` |`UC_M_LN`|`UC_LNX` |Switch to Linux input |
|
||||||
|
|`UNICODE_MODE_WIN` |`UC_M_WI`|`UC_WIN` |Switch to Windows input |
|
||||||
|
|`UNICODE_MODE_BSD` |`UC_M_BS`|`UC_BSD` |Switch to BSD input _(not implemented)_ |
|
||||||
|
|`UNICODE_MODE_WINC` |`UC_M_WC`|`UC_WINC` |Switch to Windows input using WinCompose |
|
||||||
|
|
||||||
|
You can also switch the input mode by calling `set_unicode_input_mode(x)` in your code, where _x_ is one of the above input mode constants (e.g. `UC_LNX`).
|
||||||
|
|
||||||
|
?> Using `UNICODE_SELECTED_MODES` is preferable to calling `set_unicode_input_mode()` in `matrix_init_user()` or similar functions, since it's better integrated into the Unicode system and has the added benefit of avoiding unnecessary writes to EEPROM.
|
||||||
|
|
||||||
|
#### Audio Feedback
|
||||||
|
|
||||||
If you have the [Audio feature](feature_audio.md) enabled on the board, you can set melodies to be played when you press the above keys. That way you can have some audio feedback when switching input modes.
|
If you have the [Audio feature](feature_audio.md) enabled on the board, you can set melodies to be played when you press the above keys. That way you can have some audio feedback when switching input modes.
|
||||||
|
|
||||||
For instance, you can add these definitions to your `config.h` file:
|
For instance, you can add these definitions to your `config.h` file:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
#define UNICODE_SONG_OSX COIN_SOUND
|
#define UNICODE_SONG_MAC AUDIO_ON_SOUND
|
||||||
#define UNICODE_SONG_LNX UNICODE_LINUX
|
#define UNICODE_SONG_LNX UNICODE_LINUX
|
||||||
#define UNICODE_SONG_BSD MARIO_GAMEOVER
|
#define UNICODE_SONG_BSD TERMINAL_SOUND
|
||||||
#define UNICODE_SONG_WIN UNICODE_WINDOWS
|
#define UNICODE_SONG_WIN UNICODE_WINDOWS
|
||||||
#define UNICODE_SONG_WINC UNICODE_WINDOWS
|
#define UNICODE_SONG_WINC UNICODE_WINDOWS
|
||||||
```
|
```
|
||||||
|
|
||||||
### Additional Customization
|
|
||||||
|
## Additional Customization
|
||||||
|
|
||||||
Because Unicode is a large and versatile feature, there are a number of options you can customize to make it work better on your system.
|
Because Unicode is a large and versatile feature, there are a number of options you can customize to make it work better on your system.
|
||||||
|
|
||||||
#### Start and Finish Input Functions
|
### Start and Finish Input Functions
|
||||||
|
|
||||||
The functions for starting and finishing Unicode input on your platform can be overridden locally. Possible uses include customizing input mode behavior if you don't use the default keys, or adding extra visual/audio feedback to Unicode input.
|
The functions for starting and finishing Unicode input on your platform can be overridden locally. Possible uses include customizing input mode behavior if you don't use the default keys, or adding extra visual/audio feedback to Unicode input.
|
||||||
|
|
||||||
* `void unicode_input_start(void)` – This sends the initial sequence that tells your platform to enter Unicode input mode. For example, it presses Ctrl+Shift+U on Linux and holds the Option key on macOS.
|
* `void unicode_input_start(void)` – This sends the initial sequence that tells your platform to enter Unicode input mode. For example, it holds the left Alt key followed by Num+ on Windows, and presses the `UNICODE_KEY_LNX` combination (default: Ctrl+Shift+U) on Linux.
|
||||||
* `void unicode_input_finish(void)` – This is called to exit Unicode input mode, for example by pressing Space or releasing the Option key.
|
* `void unicode_input_finish(void)` – This is called to exit Unicode input mode, for example by pressing Space or releasing the Alt key.
|
||||||
|
|
||||||
You can find the default implementations of these functions in [`process_unicode_common.c`](https://github.com/qmk/qmk_firmware/blob/master/quantum/process_keycode/process_unicode_common.c).
|
You can find the default implementations of these functions in [`process_unicode_common.c`](https://github.com/qmk/qmk_firmware/blob/master/quantum/process_keycode/process_unicode_common.c).
|
||||||
|
|
||||||
#### Input Key Configuration
|
### Input Key Configuration
|
||||||
|
|
||||||
You can customize the keys used to trigger Unicode input for macOS, Linux and WinCompose by adding corresponding defines to your `config.h`. The default values match the platforms' default settings, so you shouldn't need to change this unless Unicode input isn't working, or you want to use a different key (e.g. in order to free up left or right Alt).
|
You can customize the keys used to trigger Unicode input for macOS, Linux and WinCompose by adding corresponding defines to your `config.h`. The default values match the platforms' default settings, so you shouldn't need to change this unless Unicode input isn't working, or you want to use a different key (e.g. in order to free up left or right Alt).
|
||||||
|
|
||||||
|Define |Type |Default |Example |
|
|Define |Type |Default |Example |
|
||||||
|------------------|----------|------------------|-------------------------------------------|
|
|------------------|----------|------------------|-------------------------------------------|
|
||||||
|`UNICODE_KEY_OSX` |`uint8_t` |`KC_LALT` |`#define UNICODE_KEY_OSX KC_RALT` |
|
|`UNICODE_KEY_MAC` |`uint8_t` |`KC_LALT` |`#define UNICODE_KEY_MAC KC_RALT` |
|
||||||
|`UNICODE_KEY_LNX` |`uint16_t`|`LCTL(LSFT(KC_U))`|`#define UNICODE_KEY_LNX LCTL(LSFT(KC_E))`|
|
|`UNICODE_KEY_LNX` |`uint16_t`|`LCTL(LSFT(KC_U))`|`#define UNICODE_KEY_LNX LCTL(LSFT(KC_E))`|
|
||||||
|`UNICODE_KEY_WINC`|`uint8_t` |`KC_RALT` |`#define UNICODE_KEY_WINC KC_RGUI` |
|
|`UNICODE_KEY_WINC`|`uint8_t` |`KC_RALT` |`#define UNICODE_KEY_WINC KC_RGUI` |
|
||||||
|
|
||||||
#### Input Mode Cycling
|
|
||||||
|
|
||||||
You can choose which input modes are available for cycling through. By default, this is disabled. If you want to enable it, limiting it to just the modes you use makes sense. Note that the values in the list are comma-delimited.
|
## Sending Unicode Strings
|
||||||
|
|
||||||
```c
|
QMK provides several functions that allow you to send Unicode input to the host programmatically:
|
||||||
#define UNICODE_SELECTED_MODES UC_OSX, UC_LNX, UC_WIN, UC_WINC
|
|
||||||
```
|
|
||||||
|
|
||||||
You can cycle through the selected modes by using the `UC_MOD`/`UC_RMOD` keycodes, or by calling `cycle_unicode_input_mode(offset)` in your code (`offset` is how many modes to move forward by, so +1 corresponds to `UC_MOD`).
|
### `send_unicode_string()`
|
||||||
|
|
||||||
By default, when the keyboard boots, it will initialize the input mode to the last one you used. You can disable this and make it start with the first mode in the list every time by adding the following to your `config.h`:
|
This function is much like `send_string()`, but it allows you to input UTF-8 characters directly. It supports all code points, provided the selected input mode also supports it. Make sure your `keymap.c` file is formatted using UTF-8 encoding.
|
||||||
|
|
||||||
```c
|
|
||||||
#define UNICODE_CYCLE_PERSIST false
|
|
||||||
```
|
|
||||||
|
|
||||||
!> Using `UNICODE_SELECTED_MODES` means you don't have to initially set the input mode in `matrix_init_user()` (or a similar function); the Unicode system will do that for you on startup. This has the added benefit of avoiding unnecessary writes to EEPROM.
|
|
||||||
|
|
||||||
## `send_unicode_string()`
|
|
||||||
|
|
||||||
This function is much like `send_string()` but allows you to input UTF-8 characters directly, and supports all code points (provided the selected input method also supports it). Make sure your `keymap.c` is formatted in UTF-8 encoding.
|
|
||||||
|
|
||||||
```c
|
```c
|
||||||
send_unicode_string("(ノಠ痊ಠ)ノ彡┻━┻");
|
send_unicode_string("(ノಠ痊ಠ)ノ彡┻━┻");
|
||||||
```
|
```
|
||||||
|
|
||||||
## `send_unicode_hex_string()`
|
Example uses include sending Unicode strings when a key is pressed, as described in [Macros](feature_macros.md).
|
||||||
|
|
||||||
Similar to `send_unicode_string()`, but the characters are represented by their code point values in ASCII, separated by spaces. For example, the table flip above would be achieved with:
|
### `send_unicode_hex_string()`
|
||||||
|
|
||||||
|
Similar to `send_unicode_string()`, but the characters are represented by their Unicode code points, written in hexadecimal and separated by spaces. For example, the table flip above would be achieved with:
|
||||||
|
|
||||||
```c
|
```c
|
||||||
send_unicode_hex_string("0028 30CE 0CA0 75CA 0CA0 0029 30CE 5F61 253B 2501 253B");
|
send_unicode_hex_string("0028 30CE 0CA0 75CA 0CA0 0029 30CE 5F61 253B 2501 253B");
|
||||||
```
|
```
|
||||||
|
|
||||||
An easy way to convert your Unicode string to this format is by using [this site](https://r12a.github.io/app-conversion/), and taking the result in the "Hex/UTF-32" section.
|
An easy way to convert your Unicode string to this format is to use [this site](https://r12a.github.io/app-conversion/) and take the result in the "Hex/UTF-32" section.
|
||||||
|
|
||||||
|
|
||||||
## Additional Language Support
|
## Additional Language Support
|
||||||
|
|
||||||
In `quantum/keymap_extras/`, you'll see various language files - these work the same way as the alternative layout ones do. Most are defined by their two letter country/language code followed by an underscore and a 4-letter abbreviation of its name. `FR_UGRV` which will result in a `ù` when using a software-implemented AZERTY layout. It's currently difficult to send such characters in just the firmware.
|
In `quantum/keymap_extras`, you'll see various language files — these work the same way as the ones for alternative layouts such as Colemak or BÉPO. When you include one of these language headers, you gain access to keycodes specific to that language / national layout. Such keycodes are defined by a 2-letter country/language code, followed by an underscore and a 4-letter abbreviation of the character to which the key corresponds. For example, including `keymap_french.h` and using `FR_UGRV` in your keymap will output `ù` when typed on a system with a native French AZERTY layout.
|
||||||
|
|
||||||
|
If the primary system layout you use on your machine is different from US ANSI, using these language-specific keycodes can help your QMK keymaps better match what will actually be output on the screen. However, keep in mind that these keycodes are just aliases for the corresponding default US keycodes under the hood, and that the HID protocol used by keyboards is itself inherently based on US ANSI.
|
||||||
|
|
||||||
|
|
||||||
## International Characters on Windows
|
## International Characters on Windows
|
||||||
|
|
||||||
### AutoHotkey allows Windows users to create custom hotkeys among others.
|
### AutoHotkey
|
||||||
|
|
||||||
The method does not require Unicode support in the keyboard itself but depends instead of [AutoHotkey](https://autohotkey.com) running in the background.
|
The method does not require Unicode support in the keyboard itself but instead depends on [AutoHotkey](https://autohotkey.com) running in the background.
|
||||||
|
|
||||||
First you need to select a modifier combination that is not in use by any of your programs.
|
First you need to select a modifier combination that is not in use by any of your programs.
|
||||||
CtrlAltWin is not used very widely and should therefore be perfect for this.
|
Ctrl+Alt+Win is not used very widely and should therefore be perfect for this.
|
||||||
There is a macro defined for a mod-tab combo `LCAG_T`.
|
There is a macro defined for a mod-tab combo `LCAG_T`.
|
||||||
Add this mod-tab combo to a key on your keyboard, e.g.: `LCAG_T(KC_TAB)`.
|
Add this mod-tab combo to a key on your keyboard, e.g.: `LCAG_T(KC_TAB)`.
|
||||||
This makes the key behave like a tab key if pressed and released immediately but changes it to the modifier if used with another key.
|
This makes the key behave like a tab key if pressed and released immediately but changes it to the modifier if used with another key.
|
||||||
@@ -237,8 +268,5 @@ AutoHotkey inserts the Text right of `Send, ` when this combination is pressed.
|
|||||||
|
|
||||||
### US International
|
### US International
|
||||||
|
|
||||||
If you enable the US International layout on the system, it will use punctuation to accent the characters.
|
If you enable the US International layout on the system, it will use punctuation to accent the characters. For instance, typing "\`a" will result in à.
|
||||||
|
|
||||||
For instance, typing "\`a" will result in à.
|
|
||||||
|
|
||||||
You can find details on how to enable this [here](https://support.microsoft.com/en-us/help/17424/windows-change-keyboard-layout).
|
You can find details on how to enable this [here](https://support.microsoft.com/en-us/help/17424/windows-change-keyboard-layout).
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
# Userspace: Sharing Code Between Keymaps
|
# Userspace: Sharing Code Between Keymaps
|
||||||
|
|
||||||
If you use more than one keyboard with a similar keymap, you might see the benefit in being able to share code between them. Create your own folder in `users/` named the same as your keymap (ideally your github username, `<name>`) with the following structure:
|
If you use more than one keyboard with a similar keymap, you might see the benefit in being able to share code between them. Create your own folder in `users/` named the same as your keymap (ideally your GitHub username, `<name>`) with the following structure:
|
||||||
|
|
||||||
* `/users/<name>/` (added to the path automatically)
|
* `/users/<name>/` (added to the path automatically)
|
||||||
* `readme.md` (optional, recommended)
|
* `readme.md` (optional, recommended)
|
||||||
@@ -73,7 +73,7 @@ The reason for this, is that `<name>.h` won't be added in time to add settings (
|
|||||||
|
|
||||||
## Readme (`readme.md`)
|
## Readme (`readme.md`)
|
||||||
|
|
||||||
Please include authorship (your name, github username, email), and optionally [a license that's GPL compatible](https://www.gnu.org/licenses/license-list.html#GPLCompatibleLicenses).
|
Please include authorship (your name, GitHub username, email), and optionally [a license that's GPL compatible](https://www.gnu.org/licenses/license-list.html#GPLCompatibleLicenses).
|
||||||
|
|
||||||
You can use this as a template:
|
You can use this as a template:
|
||||||
```
|
```
|
||||||
@@ -93,17 +93,29 @@ You should have received a copy of the GNU General Public License
|
|||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
```
|
```
|
||||||
|
|
||||||
You'd want to replace the year, name, email and github username with your info.
|
You'd want to replace the year, name, email and GitHub username with your info.
|
||||||
|
|
||||||
Additionally, this is a good place to document your code, if you wish to share it with others.
|
Additionally, this is a good place to document your code, if you wish to share it with others.
|
||||||
|
|
||||||
# Examples
|
## Build All Keyboards That Support a Specific Keymap
|
||||||
|
|
||||||
For a brief example, checkout [`/users/_example/`](https://github.com/qmk/qmk_firmware/tree/master/users/drashna).
|
Want to check all your keymaps build in a single command? You can run:
|
||||||
|
|
||||||
|
make all:<name>
|
||||||
|
|
||||||
|
For example,
|
||||||
|
|
||||||
|
make all:jack
|
||||||
|
|
||||||
|
This is ideal for when you want ensure everything compiles successfully when preparing a [_Pull request_](https://github.com/qmk/qmk_firmware/pulls).
|
||||||
|
|
||||||
|
## Examples
|
||||||
|
|
||||||
|
For a brief example, checkout [`/users/_example/`](https://github.com/qmk/qmk_firmware/tree/master/users/_example).
|
||||||
For a more complicated example, checkout [`/users/drashna/`](https://github.com/qmk/qmk_firmware/tree/master/users/drashna)'s userspace.
|
For a more complicated example, checkout [`/users/drashna/`](https://github.com/qmk/qmk_firmware/tree/master/users/drashna)'s userspace.
|
||||||
|
|
||||||
|
|
||||||
## Customized Functions
|
### Customized Functions
|
||||||
|
|
||||||
QMK has a bunch of [functions](custom_quantum_functions.md) that have [`_quantum`, `_kb`, and `_user` versions](custom_quantum_functions.md#a-word-on-core-vs-keyboards-vs-keymap) that you can use. You will pretty much always want to use the user version of these functions. But the problem is that if you use them in your userspace, then you don't have a version that you can use in your keymap.
|
QMK has a bunch of [functions](custom_quantum_functions.md) that have [`_quantum`, `_kb`, and `_user` versions](custom_quantum_functions.md#a-word-on-core-vs-keyboards-vs-keymap) that you can use. You will pretty much always want to use the user version of these functions. But the problem is that if you use them in your userspace, then you don't have a version that you can use in your keymap.
|
||||||
|
|
||||||
@@ -130,7 +142,7 @@ The `_keymap` part here doesn't matter, it just needs to be something other than
|
|||||||
|
|
||||||
You can see a list of this and other common functions in [`template.c`](https://github.com/qmk/qmk_firmware/blob/master/users/drashna/template.c) in [`users/drashna`](https://github.com/qmk/qmk_firmware/tree/master/users/drashna).
|
You can see a list of this and other common functions in [`template.c`](https://github.com/qmk/qmk_firmware/blob/master/users/drashna/template.c) in [`users/drashna`](https://github.com/qmk/qmk_firmware/tree/master/users/drashna).
|
||||||
|
|
||||||
## Custom Features
|
### Custom Features
|
||||||
|
|
||||||
Since the Userspace feature can support a staggering number of boards, you may have boards that you want to enable certain functionality for, but not for others. And you can actually create "features" that you can enable or disable in your own userspace.
|
Since the Userspace feature can support a staggering number of boards, you may have boards that you want to enable certain functionality for, but not for others. And you can actually create "features" that you can enable or disable in your own userspace.
|
||||||
|
|
||||||
@@ -166,7 +178,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
|
|||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
## Consolidated Macros
|
### Consolidated Macros
|
||||||
|
|
||||||
If you wanted to consolidate macros and other functions into your userspace for all of your keymaps, you can do that. This builds upon the [Customized Functions](#customized-functions) example above. This lets you maintain a bunch of macros that are shared between the different keyboards, and allow for keyboard specific macros, too.
|
If you wanted to consolidate macros and other functions into your userspace for all of your keymaps, you can do that. This builds upon the [Customized Functions](#customized-functions) example above. This lets you maintain a bunch of macros that are shared between the different keyboards, and allow for keyboard specific macros, too.
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,25 @@
|
|||||||
|
# Word Per Minute (WPM) Calculcation
|
||||||
|
|
||||||
|
The WPM feature uses time between keystrokes to compute a rolling average words
|
||||||
|
per minute rate and makes this available for various uses.
|
||||||
|
|
||||||
|
Enable the WPM system by adding this to your `rules.mk`:
|
||||||
|
|
||||||
|
WPM_ENABLE = yes
|
||||||
|
|
||||||
|
For split keyboards using soft serial, the computed WPM
|
||||||
|
score will be available on the master AND slave half.
|
||||||
|
|
||||||
|
## Public Functions
|
||||||
|
|
||||||
|
`uint8_t get_current_wpm(void);`
|
||||||
|
This function returns the current WPM as an unsigned integer.
|
||||||
|
|
||||||
|
|
||||||
|
## Customized keys for WPM calc
|
||||||
|
|
||||||
|
By default, the WPM score only includes letters, numbers, space and some
|
||||||
|
punctuation. If you want to change the set of characters considered as part of
|
||||||
|
the WPM calculation, you can implement `wpm_keycode_user(uint16_t keycode)`
|
||||||
|
and return true for any characters you would like included in the calculation,
|
||||||
|
or false to not count that particular keycode.
|
||||||
@@ -26,7 +26,6 @@ Compatible flashers:
|
|||||||
|
|
||||||
* [QMK Toolbox](https://github.com/qmk/qmk_toolbox/releases) (recommended GUI)
|
* [QMK Toolbox](https://github.com/qmk/qmk_toolbox/releases) (recommended GUI)
|
||||||
* [dfu-programmer](https://github.com/dfu-programmer/dfu-programmer) / `:dfu` in QMK (recommended command line)
|
* [dfu-programmer](https://github.com/dfu-programmer/dfu-programmer) / `:dfu` in QMK (recommended command line)
|
||||||
* [Atmel's Flip](http://www.microchip.com/developmenttools/productdetails.aspx?partno=flip) (not recommended)
|
|
||||||
|
|
||||||
Flashing sequence:
|
Flashing sequence:
|
||||||
|
|
||||||
|
|||||||
@@ -4,8 +4,8 @@
|
|||||||
[](https://travis-ci.org/qmk/qmk_firmware)
|
[](https://travis-ci.org/qmk/qmk_firmware)
|
||||||
[](https://discord.gg/Uq7gcHh)
|
[](https://discord.gg/Uq7gcHh)
|
||||||
[](https://docs.qmk.fm)
|
[](https://docs.qmk.fm)
|
||||||
[](https://github.com/qmk/qmk_firmware/pulse/monthly)
|
[](https://github.com/qmk/qmk_firmware/pulse/monthly)
|
||||||
[](https://github.com/qmk/qmk_firmware/)
|
[](https://github.com/qmk/qmk_firmware/)
|
||||||
|
|
||||||
## Qu'est-ce que QMK Firmware ?
|
## Qu'est-ce que QMK Firmware ?
|
||||||
|
|
||||||
@@ -13,7 +13,7 @@ QMK (*Quantum Mechanical Keyboard*) est une communauté open source qui maintien
|
|||||||
|
|
||||||
## Comment l'obtenir
|
## Comment l'obtenir
|
||||||
|
|
||||||
Si vous souhaitez contribuer à une disposition de clavier (keymap), ou à des fonctionnalités de QMK alors le plus simple est de [forker le dépôt avec Github](https://github.com/qmk/qmk_firmware#fork-destination-box) puis cloner le dépôt localement pour y faire des changements. Vous pourrez pousser vos changements sur github puis ouvrir un [Pull Request](https://github.com/qmk/qmk_firmware/pulls) depuis votre fork Github.
|
Si vous souhaitez contribuer à une disposition de clavier (keymap), ou à des fonctionnalités de QMK alors le plus simple est de [forker le dépôt avec GitHub](https://github.com/qmk/qmk_firmware#fork-destination-box) puis cloner le dépôt localement pour y faire des changements. Vous pourrez pousser vos changements sur GitHub puis ouvrir un [Pull Request](https://github.com/qmk/qmk_firmware/pulls) depuis votre fork GitHub.
|
||||||
|
|
||||||
Sinon, vous pouvez aussi le télécharger directement en ([zip](https://github.com/qmk/qmk_firmware/zipball/master), [tar](https://github.com/qmk/qmk_firmware/tarball/master)), ou le cloner avec git en ssh (`[email protected]:qmk/qmk_firmware.git`), ou https (`https://github.com/qmk/qmk_firmware.git`).
|
Sinon, vous pouvez aussi le télécharger directement en ([zip](https://github.com/qmk/qmk_firmware/zipball/master), [tar](https://github.com/qmk/qmk_firmware/tarball/master)), ou le cloner avec git en ssh (`[email protected]:qmk/qmk_firmware.git`), ou https (`https://github.com/qmk/qmk_firmware.git`).
|
||||||
|
|
||||||
|
|||||||
@@ -101,7 +101,8 @@
|
|||||||
* [Guide des claviers soudés à la main](fr-fr/hand_wire.md)
|
* [Guide des claviers soudés à la main](fr-fr/hand_wire.md)
|
||||||
* [Guide de flash de l’ISP](fr-fr/isp_flashing_guide.md)
|
* [Guide de flash de l’ISP](fr-fr/isp_flashing_guide.md)
|
||||||
* [Guide du débogage ARM](fr-fr/arm_debugging.md)
|
* [Guide du débogage ARM](fr-fr/arm_debugging.md)
|
||||||
* [Drivers i2c](fr-fr/i2c_driver.md)
|
* [Drivers I2C](fr-fr/i2c_driver.md)
|
||||||
|
* [Drivers SPI](fr-fr/spi_driver.md)
|
||||||
* [Contrôles des GPIO](fr-fr/internals_gpio_control.md)
|
* [Contrôles des GPIO](fr-fr/internals_gpio_control.md)
|
||||||
* [Conversion en Proton C](fr-fr/proton_c_conversion.md)
|
* [Conversion en Proton C](fr-fr/proton_c_conversion.md)
|
||||||
|
|
||||||
|
|||||||
@@ -101,7 +101,7 @@ Ceci est fait immédiatement après la fusion de la branche `future` précédent
|
|||||||
* [ ] Regroupe ChangeLog dans un fichier.
|
* [ ] Regroupe ChangeLog dans un fichier.
|
||||||
* [ ] `git commit -m 'Merge point for <DATE> Breaking Change'`
|
* [ ] `git commit -m 'Merge point for <DATE> Breaking Change'`
|
||||||
* [ ] `git push origin future`
|
* [ ] `git push origin future`
|
||||||
* Actions sur Github
|
* Actions sur GitHub
|
||||||
* [ ] Crée un PR pour `future`
|
* [ ] Crée un PR pour `future`
|
||||||
* [ ] S'assurer que Travis ne relève aucun problème
|
* [ ] S'assurer que Travis ne relève aucun problème
|
||||||
* [ ] Fusion le PR `future`
|
* [ ] Fusion le PR `future`
|
||||||
@@ -155,11 +155,3 @@ Pour le moment, l'origine du problème n'est pas comprise, mais certaines option
|
|||||||
|
|
||||||
https://github.com/tmk/tmk_keyboard/issues/266
|
https://github.com/tmk/tmk_keyboard/issues/266
|
||||||
https://geekhack.org/index.php?topic=41989.msg1967778#msg1967778
|
https://geekhack.org/index.php?topic=41989.msg1967778#msg1967778
|
||||||
|
|
||||||
## FLIP ne marche pas
|
|
||||||
|
|
||||||
### `AtLibUsbDfu.dll` Not Found
|
|
||||||
|
|
||||||
Supprimez le pilote actuel et réinstallez celui donné par FLIP dans le gestionnaire de périphériques.
|
|
||||||
|
|
||||||
http://imgur.com/a/bnwzy
|
|
||||||
@@ -26,7 +26,6 @@ Méthodes de flash compatibles :
|
|||||||
|
|
||||||
* [QMK Toolbox](https://github.com/qmk/qmk_toolbox/releases) (interface graphique recommandé)
|
* [QMK Toolbox](https://github.com/qmk/qmk_toolbox/releases) (interface graphique recommandé)
|
||||||
* [dfu-programmer](https://github.com/dfu-programmer/dfu-programmer) / `:dfu` avec QMK (outil en ligne de commande recommandé)
|
* [dfu-programmer](https://github.com/dfu-programmer/dfu-programmer) / `:dfu` avec QMK (outil en ligne de commande recommandé)
|
||||||
* [Atmel's Flip](http://www.microchip.com/developmenttools/productdetails.aspx?partno=flip) (non recommandé)
|
|
||||||
|
|
||||||
Ordre des actions :
|
Ordre des actions :
|
||||||
|
|
||||||
|
|||||||
@@ -6,11 +6,11 @@ GitHub peut être un peu compliqué pour ceux qui n'y sont pas familier. Ce guid
|
|||||||
|
|
||||||
Commencez par la [page GitHub de QMK](https://github.com/qmk/qmk_firmware), et vous verrez un bouton dans le coin en haut à droite qui indique "Fork":
|
Commencez par la [page GitHub de QMK](https://github.com/qmk/qmk_firmware), et vous verrez un bouton dans le coin en haut à droite qui indique "Fork":
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
Si vous faites partie d'une organisation, vous aurez besoin de savoir quel compte utiliser pour le fork. Dans la plupart des cas, vous voudrez créer le fork dans votre compte personnel. Une fois le fork complet (cela peut quelques fois prendre un peu de temps), appuyez sur le bouton "Clone or download":
|
Si vous faites partie d'une organisation, vous aurez besoin de savoir quel compte utiliser pour le fork. Dans la plupart des cas, vous voudrez créer le fork dans votre compte personnel. Une fois le fork complet (cela peut quelques fois prendre un peu de temps), appuyez sur le bouton "Clone or download":
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
Faites attention à sélectionner "HTTPS", et sélectionnez le lien et copiez-le:
|
Faites attention à sélectionner "HTTPS", et sélectionnez le lien et copiez-le:
|
||||||
|
|
||||||
|
|||||||
@@ -44,7 +44,7 @@ git pull upstream master
|
|||||||
git push origin master
|
git push origin master
|
||||||
```
|
```
|
||||||
|
|
||||||
Cela vous change la branche courante en master, synchronise les données de références du dépôt QMK vers votre ordinateur. La commande pull tire les données de références vers votre branche courante puis les y téleverse. La commande push permet de pousser la branche courante (master) vers votre fork github.
|
Cela vous change la branche courante en master, synchronise les données de références du dépôt QMK vers votre ordinateur. La commande pull tire les données de références vers votre branche courante puis les y téleverse. La commande push permet de pousser la branche courante (master) vers votre fork GitHub.
|
||||||
|
|
||||||
### Faire des changements
|
### Faire des changements
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,47 @@
|
|||||||
|
# Docker Quick Start
|
||||||
|
|
||||||
|
This project includes a Docker workflow that will allow you to build a new firmware for your keyboard very easily without major changes to your primary operating system. This also ensures that when you clone the project and perform a build, you have the exact same environment as anyone else and the QMK build infrastructure. This makes it much easier for people to help you troubleshoot any issues you encounter.
|
||||||
|
|
||||||
|
## Requirements
|
||||||
|
|
||||||
|
The main prerequisite is a working `docker` install.
|
||||||
|
* [Docker CE](https://docs.docker.com/install/#supported-platforms)
|
||||||
|
|
||||||
|
## Usage
|
||||||
|
|
||||||
|
Acquire a local copy of the QMK's repository (including submodules):
|
||||||
|
|
||||||
|
```bash
|
||||||
|
git clone --recurse-submodules https://github.com/qmk/qmk_firmware.git
|
||||||
|
cd qmk_firmware
|
||||||
|
```
|
||||||
|
|
||||||
|
Run the following command to build a keymap:
|
||||||
|
```bash
|
||||||
|
util/docker_build.sh <keyboard>:<keymap>
|
||||||
|
# For example: util/docker_build.sh planck/rev6:default
|
||||||
|
```
|
||||||
|
|
||||||
|
This will compile the desired keyboard/keymap and leave the resulting `.hex` or `.bin` file in the QMK directory for you to flash. If `:keymap` is omitted, all keymaps are used. Note that the parameter format is the same as when building with `make`.
|
||||||
|
|
||||||
|
There is also support for building _and_ flashing the keyboard straight from Docker by specifying the `target` as well:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
util/docker_build.sh keyboard:keymap:target
|
||||||
|
# For example: util/docker_build.sh planck/rev6:default:flash
|
||||||
|
```
|
||||||
|
|
||||||
|
You can also start the script without any parameters, in which case it will ask you to input the build parameters one by one, which you may find easier to use:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
util/docker_build.sh
|
||||||
|
# Reads parameters as input (leave blank for all keyboards/keymaps)
|
||||||
|
```
|
||||||
|
|
||||||
|
## FAQ
|
||||||
|
|
||||||
|
### Why can't I flash on Windows/macOS
|
||||||
|
|
||||||
|
On Windows and macOS, it requires [Docker Machine](http://gw.tnode.com/docker/docker-machine-with-usb-support-on-windows-macos/) to be running. This is tedious to set up, so it's not recommended; use [QMK Toolbox](https://github.com/qmk/qmk_toolbox) instead.
|
||||||
|
|
||||||
|
!> Docker for Windows requires [Hyper-V](https://docs.microsoft.com/en-us/virtualization/hyper-v-on-windows/quick-start/enable-hyper-v) to be enabled. This means that it cannot work on versions of Windows which don't have Hyper-V, such as Windows 7, Windows 8 and **Windows 10 Home**.
|
||||||
@@ -0,0 +1,65 @@
|
|||||||
|
# How to Use GitHub with QMK
|
||||||
|
|
||||||
|
GitHub can be a little tricky to those that aren't familiar with it - this guide will walk through each step of forking, cloning, and submitting a pull request with QMK.
|
||||||
|
|
||||||
|
?> This guide assumes you're somewhat comfortable with running things at the command line, and have git installed on your system.
|
||||||
|
|
||||||
|
Start on the [QMK GitHub page](https://github.com/qmk/qmk_firmware), and you'll see a button in the upper right that says "Fork":
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
If you're a part of an organization, you'll need to choose which account to fork it to. In most circumstances, you'll want to fork it to your personal account. Once your fork is completed (sometimes this takes a little while), click the "Clone or Download" button:
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
And be sure to select "HTTPS", and select the link and copy it:
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
From here, enter `git clone --recurse-submodules ` into the command line, and then paste your link:
|
||||||
|
|
||||||
|
```
|
||||||
|
user@computer:~$ git clone --recurse-submodules https://github.com/whoeveryouare/qmk_firmware.git
|
||||||
|
Cloning into 'qmk_firmware'...
|
||||||
|
remote: Enumerating objects: 9, done.
|
||||||
|
remote: Counting objects: 100% (9/9), done.
|
||||||
|
remote: Compressing objects: 100% (5/5), done.
|
||||||
|
remote: Total 183883 (delta 5), reused 4 (delta 4), pack-reused 183874
|
||||||
|
Receiving objects: 100% (183883/183883), 132.90 MiB | 9.57 MiB/s, done.
|
||||||
|
Resolving deltas: 100% (119972/119972), done.
|
||||||
|
...
|
||||||
|
Submodule path 'lib/chibios': checked out '587968d6cbc2b0e1c7147540872f2a67e59ca18b'
|
||||||
|
Submodule path 'lib/chibios-contrib': checked out 'ede48346eee4b8d6847c19bc01420bee76a5e486'
|
||||||
|
Submodule path 'lib/googletest': checked out 'ec44c6c1675c25b9827aacd08c02433cccde7780'
|
||||||
|
Submodule path 'lib/lufa': checked out 'ce10f7642b0459e409839b23cc91498945119b4d'
|
||||||
|
Submodule path 'lib/ugfx': checked out '3e97b74e03c93631cdd3ddb2ce43b963fdce19b2'
|
||||||
|
```
|
||||||
|
|
||||||
|
You now have your QMK fork on your local machine, and you can add your keymap, compile it and flash it to your board. Once you're happy with your changes, you can add, commit, and push them to your fork like this:
|
||||||
|
|
||||||
|
```
|
||||||
|
user@computer:~$ git add .
|
||||||
|
user@computer:~$ git commit -m "adding my keymap"
|
||||||
|
[master cccb1608] adding my keymap
|
||||||
|
1 file changed, 1 insertion(+)
|
||||||
|
create mode 100644 keyboards/planck/keymaps/mine/keymap.c
|
||||||
|
user@computer:~$ git push
|
||||||
|
Counting objects: 1, done.
|
||||||
|
Delta compression using up to 4 threads.
|
||||||
|
Compressing objects: 100% (1/1), done.
|
||||||
|
Writing objects: 100% (1/1), 1.64 KiB | 0 bytes/s, done.
|
||||||
|
Total 1 (delta 1), reused 0 (delta 0)
|
||||||
|
remote: Resolving deltas: 100% (1/1), completed with 1 local objects.
|
||||||
|
To https://github.com/whoeveryouare/qmk_firmware.git
|
||||||
|
+ 20043e64...7da94ac5 master -> master
|
||||||
|
```
|
||||||
|
|
||||||
|
Your changes now exist on your fork on GitHub - if you go back there (`https://github.com/<whoeveryouare>/qmk_firmware`), you can create a "New Pull Request" by clicking this button:
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
Here you'll be able to see exactly what you've committed - if it all looks good, you can finalize it by clicking "Create Pull Request":
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
After submitting, we may talk to you about your changes, ask that you make changes, and eventually accept it! Thanks for contributing to QMK :)
|
||||||
@@ -20,7 +20,6 @@ The "easy" way to flash the firmware is using a tool from your host OS:
|
|||||||
|
|
||||||
* [QMK Toolbox](https://github.com/qmk/qmk_toolbox) (recommended)
|
* [QMK Toolbox](https://github.com/qmk/qmk_toolbox) (recommended)
|
||||||
* [Teensy Loader](https://www.pjrc.com/teensy/loader.html)
|
* [Teensy Loader](https://www.pjrc.com/teensy/loader.html)
|
||||||
* [Atmel FLIP](http://www.atmel.com/tools/flip.aspx)
|
|
||||||
|
|
||||||
If you want to program via the command line you can uncomment the ['modifyvm'] lines in the Vagrantfile to enable the USB passthrough into Linux and then program using the command line tools like dfu-util/dfu-programmer or you can install the Teensy CLI version.
|
If you want to program via the command line you can uncomment the ['modifyvm'] lines in the Vagrantfile to enable the USB passthrough into Linux and then program using the command line tools like dfu-util/dfu-programmer or you can install the Teensy CLI version.
|
||||||
|
|
||||||
|
|||||||
@@ -61,10 +61,76 @@ This file is used by the [QMK API](https://github.com/qmk/qmk_api). It contains
|
|||||||
|
|
||||||
All projects need to have a `config.h` file that sets things like the matrix size, product name, USB VID/PID, description and other settings. In general, use this file to set essential information and defaults for your keyboard that will always work.
|
All projects need to have a `config.h` file that sets things like the matrix size, product name, USB VID/PID, description and other settings. In general, use this file to set essential information and defaults for your keyboard that will always work.
|
||||||
|
|
||||||
|
The `config.h` files can also be placed in sub-folders, and the order in which they are read is as follows:
|
||||||
|
|
||||||
|
* `keyboards/top_folder/config.h`
|
||||||
|
* `keyboards/top_folder/sub_1/config.h`
|
||||||
|
* `keyboards/top_folder/sub_1/sub_2/config.h`
|
||||||
|
* `keyboards/top_folder/sub_1/sub_2/sub_3/config.h`
|
||||||
|
* `keyboards/top_folder/sub_1/sub_2/sub_3/sub_4/config.h`
|
||||||
|
* `users/a_user_folder/config.h`
|
||||||
|
* `keyboards/top_folder/keymaps/a_keymap/config.h`
|
||||||
|
* `keyboards/top_folder/sub_1/sub_2/sub_3/sub_4/post_config.h`
|
||||||
|
* `keyboards/top_folder/sub_1/sub_2/sub_3/post_config.h`
|
||||||
|
* `keyboards/top_folder/sub_1/sub_2/post_config.h`
|
||||||
|
* `keyboards/top_folder/sub_1/post_config.h`
|
||||||
|
* `keyboards/top_folder/post_config.h`
|
||||||
|
|
||||||
|
The `post_config.h` file can be used for additional post-processing, depending on what is specified in the `config.h` file. For example, if you define the `IOS_DEVICE_ENABLE` macro in your keymap-level `config.h` file as follows, you can configure more detailed settings accordingly in the `post_config.h` file:
|
||||||
|
|
||||||
|
* `keyboards/top_folder/keymaps/a_keymap/config.h`
|
||||||
|
```c
|
||||||
|
#define IOS_DEVICE_ENABLE
|
||||||
|
```
|
||||||
|
* `keyboards/top_folder/post_config.h`
|
||||||
|
```c
|
||||||
|
#ifndef IOS_DEVICE_ENABLE
|
||||||
|
// USB_MAX_POWER_CONSUMPTION value for this keyboard
|
||||||
|
#define USB_MAX_POWER_CONSUMPTION 400
|
||||||
|
#else
|
||||||
|
// fix iPhone and iPad power adapter issue
|
||||||
|
// iOS device need lessthan 100
|
||||||
|
#define USB_MAX_POWER_CONSUMPTION 100
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef RGBLIGHT_ENABLE
|
||||||
|
#ifndef IOS_DEVICE_ENABLE
|
||||||
|
#define RGBLIGHT_LIMIT_VAL 200
|
||||||
|
#define RGBLIGHT_VAL_STEP 17
|
||||||
|
#else
|
||||||
|
#define RGBLIGHT_LIMIT_VAL 35
|
||||||
|
#define RGBLIGHT_VAL_STEP 4
|
||||||
|
#endif
|
||||||
|
#ifndef RGBLIGHT_HUE_STEP
|
||||||
|
#define RGBLIGHT_HUE_STEP 10
|
||||||
|
#endif
|
||||||
|
#ifndef RGBLIGHT_SAT_STEP
|
||||||
|
#define RGBLIGHT_SAT_STEP 17
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
```
|
||||||
|
|
||||||
|
?> If you define options using `post_config.h` as in the above example, you should not define the same options in the keyboard- or user-level `config.h`.
|
||||||
|
|
||||||
### `rules.mk`
|
### `rules.mk`
|
||||||
|
|
||||||
The presence of this file means that the folder is a keyboard target and can be used in `make` commands. This is where you setup the build environment for your keyboard and configure the default set of features.
|
The presence of this file means that the folder is a keyboard target and can be used in `make` commands. This is where you setup the build environment for your keyboard and configure the default set of features.
|
||||||
|
|
||||||
|
The `rules.mk` file can also be placed in a sub-folder, and its reading order is as follows:
|
||||||
|
|
||||||
|
* `keyboards/top_folder/rules.mk`
|
||||||
|
* `keyboards/top_folder/sub_1/rules.mk`
|
||||||
|
* `keyboards/top_folder/sub_1/sub_2/rules.mk`
|
||||||
|
* `keyboards/top_folder/sub_1/sub_2/sub_3/rules.mk`
|
||||||
|
* `keyboards/top_folder/sub_1/sub_2/sub_3/sub_4/rules.mk`
|
||||||
|
* `keyboards/top_folder/keymaps/a_keymap/rules.mk`
|
||||||
|
* `users/a_user_folder/rules.mk`
|
||||||
|
* `common_features.mk`
|
||||||
|
|
||||||
|
Many of the settings written in the `rules.mk` file are interpreted by `common_features.mk`, which sets the necessary source files and compiler options.
|
||||||
|
|
||||||
|
?> See `build_keyboard.mk` and `common_features.mk` for more details.
|
||||||
|
|
||||||
### `<keyboard_name.c>`
|
### `<keyboard_name.c>`
|
||||||
|
|
||||||
This is where you will write custom code for your keyboard. Typically you will write code to initialize and interface with the hardware in your keyboard. If your keyboard consists of only a key matrix with no LEDs, speakers, or other auxiliary hardware this file can be blank.
|
This is where you will write custom code for your keyboard. Typically you will write code to initialize and interface with the hardware in your keyboard. If your keyboard consists of only a key matrix with no LEDs, speakers, or other auxiliary hardware this file can be blank.
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ QMK (*Quantum Mechanical Keyboard*) היא קהילת קוד פתוח (open sour
|
|||||||
|
|
||||||
## איך להשיג אותה
|
## איך להשיג אותה
|
||||||
|
|
||||||
אם אתם מתכננים לתרום מיפוי מקשים, מקלדת או יכולת ל QMK, הדבר הקל ביותר הוא [לעשות פורק לריפו בGithub](https://github.com/qmk/qmk_firmware#fork-destination-box), ולעשות קלון לריפו בסביבה המקומית ושם לבצע את השינויים שלכם, לדחוף אותם ולפתוח [Pull Request](https://github.com/qmk/qmk_firmware/pulls) מהפורק שלך.
|
אם אתם מתכננים לתרום מיפוי מקשים, מקלדת או יכולת ל QMK, הדבר הקל ביותר הוא [לעשות פורק לריפו בGitHub](https://github.com/qmk/qmk_firmware#fork-destination-box), ולעשות קלון לריפו בסביבה המקומית ושם לבצע את השינויים שלכם, לדחוף אותם ולפתוח [Pull Request](https://github.com/qmk/qmk_firmware/pulls) מהפורק שלך.
|
||||||
|
|
||||||
אחרת, אפשר להוריד את הקושחה באופן ישיר ([zip](https://github.com/qmk/qmk_firmware/zipball/master), [tar](https://github.com/qmk/qmk_firmware/tarball/master)), או לשכפל אותה באמצעות git (`[email protected]:qmk/qmk_firmware.git`), או https (`https://github.com/qmk/qmk_firmware.git`).
|
אחרת, אפשר להוריד את הקושחה באופן ישיר ([zip](https://github.com/qmk/qmk_firmware/zipball/master), [tar](https://github.com/qmk/qmk_firmware/tarball/master)), או לשכפל אותה באמצעות git (`[email protected]:qmk/qmk_firmware.git`), או https (`https://github.com/qmk/qmk_firmware.git`).
|
||||||
|
|
||||||
|
|||||||
@@ -5,7 +5,7 @@
|
|||||||
* [מקורות ללמידה](he-il/newbs_learn_more_resources.md)
|
* [מקורות ללמידה](he-il/newbs_learn_more_resources.md)
|
||||||
* [בסיס QMK](he-il/README.md)
|
* [בסיס QMK](he-il/README.md)
|
||||||
* [מבוא לQMK](he-il/getting_started_introduction.md)
|
* [מבוא לQMK](he-il/getting_started_introduction.md)
|
||||||
* [איך להשתמש בGithub](he-il/getting_started_github.md)
|
* [איך להשתמש בGitHub](he-il/getting_started_github.md)
|
||||||
* [קבלת עזרה](he-il/getting_started_getting_help.md)
|
* [קבלת עזרה](he-il/getting_started_getting_help.md)
|
||||||
* [שאלות נפוצות](he-il/faq.md)
|
* [שאלות נפוצות](he-il/faq.md)
|
||||||
* [שאלות נפוצות כלליות](he-il/faq_general.md)
|
* [שאלות נפוצות כלליות](he-il/faq_general.md)
|
||||||
@@ -27,7 +27,7 @@
|
|||||||
* [QMK CLI](he-il/cli.md)
|
* [QMK CLI](he-il/cli.md)
|
||||||
* [QMK CLI Config](he-il/cli_configuration.md)
|
* [QMK CLI Config](he-il/cli_configuration.md)
|
||||||
* [תרומה ל QMK](he-il/contributing.md)
|
* [תרומה ל QMK](he-il/contributing.md)
|
||||||
* [איך להשתמש בGithub](he-il/getting_started_github.md)
|
* [איך להשתמש בGitHub](he-il/getting_started_github.md)
|
||||||
* [קבלת עזרה](he-il/getting_started_getting_help.md)
|
* [קבלת עזרה](he-il/getting_started_getting_help.md)
|
||||||
|
|
||||||
* [שינויים משמעותיים](he-il/breaking_changes.md)
|
* [שינויים משמעותיים](he-il/breaking_changes.md)
|
||||||
@@ -114,6 +114,7 @@
|
|||||||
* [מדריך לצריבת ISP](he-il/isp_flashing_guide.md)
|
* [מדריך לצריבת ISP](he-il/isp_flashing_guide.md)
|
||||||
* [מדריך לדיבאגינג ARM](he-il/arm_debugging.md)
|
* [מדריך לדיבאגינג ARM](he-il/arm_debugging.md)
|
||||||
* [מנהל התקן I2C](he-il/i2c_driver.md)
|
* [מנהל התקן I2C](he-il/i2c_driver.md)
|
||||||
|
* [מנהל התקן SPI](he-il/spi_driver.md)
|
||||||
* [בקרת GPIO](he-il/internals_gpio_control.md)
|
* [בקרת GPIO](he-il/internals_gpio_control.md)
|
||||||
* [המרת Proton C](he-il/proton_c_conversion.md)
|
* [המרת Proton C](he-il/proton_c_conversion.md)
|
||||||
|
|
||||||
|
|||||||
@@ -11,7 +11,7 @@
|
|||||||
|
|
||||||
הפורום הרשמי של QMK נמצא ב - [/r/olkb](https://reddit.com/r/olkb) באתר [reddit.com](https://reddit.com).
|
הפורום הרשמי של QMK נמצא ב - [/r/olkb](https://reddit.com/r/olkb) באתר [reddit.com](https://reddit.com).
|
||||||
|
|
||||||
## סוגיות Github
|
## סוגיות GitHub
|
||||||
|
|
||||||
ניתן לפתוח [סוגייה ב-GitHub](https://github.com/qmk/qmk_firmware/issues). הדבר שימושי במיוחד כאשר הסוגיה דורשת דיון עמוק וארוך או דיבאגינג.
|
ניתן לפתוח [סוגייה ב-GitHub](https://github.com/qmk/qmk_firmware/issues). הדבר שימושי במיוחד כאשר הסוגיה דורשת דיון עמוק וארוך או דיבאגינג.
|
||||||
</div>
|
</div>
|
||||||
@@ -1,17 +1,17 @@
|
|||||||
<div dir="rtl" markdown="1">
|
<div dir="rtl" markdown="1">
|
||||||
# איך להשתמש ב-Github עם QMK
|
# איך להשתמש ב-GitHub עם QMK
|
||||||
|
|
||||||
Github עלול להיות קצת טריקי למי שלא מכיר את העבודה איתו - מדריך זה ילווה אתכם שלב אחר שלב דרך ביצוע פעולות fork, clone ו-pull request עם QMK.
|
GitHub עלול להיות קצת טריקי למי שלא מכיר את העבודה איתו - מדריך זה ילווה אתכם שלב אחר שלב דרך ביצוע פעולות fork, clone ו-pull request עם QMK.
|
||||||
|
|
||||||
?> מדריך זה מניח שאתם מרגישים בנוח עם הרצה של פקודות בסביבת command line (שורת הפקודה) ו-git מותקן במערכת שלכם.
|
?> מדריך זה מניח שאתם מרגישים בנוח עם הרצה של פקודות בסביבת command line (שורת הפקודה) ו-git מותקן במערכת שלכם.
|
||||||
|
|
||||||
התחילו ב- [עמוד של QMK ב-Github](https://github.com/qmk/qmk_firmware), ותצמאו כפתור בחלק העליון מימין עם התיכוב "Fork":
|
התחילו ב- [עמוד של QMK ב-GitHub](https://github.com/qmk/qmk_firmware), ותצמאו כפתור בחלק העליון מימין עם התיכוב "Fork":
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
אם אתם חלק מארגון, תצטרכו לבחור לאיזה חשבון לבצע פעולת fork. ברוב המבקרים, תרצו לבצע fork לתוך החשבון הפרטי שלכם. ברגע שה-fork הסתיים (לפעמים זה יכול לקחת קצת זמן) הקליקו על כפתור ה-"Clone or Download":
|
אם אתם חלק מארגון, תצטרכו לבחור לאיזה חשבון לבצע פעולת fork. ברוב המבקרים, תרצו לבצע fork לתוך החשבון הפרטי שלכם. ברגע שה-fork הסתיים (לפעמים זה יכול לקחת קצת זמן) הקליקו על כפתור ה-"Clone or Download":
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
תוודאו שאתם בוחרים באופצייה של "HTTPS", בחרו את הקישור והעתיקו אותו:
|
תוודאו שאתם בוחרים באופצייה של "HTTPS", בחרו את הקישור והעתיקו אותו:
|
||||||
|
|
||||||
|
|||||||
+35
-22
@@ -1,33 +1,46 @@
|
|||||||
# I2C Master Driver
|
# I2C Master Driver :id=i2c-master-driver
|
||||||
|
|
||||||
The I2C Master drivers used in QMK have a set of common functions to allow portability between MCUs.
|
The I2C Master drivers used in QMK have a set of common functions to allow portability between MCUs.
|
||||||
|
|
||||||
## Available functions
|
## An important note on I2C Addresses :id=note-on-i2c-addresses
|
||||||
|
|
||||||
|
All of the addresses expected by this driver should be pushed to the upper 7 bits of the address byte. Setting
|
||||||
|
the lower bit (indicating read/write) will be done by the respective functions. Almost all I2C addresses listed
|
||||||
|
on datasheets and the internet will be represented as 7 bits occupying the lower 7 bits and will need to be
|
||||||
|
shifted to the left (more significant) by one bit. This is easy to do via the bitwise shift operator `<< 1`.
|
||||||
|
|
||||||
|
You can either do this on each call to the functions below, or once in your definition of the address. For example if your device has an address of `0x18`:
|
||||||
|
|
||||||
|
`#define MY_I2C_ADDRESS (0x18 << 1)`
|
||||||
|
|
||||||
|
See https://www.robot-electronics.co.uk/i2c-tutorial for more information about I2C addressing and other technical details.
|
||||||
|
|
||||||
|
## Available functions :id=available-functions
|
||||||
|
|
||||||
|Function |Description |
|
|Function |Description |
|
||||||
|------------------------------------------------------------------------------------------------------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
|
|------------------------------------------------------------------------------------------------------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
|
||||||
|`void i2c_init(void);` |Initializes the I2C driver. This function should be called once before any transaction is initiated. |
|
|`void i2c_init(void);` |Initializes the I2C driver. This function should be called once before any transaction is initiated. |
|
||||||
|`uint8_t i2c_start(uint8_t address, uint16_t timeout);` |Starts an I2C transaction. Address is the 7-bit slave address without the direction bit. |
|
|`i2c_status_t i2c_start(uint8_t address, uint16_t timeout);` |Starts an I2C transaction. Address is the 7-bit slave address without the direction bit. |
|
||||||
|`uint8_t i2c_transmit(uint8_t address, uint8_t* data, uint16_t length, uint16_t timeout);` |Transmit data over I2C. Address is the 7-bit slave address without the direction. Returns status of transaction. |
|
|`i2c_status_t i2c_transmit(uint8_t address, uint8_t* data, uint16_t length, uint16_t timeout);` |Transmit data over I2C. Address is the 7-bit slave address without the direction. Returns status of transaction. |
|
||||||
|`uint8_t i2c_receive(uint8_t address, uint8_t* data, uint16_t length, uint16_t timeout);` |Receive data over I2C. Address is the 7-bit slave address without the direction. Saves number of bytes specified by `length` in `data` array. Returns status of transaction. |
|
|`i2c_status_t i2c_receive(uint8_t address, uint8_t* data, uint16_t length, uint16_t timeout);` |Receive data over I2C. Address is the 7-bit slave address without the direction. Saves number of bytes specified by `length` in `data` array. Returns status of transaction. |
|
||||||
|`uint8_t i2c_writeReg(uint8_t devaddr, uint8_t regaddr, uint8_t* data, uint16_t length, uint16_t timeout);` |Same as the `i2c_transmit` function but `regaddr` sets where in the slave the data will be written. |
|
|`i2c_status_t i2c_writeReg(uint8_t devaddr, uint8_t regaddr, uint8_t* data, uint16_t length, uint16_t timeout);` |Same as the `i2c_transmit` function but `regaddr` sets where in the slave the data will be written. |
|
||||||
|`uint8_t i2c_readReg(uint8_t devaddr, uint8_t regaddr, uint8_t* data, uint16_t length, uint16_t timeout);` |Same as the `i2c_receive` function but `regaddr` sets from where in the slave the data will be read. |
|
|`i2c_status_t i2c_readReg(uint8_t devaddr, uint8_t regaddr, uint8_t* data, uint16_t length, uint16_t timeout);` |Same as the `i2c_receive` function but `regaddr` sets from where in the slave the data will be read. |
|
||||||
|`uint8_t i2c_stop(void);` |Ends an I2C transaction. |
|
|`i2c_status_t i2c_stop(void);` |Ends an I2C transaction. |
|
||||||
|
|
||||||
### Function Return
|
### Function Return :id=function-return
|
||||||
|
|
||||||
All the above functions, except `void i2c_init(void);` return the following truth table:
|
All the above functions, except `void i2c_init(void);` return the following truth table:
|
||||||
|
|
||||||
|Return Value |Description |
|
|Return Constant |Value|Description |
|
||||||
|---------------|---------------------------------------------------|
|
|--------------------|-----|--------------------------------|
|
||||||
|0 |Operation executed successfully. |
|
|`I2C_STATUS_SUCCESS`|0 |Operation executed successfully.|
|
||||||
|-1 |Operation failed. |
|
|`I2C_STATUS_ERROR` |-1 |Operation failed. |
|
||||||
|-2 |Operation timed out. |
|
|`I2C_STATUS_TIMEOUT`|-2 |Operation timed out. |
|
||||||
|
|
||||||
|
|
||||||
## AVR
|
## AVR :id=avr
|
||||||
|
|
||||||
### Configuration
|
### Configuration :id=avr-configuration
|
||||||
|
|
||||||
The following defines can be used to configure the I2C master driver.
|
The following defines can be used to configure the I2C master driver.
|
||||||
|
|
||||||
@@ -37,12 +50,12 @@ The following defines can be used to configure the I2C master driver.
|
|||||||
|
|
||||||
AVRs usually have set GPIO which turn into I2C pins, therefore no further configuration is required.
|
AVRs usually have set GPIO which turn into I2C pins, therefore no further configuration is required.
|
||||||
|
|
||||||
## ARM
|
## ARM :id=arm
|
||||||
|
|
||||||
For ARM the Chibios I2C HAL driver is under the hood.
|
For ARM the Chibios I2C HAL driver is under the hood.
|
||||||
This section assumes an STM32 MCU.
|
This section assumes an STM32 MCU.
|
||||||
|
|
||||||
### Configuration
|
### Configuration :id=arm-configuration
|
||||||
|
|
||||||
The configuration for ARM MCUs can be quite complex as often there are multiple I2C drivers which can be assigned to a variety of ports.
|
The configuration for ARM MCUs can be quite complex as often there are multiple I2C drivers which can be assigned to a variety of ports.
|
||||||
|
|
||||||
@@ -77,7 +90,7 @@ The ChibiOS I2C driver configuration depends on STM32 MCU:
|
|||||||
STM32F1xx, STM32F2xx, STM32F4xx, STM32L0xx and STM32L1xx use I2Cv1;
|
STM32F1xx, STM32F2xx, STM32F4xx, STM32L0xx and STM32L1xx use I2Cv1;
|
||||||
STM32F0xx, STM32F3xx, STM32F7xx and STM32L4xx use I2Cv2;
|
STM32F0xx, STM32F3xx, STM32F7xx and STM32L4xx use I2Cv2;
|
||||||
|
|
||||||
#### I2Cv1
|
#### I2Cv1 :id=i2cv1
|
||||||
STM32 MCUs allow for different clock and duty parameters when configuring I2Cv1. These can be modified using the following parameters, using <https://www.playembedded.org/blog/stm32-i2c-chibios/#I2Cv1_configuration_structure> as a reference:
|
STM32 MCUs allow for different clock and duty parameters when configuring I2Cv1. These can be modified using the following parameters, using <https://www.playembedded.org/blog/stm32-i2c-chibios/#I2Cv1_configuration_structure> as a reference:
|
||||||
|
|
||||||
| Variable | Default |
|
| Variable | Default |
|
||||||
@@ -86,7 +99,7 @@ STM32 MCUs allow for different clock and duty parameters when configuring I2Cv1.
|
|||||||
| `I2C1_CLOCK_SPEED` | `100000` |
|
| `I2C1_CLOCK_SPEED` | `100000` |
|
||||||
| `I2C1_DUTY_CYCLE` | `STD_DUTY_CYCLE` |
|
| `I2C1_DUTY_CYCLE` | `STD_DUTY_CYCLE` |
|
||||||
|
|
||||||
#### I2Cv2
|
#### I2Cv2 :id=i2cv2
|
||||||
STM32 MCUs allow for different timing parameters when configuring I2Cv2. These can be modified using the following parameters, using <https://www.st.com/en/embedded-software/stsw-stm32126.html> as a reference:
|
STM32 MCUs allow for different timing parameters when configuring I2Cv2. These can be modified using the following parameters, using <https://www.st.com/en/embedded-software/stsw-stm32126.html> as a reference:
|
||||||
|
|
||||||
| Variable | Default |
|
| Variable | Default |
|
||||||
@@ -104,10 +117,10 @@ STM32 MCUs allow for different "alternate function" modes when configuring GPIO
|
|||||||
| `I2C1_SCL_PAL_MODE` | `4` |
|
| `I2C1_SCL_PAL_MODE` | `4` |
|
||||||
| `I2C1_SDA_PAL_MODE` | `4` |
|
| `I2C1_SDA_PAL_MODE` | `4` |
|
||||||
|
|
||||||
#### Other
|
#### Other :id=other
|
||||||
You can also overload the `void i2c_init(void)` function, which has a weak attribute. If you do this the configuration variables above will not be used. Please consult the datasheet of your MCU for the available GPIO configurations. The following is an example initialization function:
|
You can also overload the `void i2c_init(void)` function, which has a weak attribute. If you do this the configuration variables above will not be used. Please consult the datasheet of your MCU for the available GPIO configurations. The following is an example initialization function:
|
||||||
|
|
||||||
```C
|
```c
|
||||||
void i2c_init(void)
|
void i2c_init(void)
|
||||||
{
|
{
|
||||||
setPinInput(B6); // Try releasing special pins for a short time
|
setPinInput(B6); // Try releasing special pins for a short time
|
||||||
|
|||||||
+5
-2
@@ -16,7 +16,8 @@
|
|||||||
<link rel="stylesheet" href="//unpkg.com/docsify/lib/themes/buble.css" title="light">
|
<link rel="stylesheet" href="//unpkg.com/docsify/lib/themes/buble.css" title="light">
|
||||||
<link rel="stylesheet" href="//unpkg.com/docsify/lib/themes/dark.css" media="(prefers-color-scheme: dark)">
|
<link rel="stylesheet" href="//unpkg.com/docsify/lib/themes/dark.css" media="(prefers-color-scheme: dark)">
|
||||||
<link rel="stylesheet" href="//unpkg.com/[email protected]/dist/toc.css">
|
<link rel="stylesheet" href="//unpkg.com/[email protected]/dist/toc.css">
|
||||||
<link rel="stylesheet" href="sidebar.css" />
|
<link rel="stylesheet" href="qmk_custom_light.css">
|
||||||
|
<link rel="stylesheet" href="qmk_custom_dark.css" media="(prefers-color-scheme: dark)">
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<div id="app"></div>
|
<div id="app"></div>
|
||||||
@@ -31,7 +32,8 @@
|
|||||||
|
|
||||||
// Moved pages
|
// Moved pages
|
||||||
'/adding_a_keyboard_to_qmk': '/hardware_keyboard_guidelines',
|
'/adding_a_keyboard_to_qmk': '/hardware_keyboard_guidelines',
|
||||||
'/build_environment_setup': '/getting_started_build_tools',
|
'/build_environment_setup': '/newbs_getting_started',
|
||||||
|
'/cli_dev_configuration': '/cli_configuration',
|
||||||
'/dynamic_macros': '/feature_dynamic_macros',
|
'/dynamic_macros': '/feature_dynamic_macros',
|
||||||
'/feature_common_shortcuts': '/feature_advanced_keycodes',
|
'/feature_common_shortcuts': '/feature_advanced_keycodes',
|
||||||
'/glossary': '/reference_glossary',
|
'/glossary': '/reference_glossary',
|
||||||
@@ -43,6 +45,7 @@
|
|||||||
'/tap_dance': '/feature_tap_dance',
|
'/tap_dance': '/feature_tap_dance',
|
||||||
'/unicode': '/feature_unicode',
|
'/unicode': '/feature_unicode',
|
||||||
'/python_development': '/cli_development',
|
'/python_development': '/cli_development',
|
||||||
|
'/getting_started_build_tools':'/newbs_getting_started',
|
||||||
},
|
},
|
||||||
basePath: '/',
|
basePath: '/',
|
||||||
name: 'QMK Firmware',
|
name: 'QMK Firmware',
|
||||||
|
|||||||
@@ -1,22 +1,23 @@
|
|||||||
# GPIO Control
|
# GPIO Control :id=gpio-control
|
||||||
|
|
||||||
QMK has a GPIO control abstraction layer which is microcontroller agnostic. This is done to allow easy access to pin control across different platforms.
|
QMK has a GPIO control abstraction layer which is microcontroller agnostic. This is done to allow easy access to pin control across different platforms.
|
||||||
|
|
||||||
## Functions
|
## Functions :id=functions
|
||||||
|
|
||||||
The following functions can provide basic control of GPIOs and are found in `quantum/quantum.h`.
|
The following functions can provide basic control of GPIOs and are found in `quantum/quantum.h`.
|
||||||
|
|
||||||
|Function |Description | Old AVR Examples | Old ChibiOS/ARM Examples |
|
|Function |Description | Old AVR Examples | Old ChibiOS/ARM Examples |
|
||||||
|----------------------|------------------------------------------------------------------|------------------------------------------------|-------------------------------------------------|
|
|------------------------|--------------------------------------------------|-------------------------------------------------|-------------------------------------------------|
|
||||||
|`setPinInput(pin)` |Set pin as input with high impedance (High-Z) | `DDRB &= ~(1<<2)` | `palSetLineMode(pin, PAL_MODE_INPUT)` |
|
| `setPinInput(pin)` | Set pin as input with high impedance (High-Z) | `DDRB &= ~(1<<2)` | `palSetLineMode(pin, PAL_MODE_INPUT)` |
|
||||||
|`setPinInputHigh(pin)`|Set pin as input with builtin pull-up resistor | `DDRB &= ~(1<<2); PORTB \|= (1<<2)` | `palSetLineMode(pin, PAL_MODE_INPUT_PULLUP)` |
|
| `setPinInputHigh(pin)` | Set pin as input with builtin pull-up resistor | `DDRB &= ~(1<<2); PORTB \|= (1<<2)` | `palSetLineMode(pin, PAL_MODE_INPUT_PULLUP)` |
|
||||||
|`setPinInputLow(pin)` |Set pin as input with builtin pull-down resistor | N/A (Not supported on AVR) | `palSetLineMode(pin, PAL_MODE_INPUT_PULLDOWN)` |
|
| `setPinInputLow(pin)` | Set pin as input with builtin pull-down resistor | N/A (Not supported on AVR) | `palSetLineMode(pin, PAL_MODE_INPUT_PULLDOWN)` |
|
||||||
|`setPinOutput(pin)` |Set pin as output | `DDRB \|= (1<<2)` | `palSetLineMode(pin, PAL_MODE_OUTPUT_PUSHPULL)` |
|
| `setPinOutput(pin)` | Set pin as output | `DDRB \|= (1<<2)` | `palSetLineMode(pin, PAL_MODE_OUTPUT_PUSHPULL)` |
|
||||||
|`writePinHigh(pin)` |Set pin level as high, assuming it is an output | `PORTB \|= (1<<2)` | `palSetLine(pin)` |
|
| `writePinHigh(pin)` | Set pin level as high, assuming it is an output | `PORTB \|= (1<<2)` | `palSetLine(pin)` |
|
||||||
|`writePinLow(pin)` |Set pin level as low, assuming it is an output | `PORTB &= ~(1<<2)` | `palClearLine(pin)` |
|
| `writePinLow(pin)` | Set pin level as low, assuming it is an output | `PORTB &= ~(1<<2)` | `palClearLine(pin)` |
|
||||||
|`writePin(pin, level)`|Set pin level, assuming it is an output | `(level) ? PORTB \|= (1<<2) : PORTB &= ~(1<<2)` | `(level) ? palSetLine(pin) : palClearLine(pin)` |
|
| `writePin(pin, level)` | Set pin level, assuming it is an output | `(level) ? PORTB \|= (1<<2) : PORTB &= ~(1<<2)` | `(level) ? palSetLine(pin) : palClearLine(pin)` |
|
||||||
|`readPin(pin)` |Returns the level of the pin | `_SFR_IO8(pin >> 4) & _BV(pin & 0xF)` | `palReadLine(pin)` |
|
| `readPin(pin)` | Returns the level of the pin | `_SFR_IO8(pin >> 4) & _BV(pin & 0xF)` | `palReadLine(pin)` |
|
||||||
|
| `togglePin(pin)` | Invert pin level, assuming it is an output | `PORTB ^= (1<<2)` | `palToggleLine(pin)` |
|
||||||
|
|
||||||
## Advanced Settings
|
## Advanced Settings :id=advanced-settings
|
||||||
|
|
||||||
Each microcontroller can have multiple advanced settings regarding its GPIO. This abstraction layer does not limit the use of architecture-specific functions. Advanced users should consult the datasheet of their desired device and include any needed libraries. For AVR, the standard avr/io.h library is used; for STM32, the ChibiOS [PAL library](http://chibios.sourceforge.net/docs3/hal/group___p_a_l.html) is used.
|
Each microcontroller can have multiple advanced settings regarding its GPIO. This abstraction layer does not limit the use of architecture-specific functions. Advanced users should consult the datasheet of their desired device and include any needed libraries. For AVR, the standard avr/io.h library is used; for STM32, the ChibiOS [PAL library](http://chibios.sourceforge.net/docs3/hal/group___p_a_l.html) is used.
|
||||||
@@ -115,12 +115,18 @@ The simplest and quickest way to get things back to normal is to flash only a bo
|
|||||||
|
|
||||||
You can find the stock bootloaders in the [`util/` folder](https://github.com/qmk/qmk_firmware/tree/master/util). Be sure to flash the correct bootloader for your chip:
|
You can find the stock bootloaders in the [`util/` folder](https://github.com/qmk/qmk_firmware/tree/master/util). Be sure to flash the correct bootloader for your chip:
|
||||||
|
|
||||||
* [`atmega32u4`](https://github.com/qmk/qmk_firmware/blob/master/util/bootloader_atmega32u4_1_0_0.hex) - Most keyboards, Planck Rev 1-5, Preonic Rev 1-2
|
* **Atmel DFU**
|
||||||
* [`Pro Micro`](https://github.com/sparkfun/Arduino_Boards/blob/master/sparkfun/avr/bootloaders/caterina/Caterina-promicro16.hex) - The default bootloader for Pro Micro controllers
|
* [ATmega16U4](https://github.com/qmk/qmk_firmware/blob/master/util/bootloader_atmega16u4_1.0.1.hex)
|
||||||
* [`at90usb1286`](https://github.com/qmk/qmk_firmware/blob/master/util/bootloader_at90usb128x_1_0_1.hex) - Planck Light Rev 1
|
* [ATmega32U4](https://github.com/qmk/qmk_firmware/blob/master/util/bootloader_atmega32u4_1.0.0.hex)
|
||||||
* [`atmega32a`](https://github.com/qmk/qmk_firmware/blob/master/util/bootloader_atmega32a_1_0_0.hex) - jj40, and other V-USB/ps2avrGB keyboards
|
* [AT90USB64](https://github.com/qmk/qmk_firmware/blob/master/util/bootloader_at90usb64_1.0.0.hex)
|
||||||
|
* [AT90USB128](https://github.com/qmk/qmk_firmware/blob/master/util/bootloader_at90usb128_1.0.1.hex)
|
||||||
|
* **Caterina**
|
||||||
|
* [Pro Micro (5V/16MHz)](https://github.com/sparkfun/Arduino_Boards/blob/master/sparkfun/avr/bootloaders/caterina/Caterina-promicro16.hex)
|
||||||
|
* [Pro Micro (3.3V/8MHz)](https://github.com/sparkfun/Arduino_Boards/blob/master/sparkfun/avr/bootloaders/caterina/Caterina-promicro8.hex)
|
||||||
|
* **BootloadHID (PS2AVRGB)**
|
||||||
|
* [ATmega32A](https://github.com/qmk/qmk_firmware/blob/master/util/bootloader_ps2avrgb_bootloadhid_1.0.1.hex)
|
||||||
|
|
||||||
If you're not sure what your board uses, look in the `rules.mk` file for the keyboard in QMK. The `MCU =` line will have the value you need. It may differ between different versions of the board.
|
If you're not sure what your board uses, look in the `rules.mk` file for the keyboard in QMK. The `MCU` and `BOOTLOADER` lines will have the value you need. It may differ between different versions of the board.
|
||||||
|
|
||||||
### Production Techniques
|
### Production Techniques
|
||||||
|
|
||||||
|
|||||||
+25
-14
@@ -1,8 +1,8 @@
|
|||||||
# Quantum Mechanical Keyboard Firmware
|
# Quantum Mechanical Keyboard Firmware
|
||||||
|
|
||||||
<!---
|
<!---
|
||||||
original document: eae21eed7:docs/README.md
|
original document: 0.8.58:docs/README.md
|
||||||
git diff eae21eed7 HEAD -- docs/README.md | cat
|
git diff 0.8.58 HEAD -- docs/README.md | cat
|
||||||
-->
|
-->
|
||||||
|
|
||||||
[](https://github.com/qmk/qmk_firmware/tags)
|
[](https://github.com/qmk/qmk_firmware/tags)
|
||||||
@@ -12,26 +12,37 @@
|
|||||||
[](https://github.com/qmk/qmk_firmware/pulse/monthly)
|
[](https://github.com/qmk/qmk_firmware/pulse/monthly)
|
||||||
[](https://github.com/qmk/qmk_firmware/)
|
[](https://github.com/qmk/qmk_firmware/)
|
||||||
|
|
||||||
## QMK ファームウェアとは何か?
|
## QMK ファームウェアとは何でしょうか?
|
||||||
|
|
||||||
QMK (*Quantum Mechanical Keyboard*)は QMK ファームウェア、QMK ツールボックス、qmk.fm およびそれらのドキュメントを保守するオープンソースコミュニティです。QMK ファームウェアは[tmk\_keyboard](http://github.com/tmk/tmk_keyboard) を元にしたキーボードファームウェアで、Atmel AVR コントローラ、より具体的には [OLKB 製品](http://olkb.com)、[ErgoDox EZ](http://www.ergodox-ez.com) キーボードおよび [Clueboard 製品](http://clueboard.co/) のための幾つかの便利な機能を持ちます。また、ChibiOS を使って ARM チップに移植されています。これを使ってあなたの作った手配線のキーボードあるいはカスタムキーボード PCB で作ったキーボードを動かすことができます。
|
QMK (*Quantum Mechanical Keyboard*)は、コンピュータ入力デバイスの開発を中心としたオープンソースコミュニティです。コミュニティには、キーボード、マウス、MIDI デバイスなど、全ての種類の入力デバイスが含まれます。協力者の中心グループは、[QMK ファームウェア](https://github.com/qmk/qmk_firmware)、[QMK Configurator](https://config.qmk.fm)、[QMK ツールボックス](https://github.com/qmk/qmk_toolbox)、[qmk.fm](https://qmk.fm)、そして、このドキュメントを、あなたのようなコミュニティメンバーの助けを借りて保守しています。
|
||||||
|
|
||||||
## 入手方法
|
## 始めましょう
|
||||||
|
|
||||||
QMK のキーマップ、キーボード、機能に貢献をする予定がある場合、最も簡単なのは、[Github を介してリポジトリをフォークし](https://github.com/qmk/qmk_firmware#fork-destination-box)、リポジトリをあなたの開発環境にクローンして変更を加え、それらをプッシュし、[プルリクエスト](https://github.com/qmk/qmk_firmware/pulls)を開くことです。
|
QMK は初めてですか?始めるには2つの方法があります:
|
||||||
|
|
||||||
それ以外の場合は、`git clone https://github.com/qmk/qmk_firmware` を介して直接クローンすることができます。zip または tar ファイルをダウンロードしないでください。コンパイルするためのサブモジュールをダウンロードするために git リポジトリが必要です。
|
* 基本: [QMK Configurator](https://config.qmk.fm)
|
||||||
|
* ドロップダウンからあなたのキーボードを選択し、キーボードをプログラムします。
|
||||||
|
* 見ることができる [紹介ビデオ](https://www.youtube.com/watch?v=-imgglzDMdY) があります。
|
||||||
|
* 読むことができる概要 [ドキュメント](ja/newbs_building_firmware_configurator.md) があります。
|
||||||
|
* 発展: [ソースを使用します](ja/newbs.md)
|
||||||
|
* より強力ですが、使うのはより困難です。
|
||||||
|
|
||||||
## コンパイル方法
|
## 自分用にアレンジします
|
||||||
|
|
||||||
コンパイルをする前に、AVR または ARM 開発のための[環境をインストール](ja/getting_started_build_tools.md)する必要があります。それが完了したら、`make` コマンドを使用して、以下の表記でキーボードとキーマップをビルドします。
|
QMK には、探求すべき多くの[機能](ja/features.md)と、深く知るためのリファレンスドキュメントがたくさんあります。ほとんどの機能は[キーマップ](ja/keymap.md)を変更し、[キーコード](ja/keycodes.md)を変更することで活用されます。
|
||||||
|
|
||||||
make planck/rev4:default
|
## 手助けが必要ですか?
|
||||||
|
|
||||||
これは、`planck` の `rev4` リビジョンを `default` キーマップでビルドします。全てのキーボードにリビジョン(サブプロジェクトまたはフォルダとも呼ばれます)があるわけではありません。その場合は省略されます:
|
[サポートページ](ja/support.md) をチェックして、QMK の使い方について手助けを得る方法を確認してください。
|
||||||
|
|
||||||
make preonic:default
|
## 貢献する
|
||||||
|
|
||||||
## カスタマイズ方法
|
QMK コミュニティに貢献する方法はたくさんあります。始める最も簡単な方法は、それを使って友人に QMK という単語を広めることです。
|
||||||
|
|
||||||
QMK には、探求すべき多くの[機能](ja/features.md)と、深堀りするための[リファレンス ドキュメント](http://docs.qmk.fm)がたくさんあります。ほとんどの機能は[キーマップ](ja/keymap.md)を変更し、[キーコード](ja/keycodes.md)を変更することで活用されます。
|
* フォーラムやチャットルームで人々を支援します:
|
||||||
|
* [/r/olkb](https://www.reddit.com/r/olkb/)
|
||||||
|
* [Discord サーバ](https://discord.gg/Uq7gcHh)
|
||||||
|
* 下にある「Edit This Page」をクリックしてドキュメントに貢献します
|
||||||
|
* [ドキュメントをあなたの言語に翻訳します](ja/translating.md)
|
||||||
|
* [バグを報告します](https://github.com/qmk/qmk_firmware/issues/new/choose)
|
||||||
|
* [プルリクエストを開きます](ja/contributing.md)
|
||||||
+152
-119
@@ -1,130 +1,163 @@
|
|||||||
* [完全な初心者のガイド](ja/newbs.md)
|
* チュートリアル
|
||||||
* [はじめに](ja/newbs_getting_started.md)
|
* [入門](ja/newbs.md)
|
||||||
* [初めてのファームウェアの構築](ja/newbs_building_firmware.md)
|
* [セットアップ](ja/newbs_getting_started.md)
|
||||||
* [ファームウェアのフラッシュ](ja/newbs_flashing.md)
|
* [初めてのファームウェアの構築](ja/newbs_building_firmware.md)
|
||||||
* [テストとデバッグ](ja/newbs_testing_debugging.md)
|
* [ファームウェアのフラッシュ](ja/newbs_flashing.md)
|
||||||
* [QMK における Git 運用作法](ja/newbs_git_best_practices.md)
|
* [テストとデバッグ](ja/newbs_testing_debugging.md)
|
||||||
* [あなたのフォークの master ブランチ](ja/newbs_git_using_your_master_branch.md)
|
* [手助けを得る/サポート](ja/support.md)
|
||||||
* [マージの競合の解決](ja/newbs_git_resolving_merge_conflicts.md)
|
* [他のリソース](ja/newbs_learn_more_resources.md)
|
||||||
* [同期のとれていない git ブランチの再同期](ja/newbs_git_resynchronize_a_branch.md)
|
|
||||||
* [学習リソース](ja/newbs_learn_more_resources.md)
|
|
||||||
|
|
||||||
* [QMKの基本](ja/README.md)
|
* FAQ
|
||||||
* [QMK の導入](ja/getting_started_introduction.md)
|
* [一般的な FAQ](ja/faq_general.md)
|
||||||
* [QMK CLI](ja/cli.md)
|
* [QMK のビルド/コンパイル](ja/faq_build.md)
|
||||||
* [QMK CLI 設定](ja/cli_configuration.md)
|
* [QMK のデバッグ/トラブルシューティング](ja/faq_debug.md)
|
||||||
* [QMK への貢献](ja/contributing.md)
|
* [キーマップ FAQ](ja/faq_keymap.md)
|
||||||
* [Github の使い方](ja/getting_started_github.md)
|
* [用語](ja/reference_glossary.md)
|
||||||
* [ヘルプ](ja/getting_started_getting_help.md)
|
|
||||||
|
|
||||||
* [破壊的な変更](ja/breaking_changes.md)
|
* Configurator
|
||||||
* [プルリクエストにフラグが付けられた](ja/breaking_changes_instructions.md)
|
* [概要](ja/newbs_building_firmware_configurator.md)
|
||||||
* [2019年8月30日](ja/ChangeLog/20190830.md)
|
* [ステップ・バイ・ステップ](ja/configurator_step_by_step.md)
|
||||||
|
* [トラブルシューティング](ja/configurator_troubleshooting.md)
|
||||||
|
* QMK API
|
||||||
|
* [概要](ja/api_overview.md)
|
||||||
|
* [API ドキュメント](ja/api_docs.md)
|
||||||
|
* [キーボードサポート](ja/reference_configurator_support.md)
|
||||||
|
|
||||||
* [FAQ](ja/faq.md)
|
* CLI
|
||||||
* [一般的な FAQ](ja/faq_general.md)
|
* [概要](ja/cli.md)
|
||||||
* [QMK のビルド/コンパイル](ja/faq_build.md)
|
* [設定](ja/cli_configuration.md)
|
||||||
* [QMK のデバッグ/トラブルシューティング](ja/faq_debug.md)
|
* [コマンド](ja/cli_commands.md)
|
||||||
* [キーマップ](ja/faq_keymap.md)
|
|
||||||
* [Zadig を使ったドライバのインストール](ja/driver_installation_zadig.md)
|
|
||||||
|
|
||||||
* 詳細なガイド
|
* QMK を使う
|
||||||
* [ビルドツールのインストール](ja/getting_started_build_tools.md)
|
* ガイド
|
||||||
* [Vagrant のガイド](ja/getting_started_vagrant.md)
|
* [機能のカスタマイズ](ja/custom_quantum_functions.md)
|
||||||
* [ビルド/コンパイルの説明](ja/getting_started_make_guide.md)
|
* [Zadig を使ったドライバのインストール](ja/driver_installation_zadig.md)
|
||||||
* [ファームウェアのフラッシュ](ja/flashing.md)
|
* [キーマップの概要](ja/keymap.md)
|
||||||
* [機能のカスタマイズ](ja/custom_quantum_functions.md)
|
* [Vagrant のガイド](ja/getting_started_vagrant.md)
|
||||||
* [キーマップの概要](ja/keymap.md)
|
* 書き込み
|
||||||
|
* [書き込み](ja/flashing.md)
|
||||||
|
* [ATmega32A の書き込み (ps2avrgb)](ja/flashing_bootloadhid.md)
|
||||||
|
* IDE
|
||||||
|
* [Eclipse で QMK を使用](ja/other_eclipse.md)
|
||||||
|
* [VSCode で QMK を使用](ja/other_vscode.md)
|
||||||
|
* Git のベストプラクティス
|
||||||
|
* [入門](ja/newbs_git_best_practices.md)
|
||||||
|
* [フォーク](ja/newbs_git_using_your_master_branch.md)
|
||||||
|
* [マージの競合の解決](ja/newbs_git_resolving_merge_conflicts.md)
|
||||||
|
* [ブランチの修正](ja/newbs_git_resynchronize_a_branch.md)
|
||||||
|
* キーボードを作る
|
||||||
|
* [Hand Wiring ガイド](ja/hand_wire.md)
|
||||||
|
* [ISP 書き込みガイド](ja/isp_flashing_guide.md)
|
||||||
|
|
||||||
* [ハードウェア](ja/hardware.md)
|
* 単純なキーコード
|
||||||
* [互換性のあるマイクロコントローラ](ja/compatible_microcontrollers.md)
|
* [完全なリスト](ja/keycodes.md)
|
||||||
* [AVR プロセッサ](ja/hardware_avr.md)
|
* [基本的なキーコード](ja/keycodes_basic.md)
|
||||||
* [ドライバ](ja/hardware_drivers.md)
|
* [修飾キー](ja/feature_advanced_keycodes.md)
|
||||||
|
* [Quantum キーコード](ja/quantum_keycodes.md)
|
||||||
|
|
||||||
* リファレンス
|
* 高度なキーコード
|
||||||
* [キーボード ガイドライン](ja/hardware_keyboard_guidelines.md)
|
* [コマンド](ja/feature_command.md)
|
||||||
* [設定オプション](ja/config_options.md)
|
* [動的マクロ](ja/feature_dynamic_macros.md)
|
||||||
* [キーコード](ja/keycodes.md)
|
* [グレイブ エスケープ](ja/feature_grave_esc.md)
|
||||||
* [コーディング規約 - C](ja/coding_conventions_c.md)
|
* [リーダーキー](ja/feature_leader_key.md)
|
||||||
* [コーディング規約 - Python](ja/coding_conventions_python.md)
|
* [モッドタップ](ja/mod_tap.md)
|
||||||
* [ドキュメント ベストプラクティス](ja/documentation_best_practices.md)
|
* [マクロ](ja/feature_macros.md)
|
||||||
* [ドキュメント テンプレート](ja/documentation_templates.md)
|
* [マウスキー](ja/feature_mouse_keys.md)
|
||||||
* [用語](ja/reference_glossary.md)
|
* [Space Cadet Shift](ja/feature_space_cadet.md)
|
||||||
* [ユニットテスト](ja/unit_testing.md)
|
* [US ANSI シフトキー](ja/keycodes_us_ansi_shifted.md)
|
||||||
* [便利な関数](ja/ref_functions.md)
|
|
||||||
* [Configurator サポート](ja/reference_configurator_support.md)
|
|
||||||
* [info.json 形式](ja/reference_info_json.md)
|
|
||||||
* [Python CLI 開発](ja/cli_development.md)
|
|
||||||
|
|
||||||
* [機能](ja/features.md)
|
* ソフトウェア機能
|
||||||
* [基本的なキーコード](ja/keycodes_basic.md)
|
* [自動シフト](ja/feature_auto_shift.md)
|
||||||
* [US ANSI シフトキー](ja/keycodes_us_ansi_shifted.md)
|
* [コンボ](ja/feature_combo.md)
|
||||||
* [Quantum キーコード](ja/quantum_keycodes.md)
|
* [デバウンス API](ja/feature_debounce_type.md)
|
||||||
* [Advanced キーコード](ja/feature_advanced_keycodes.md)
|
* [キーロック](ja/feature_key_lock.md)
|
||||||
* [オーディオ](ja/feature_audio.md)
|
* [レイヤー](ja/feature_layers.md)
|
||||||
* [自動シフト](ja/feature_auto_shift.md)
|
* [One Shot Keys](ja/one_shot_keys.md)
|
||||||
* [バックライト](ja/feature_backlight.md)
|
* [ポインティング デバイス](ja/feature_pointing_device.md)
|
||||||
* [ブルートゥース](ja/feature_bluetooth.md)
|
* [Swap Hands](ja/feature_swap_hands.md)
|
||||||
* [ブートマジック](ja/feature_bootmagic.md)
|
* [タップダンス](ja/feature_tap_dance.md)
|
||||||
* [コンボ](ja/feature_combo.md)
|
* [タップホールド設定](ja/tap_hold.md)
|
||||||
* [コマンド](ja/feature_command.md)
|
* [ターミナル](ja/feature_terminal.md)
|
||||||
* [デバウンス API](ja/feature_debounce_type.md)
|
* [ユニコード](ja/feature_unicode.md)
|
||||||
* [DIP スイッチ](ja/feature_dip_switch.md)
|
* [ユーザスペース](ja/feature_userspace.md)
|
||||||
* [動的マクロ](ja/feature_dynamic_macros.md)
|
* [WPM 計算](ja/feature_wpm.md)
|
||||||
* [エンコーダ](ja/feature_encoders.md)
|
|
||||||
* [グレイブ エスケープ](ja/feature_grave_esc.md)
|
|
||||||
* [触覚フィードバック](ja/feature_haptic_feedback.md)
|
|
||||||
* [HD44780 LCD コントローラ](ja/feature_hd44780.md)
|
|
||||||
* [キーロック](ja/feature_key_lock.md)
|
|
||||||
* [レイアウト](ja/feature_layouts.md)
|
|
||||||
* [リーダー キー](ja/feature_leader_key.md)
|
|
||||||
* [LED マトリクス](ja/feature_led_matrix.md)
|
|
||||||
* [マクロ](ja/feature_macros.md)
|
|
||||||
* [マウスキー](ja/feature_mouse_keys.md)
|
|
||||||
* [OLED ドライバ](ja/feature_oled_driver.md)
|
|
||||||
* [One Shot Keys](ja/one_shot_keys.md)
|
|
||||||
* [ポインティング デバイス](ja/feature_pointing_device.md)
|
|
||||||
* [PS/2 マウス](ja/feature_ps2_mouse.md)
|
|
||||||
* [RGB ライト](ja/feature_rgblight.md)
|
|
||||||
* [RGB マトリクス](ja/feature_rgb_matrix.md)
|
|
||||||
* [Space Cadet](ja/feature_space_cadet.md)
|
|
||||||
* [分割キーボード](ja/feature_split_keyboard.md)
|
|
||||||
* [Stenography](ja/feature_stenography.md)
|
|
||||||
* [Swap Hands](ja/feature_swap_hands.md)
|
|
||||||
* [タップ ダンス](ja/feature_tap_dance.md)
|
|
||||||
* [ターミナル](ja/feature_terminal.md)
|
|
||||||
* [感熱式プリンタ](ja/feature_thermal_printer.md)
|
|
||||||
* [ユニコード](ja/feature_unicode.md)
|
|
||||||
* [ユーザスペース](ja/feature_userspace.md)
|
|
||||||
* [Velocikey](ja/feature_velocikey.md)
|
|
||||||
|
|
||||||
* メーカーおよびモッダーのために
|
* ハードウェア機能
|
||||||
* [Hand Wiring ガイド](ja/hand_wire.md)
|
* 表示
|
||||||
* [ISP 書き込みガイド](ja/isp_flashing_guide.md)
|
* [HD44780 LCD コントローラ](ja/feature_hd44780.md)
|
||||||
* [ARM デバッグ ガイド](ja/arm_debugging.md)
|
* [OLED ドライバ](ja/feature_oled_driver.md)
|
||||||
* [ADC ドライバ](ja/adc_driver.md)
|
* 電飾
|
||||||
* [I2C ドライバ](ja/i2c_driver.md)
|
* [バックライト](ja/feature_backlight.md)
|
||||||
* [WS2812 ドライバ](ja/ws2812_driver.md)
|
* [LED マトリックス](ja/feature_led_matrix.md)
|
||||||
* [EEPROM ドライバ](ja/eeprom_driver.md)
|
* [RGB ライト](ja/feature_rgblight.md)
|
||||||
* [GPIO コントロール](ja/internals_gpio_control.md)
|
* [RGB マトリックス](ja/feature_rgb_matrix.md)
|
||||||
* [カスタムマトリックス](ja/custom_matrix.md)
|
* [オーディオ](ja/feature_audio.md)
|
||||||
* [Proton C 規約](ja/proton_c_conversion.md)
|
* [Bluetooth](ja/feature_bluetooth.md)
|
||||||
|
* [ブートマジック](ja/feature_bootmagic.md)
|
||||||
|
* [カスタムマトリックス](ja/custom_matrix.md)
|
||||||
|
* [DIP スイッチ](ja/feature_dip_switch.md)
|
||||||
|
* [エンコーダ](ja/feature_encoders.md)
|
||||||
|
* [触覚フィードバック](ja/feature_haptic_feedback.md)
|
||||||
|
* [Proton C 規約](ja/proton_c_conversion.md)
|
||||||
|
* [PS/2 マウス](ja/feature_ps2_mouse.md)
|
||||||
|
* [分割キーボード](ja/feature_split_keyboard.md)
|
||||||
|
* [Stenography](ja/feature_stenography.md)
|
||||||
|
* [感熱式プリンタ](ja/feature_thermal_printer.md)
|
||||||
|
* [Velocikey](ja/feature_velocikey.md)
|
||||||
|
|
||||||
* より深く知るために
|
* QMK の開発
|
||||||
* [キーボードがどのように動作するか](ja/how_keyboards_work.md)
|
* 互換性を破る変更/Breaking changes
|
||||||
* [QMK の理解](ja/understanding_qmk.md)
|
* [概要](ja/breaking_changes.md)
|
||||||
|
* [プルリクエストにフラグが付けられた](ja/breaking_changes_instructions.md)
|
||||||
|
* 履歴
|
||||||
|
* [2020年2月29日](ja/ChangeLog/20200229.md)
|
||||||
|
* [2019年8月30日](ja/ChangeLog/20190830.md)
|
||||||
|
|
||||||
* 他の話題
|
* C 開発
|
||||||
* [Eclipse で QMK を使用](ja/other_eclipse.md)
|
* [ARM デバッグ ガイド](ja/arm_debugging.md)
|
||||||
* [VSCode で QMK を使用](ja/other_vscode.md)
|
* [AVR プロセッサ](ja/hardware_avr.md)
|
||||||
* [サポート](ja/getting_started_getting_help.md)
|
* [コーディング規約](ja/coding_conventions_c.md)
|
||||||
* [翻訳を追加する方法](ja/translating.md)
|
* [互換性のあるマイクロコントローラ](ja/compatible_microcontrollers.md)
|
||||||
|
* [ドライバ](ja/hardware_drivers.md)
|
||||||
|
* [ADC ドライバ](ja/adc_driver.md)
|
||||||
|
* [I2C ドライバ](ja/i2c_driver.md)
|
||||||
|
* [SPI ドライバ](ja/spi_driver.md)
|
||||||
|
* [WS2812 ドライバ](ja/ws2812_driver.md)
|
||||||
|
* [EEPROM ドライバ](ja/eeprom_driver.md)
|
||||||
|
* [GPIO コントロール](ja/internals_gpio_control.md)
|
||||||
|
* [キーボード ガイドライン](ja/hardware_keyboard_guidelines.md)
|
||||||
|
|
||||||
* QMK の内部詳細(作成中)
|
* Python 開発
|
||||||
* [定義](ja/internals_defines.md)
|
* [コーディング規約](ja/coding_conventions_python.md)
|
||||||
* [Input Callback Reg](ja/internals_input_callback_reg.md)
|
* [QMK CLI 開発](ja/cli_development.md)
|
||||||
* [Midi ドライバ](ja/internals_midi_device.md)
|
|
||||||
* [Midi デバイスのセットアップ手順](ja/internals_midi_device_setup_process.md)
|
* Configurator 開発
|
||||||
* [Midi ユーティリティ](ja/internals_midi_util.md)
|
* QMK API
|
||||||
* [Send Functions](ja/internals_send_functions.md)
|
* [開発環境](ja/api_development_environment.md)
|
||||||
* [Sysex Tools](ja/internals_sysex_tools.md)
|
* [アーキテクチャの概要](ja/api_development_overview.md)
|
||||||
|
|
||||||
|
* QMK Reference
|
||||||
|
* [QMK への貢献](ja/contributing.md)
|
||||||
|
* [QMK ドキュメントの翻訳](ja/translating.md)
|
||||||
|
* [設定オプション](ja/config_options.md)
|
||||||
|
* [Make ドキュメント](ja/getting_started_make_guide.md)
|
||||||
|
* [ドキュメント ベストプラクティス](ja/documentation_best_practices.md)
|
||||||
|
* [ドキュメント テンプレート](ja/documentation_templates.md)
|
||||||
|
* [コミュニティレイアウト](ja/feature_layouts.md)
|
||||||
|
* [ユニットテスト](ja/unit_testing.md)
|
||||||
|
* [便利な関数](ja/ref_functions.md)
|
||||||
|
* [info.json 形式](ja/reference_info_json.md)
|
||||||
|
|
||||||
|
* より深く知るために
|
||||||
|
* [キーボードがどのように動作するか](ja/how_keyboards_work.md)
|
||||||
|
* [マトリックスがどのように動作するか](ja/how_a_matrix_works.md)
|
||||||
|
* [QMK を理解する](ja/understanding_qmk.md)
|
||||||
|
|
||||||
|
* QMK の内部詳細(作成中)
|
||||||
|
* [定義](ja/internals_defines.md)
|
||||||
|
* [Input Callback Reg](ja/internals_input_callback_reg.md)
|
||||||
|
* [Midi デバイス](ja/internals_midi_device.md)
|
||||||
|
* [Midi デバイスのセットアップ手順](ja/internals_midi_device_setup_process.md)
|
||||||
|
* [Midi ユーティリティ](ja/internals_midi_util.md)
|
||||||
|
* [Send Functions](ja/internals_send_functions.md)
|
||||||
|
* [Sysex Tools](ja/internals_sysex_tools.md)
|
||||||
@@ -1,8 +1,8 @@
|
|||||||
# Eclipse を使った ARM デバッグ
|
# Eclipse を使った ARM デバッグ
|
||||||
|
|
||||||
<!---
|
<!---
|
||||||
original document: eae21eed7:docs/arm_debugging.md
|
original document: 0.8.58:docs/arm_debugging.md
|
||||||
git diff eae21eed7 HEAD -- docs/arm_debugging.md | cat
|
git diff 0.8.58 HEAD -- docs/arm_debugging.md | cat
|
||||||
-->
|
-->
|
||||||
|
|
||||||
このページでは、SWD アダプタとオープンソース/フリーツールを使って ARM MCU をデバッグするためのセットアップ方法について説明します。このガイドでは、GNU MCU Eclipse IDE for C/C++ Developers および OpenOCD を必要な依存関係と一緒にインストールします。
|
このページでは、SWD アダプタとオープンソース/フリーツールを使って ARM MCU をデバッグするためのセットアップ方法について説明します。このガイドでは、GNU MCU Eclipse IDE for C/C++ Developers および OpenOCD を必要な依存関係と一緒にインストールします。
|
||||||
@@ -60,7 +60,7 @@ Java は Eclipse で必要とされるため、[ここ](https://www.oracle.com/t
|
|||||||
|
|
||||||
Eclipse に QMK をビルドしようとするデバイスを教える必要があります。QMK フォルダを右クリック -> Properties -> C/C++ Build -> Settings を選択します。Devices タブを選択し、Devices の下から MCU の適切な種類を選択します。私の例では、STM32F303CC です。
|
Eclipse に QMK をビルドしようとするデバイスを教える必要があります。QMK フォルダを右クリック -> Properties -> C/C++ Build -> Settings を選択します。Devices タブを選択し、Devices の下から MCU の適切な種類を選択します。私の例では、STM32F303CC です。
|
||||||
|
|
||||||
この間に、Build コマンドもセットアップしましょう。C/C++ Build を選択し、Behavior タブを選択します。build コマンドのところで、`all` を必要な make コマンドに置き換えます。例えば、rev6 Planck の default キーマップの場合、これは `planck/rev6:default` になります。Apply and Close を選択します。
|
この間に、Build コマンドもセットアップしましょう。C/C++ Build を選択し、Behavior タブを選択します。Build コマンドのところで、`all` を必要な make コマンドに置き換えます。例えば、rev6 Planck の default キーマップの場合、これは `planck/rev6:default` になります。Apply and Close を選択します。
|
||||||
|
|
||||||
## ビルド
|
## ビルド
|
||||||
|
|
||||||
@@ -70,13 +70,13 @@ Eclipse に QMK をビルドしようとするデバイスを教える必要が
|
|||||||
|
|
||||||
### デバッガの接続
|
### デバッガの接続
|
||||||
|
|
||||||
ARM MCU は、クロック信号(SWCLK) とデータ信号(SWDIO) で構成される Single Wire Debug (SWD) プロトコルを使います。MCU を 完全に操作するには、この2本のワイヤとグラウンドを接続するだけで十分です。ここでは、キーボードは USB を介して電力が供給されると想定しています。手動でリセットボタンを使えるため、RESET 信号は必要ありません。より高度なセットアップのために printf と scanf をホストに非同期にパイプする SWO 信号を使用できますが、私たちのセットアップでは無視します。
|
ARM MCU は、クロック信号(SWCLK) とデータ信号(SWDIO) で構成される Single Wire Debug (SWD) プロトコルを使います。MCU を完全に操作するには、この2本のワイヤとグラウンドを接続するだけで十分です。ここでは、キーボードは USB を介して電力が供給されると想定しています。手動でリセットボタンを使えるため、RESET 信号は必要ありません。より高度なセットアップのために printf と scanf をホストに非同期にパイプする SWO 信号を使用できますが、私たちのセットアップでは無視します。
|
||||||
|
|
||||||
注意: SWCLK と SWDIO ピンがキーボードのマトリックスで使われていないことを確認してください。もし使われている場合は、一時的に他のピンに切り替えることができます。
|
注意: SWCLK と SWDIO ピンがキーボードのマトリックスで使われていないことを確認してください。もし使われている場合は、一時的に他のピンに切り替えることができます。
|
||||||
|
|
||||||
### デバッガの設定
|
### デバッガの設定
|
||||||
|
|
||||||
QMK フォルダを右クリックし、Debug As -> Debug Configurations... を選択します。ここで、GDB OpenOCD Debugging をダブルクリックします。Debugger タブを選択し、MCU に必要な設定を入力します。これを見つけるにはいじったりググったりする必要があるかもしれません。STM32F3 用のデフォルトスクリプトは stm32f3discovery.cfg と呼ばれます。OpenOCD に伝えるには、Config options で `-f board/stm32f3discovery.cfg` と入力します。
|
QMK フォルダを右クリックし、Debug As -> Debug Configurations... を選択します。ここで、GDB OpenOCD Debugging をダブルクリックします。Debugger タブを選択し、MCU に必要な設定を入力します。これを見つけるにはいじったりググったりする必要があるかもしれません。STM32F3 用のデフォルトスクリプトは `stm32f3discovery.cfg` と呼ばれます。OpenOCD に伝えるには、Config options で `-f board/stm32f3discovery.cfg` と入力します。
|
||||||
|
|
||||||
注意: 私の場合、この設定スクリプトはリセット操作を無効にするために編集が必要です。スクリプトの場所は、通常はパス `openocd/version/.content/scripts/board` の下の実際の実行可能フィールドの中で見つかります。ここで、私は `reset_config srst_only` を `reset_config none` に編集しました。
|
注意: 私の場合、この設定スクリプトはリセット操作を無効にするために編集が必要です。スクリプトの場所は、通常はパス `openocd/version/.content/scripts/board` の下の実際の実行可能フィールドの中で見つかります。ここで、私は `reset_config srst_only` を `reset_config none` に編集しました。
|
||||||
|
|
||||||
@@ -86,7 +86,7 @@ Apply and Close を選択します。
|
|||||||
|
|
||||||
キーボードをリセットしてください。
|
キーボードをリセットしてください。
|
||||||
|
|
||||||
虫アイコンをクリックし、もし全てうまく行けば Debug パースペクティブに移動します。ここでは、main 関数の最初でプログラムカウンタが停止するので、Play ボタンを押します。全てのデバッガのほとんどの機能は ARM MCU で動作しますが、正確な詳細については google があなたのお友達です!
|
虫アイコンをクリックし、もし全てうまく行けば Debug パースペクティブに移動します。ここでは、main 関数の最初でプログラムカウンタが停止し、Play ボタンが押されるのを待ちます。全てのデバッガのほとんどの機能は Arm MCU で動作しますが、正確な詳細については Google があなたのお友達です!
|
||||||
|
|
||||||
|
|
||||||
ハッピーデバッギング!
|
ハッピーデバッギング!
|
||||||
@@ -0,0 +1,120 @@
|
|||||||
|
# Breaking changes/互換性を破る変更
|
||||||
|
|
||||||
|
<!---
|
||||||
|
grep --no-filename "^[ ]*git diff" docs/ja/*.md | sh
|
||||||
|
original document: 0.9.0:docs/breaking_changes.md
|
||||||
|
git diff 0.9.0 HEAD -- docs/breaking_changes.md | cat
|
||||||
|
-->
|
||||||
|
|
||||||
|
このドキュメントは QMK の互換性を破る変更(Breaking change) のプロセスについて説明します。
|
||||||
|
互換性を破る変更とは、互換性がなかったり潜在的な危険が生じるように QMK の動作を変える変更を指します。
|
||||||
|
ユーザが QMK ツリーを更新しても自分のキーマップが壊れない事を確信できるように、これらの変更を制限します。(訳注:以後、原文のまま Breaking change を用語として使用します。)
|
||||||
|
|
||||||
|
Breaking change ピリオドとは、危険な変更、または予想外の変更を QMK へ行なう PR をマージする時のことです。
|
||||||
|
付随するテスト期間があるため、問題が起きることはまれか、有りえないと確信しています。
|
||||||
|
|
||||||
|
## 過去の Breaking change には何が含まれますか?
|
||||||
|
|
||||||
|
* [2020年5月30日](ja/ChangeLog/20200530.md)
|
||||||
|
* [2020年2月29日](ja/ChangeLog/20200229.md)
|
||||||
|
* [2019年8月30日](ja/ChangeLog/20190830.md)
|
||||||
|
|
||||||
|
## 次の Breaking change はいつですか?
|
||||||
|
|
||||||
|
次の Breaking change は2020年8月29日に予定されています。
|
||||||
|
|
||||||
|
### 重要な日付
|
||||||
|
|
||||||
|
* [x] 2020年 5月30日 - `develop` が作成されました。毎週リベースされます。
|
||||||
|
* [ ] 2020年 8月 1日 - `develop` は新しいPRを取り込みません。
|
||||||
|
* [ ] 2020年 8月 1日 - テスターの募集。
|
||||||
|
* [ ] 2020年 8月27日 - `master`がロックされ、PR はマージされません。
|
||||||
|
* [ ] 2020年 8月29日 - `develop` を `master` にマージします。
|
||||||
|
* [ ] 2020年 8月29日 - `master` のロックが解除されます。PR を再びマージすることができます。
|
||||||
|
|
||||||
|
## どのような変更が含まれますか?
|
||||||
|
|
||||||
|
最新の Breaking change 候補を見るには、[`breaking_change` ラベル](https://github.com/qmk/qmk_firmware/pulls?q=is%3Aopen+label%3Abreaking_change+is%3Apr)を参照してください。
|
||||||
|
現在から `develop` が閉じられるまでの間に新しい変更が追加される可能性があり、そのラベルが適用された PR はマージされることは保証されていません。
|
||||||
|
|
||||||
|
このラウンドに、あなたの Breaking change を含めたい場合は、`breaking_change` ラベルを持つ PR を作成し、`develop` が閉じる前に承認してもらう必要があります。
|
||||||
|
`develop` が閉じた後は、新しい Breaking change は受け付けられません。
|
||||||
|
|
||||||
|
受け入れの基準:
|
||||||
|
|
||||||
|
* PR が完了し、マージの準備ができている
|
||||||
|
* PR が ChangeLog を持つ
|
||||||
|
|
||||||
|
# チェックリスト
|
||||||
|
|
||||||
|
ここでは、Breaking change プロセスを実行する時に使用する様々なプロセスについて説明します。
|
||||||
|
|
||||||
|
## `master` から `develop` をリベースします
|
||||||
|
|
||||||
|
これは `develop` が開いている間、毎週金曜日に実行されます。
|
||||||
|
|
||||||
|
プロセス:
|
||||||
|
|
||||||
|
```
|
||||||
|
cd qmk_firmware
|
||||||
|
git checkout master
|
||||||
|
git pull --ff-only
|
||||||
|
git checkout develop
|
||||||
|
git rebase master
|
||||||
|
git push --force
|
||||||
|
```
|
||||||
|
|
||||||
|
## `develop` ブランチの作成
|
||||||
|
|
||||||
|
以前の `develop` ブランチがマージされた直後に、これが発生します。
|
||||||
|
|
||||||
|
* `qmk_firmware` git commands
|
||||||
|
* [ ] `git checkout master`
|
||||||
|
* [ ] `git pull --ff-only`
|
||||||
|
* [ ] `git checkout -b develop`
|
||||||
|
* [ ] Edit `readme.md`
|
||||||
|
* [ ] これがテストブランチであることを上部に大きな通知で追加します。
|
||||||
|
* [ ] このドキュメントへのリンクを含めます
|
||||||
|
* [ ] `git commit -m 'Branch point for <DATE> Breaking Change'`
|
||||||
|
* [ ] `git tag breakpoint_<YYYY>_<MM>_<DD>`
|
||||||
|
* [ ] `git tag <next_version>` # ブレーキング ポイント タグがバージョンの増分を混乱させないようにします
|
||||||
|
* [ ] `git push origin develop`
|
||||||
|
* [ ] `git push --tags`
|
||||||
|
|
||||||
|
## マージの 4 週間前
|
||||||
|
|
||||||
|
* `develop` は新しい PR に対して閉じられ、現在の PR の修正のみがマージされる可能性があります。
|
||||||
|
* テスターの呼び出しを投稿します
|
||||||
|
* [ ] Discord
|
||||||
|
* [ ] GitHub PR
|
||||||
|
* [ ] https://reddit.com/r/olkb
|
||||||
|
|
||||||
|
## マージの 1 週間前
|
||||||
|
|
||||||
|
* master が < 2 日前> から <マージの日> まで閉じられることを発表します
|
||||||
|
* [ ] Discord
|
||||||
|
* [ ] GitHub PR
|
||||||
|
* [ ] https://reddit.com/r/olkb
|
||||||
|
|
||||||
|
## マージの 2 日前
|
||||||
|
|
||||||
|
* master が 2 日間閉じられることを発表します
|
||||||
|
* [ ] Discord
|
||||||
|
* [ ] GitHub PR
|
||||||
|
* [ ] https://reddit.com/r/olkb
|
||||||
|
|
||||||
|
## マージの日
|
||||||
|
|
||||||
|
* `qmk_firmware` git commands
|
||||||
|
* [ ] `git checkout develop`
|
||||||
|
* [ ] `git pull --ff-only`
|
||||||
|
* [ ] `git rebase origin/master`
|
||||||
|
* [ ] Edit `readme.md`
|
||||||
|
* [ ] `develop` についてのメモを削除
|
||||||
|
* [ ] ChangeLog を 1 つのファイルにまとめます。
|
||||||
|
* [ ] `git commit -m 'Merge point for <DATE> Breaking Change'`
|
||||||
|
* [ ] `git push origin develop`
|
||||||
|
* GitHub Actions
|
||||||
|
* [ ] `develop`の PR を作成します
|
||||||
|
* [ ] travis がクリーンに戻ったことを確認します
|
||||||
|
* [ ] `develop` PR をマージします
|
||||||
@@ -0,0 +1,51 @@
|
|||||||
|
# breaking changes/互換性を破る変更: プルリクエストにフラグが付けられた
|
||||||
|
|
||||||
|
<!---
|
||||||
|
grep --no-filename "^[ ]*git diff" docs/ja/*.md | sh
|
||||||
|
original document: 0.9.0:docs/breaking_changes_instructions.md
|
||||||
|
git diff 0.9.0 HEAD -- docs/breaking_changes_instructions.md | cat
|
||||||
|
-->
|
||||||
|
|
||||||
|
QMK のメンバーがあなたのプルリクエストに返信し、あなたの提出したものは Breaking change (互換性を破る変更) であると述べている場合があります。メンバーの判断では、あなたが提案した変更は QMK やその利用者にとってより大きな影響を持つと考えられます。
|
||||||
|
|
||||||
|
プルリクエストにフラグが立てられる原因となるものには、以下のようなものがあります:
|
||||||
|
|
||||||
|
- **ユーザーのキーマップに対する編集**
|
||||||
|
ユーザーが自分のキーマップを QMK に提出した後、しばらくしてさらに更新してプルリクエストを開いたところ、それが `qmk/qmk_firmware` リポジトリで編集されていたためにマージできなかったことに気づくことがあるかもしれません。すべてのユーザーが Git や GitHub を使いこなせるわけではないので、ユーザー自身で問題を修正できないことに気づくかもしれません。
|
||||||
|
- **期待される動作の変更**
|
||||||
|
QMK の動作を変更すると、既存の QMK 機能への変更を組み込んだ新しいファームウェアをフラッシュした場合、ユーザはハードウェアまたは QMK が壊れていると考え、希望する動作を復元する手段がないことに気付くことがあります。
|
||||||
|
- **ユーザーのアクションを必要とする変更**
|
||||||
|
変更には、ツールチェインを更新したり、Git で何らかのアクションを取るなど、ユーザーがアクションを行う必要がある場合もあります。
|
||||||
|
- **精査が必要な変更**
|
||||||
|
時には、投稿がプロジェクトとしての QMK に影響を与えることもあります。これは、著作権やライセンスの問題、コーディング規約、大規模な機能のオーバーホール、コミュニティによるより広範なテストを必要とする「リスクの高い」変更、あるいは全く別のものである可能性があります。
|
||||||
|
- **エンドユーザーとのコミュニケーションを必要とする変更**
|
||||||
|
これには、将来の非推奨化への警告、時代遅れの慣習、その他伝えなければならないが上記のカテゴリのどれかに当てはまらないものが含まれます。
|
||||||
|
|
||||||
|
## 何をすればいいのか?
|
||||||
|
|
||||||
|
提出したものが Breaking change だと判断された場合、手続きをスムーズに進めるためにできることがいくつかあります。
|
||||||
|
|
||||||
|
### PR を分割することを検討する
|
||||||
|
|
||||||
|
あなたがコアコードを投稿していて、それが Breaking change プロセスを経る必要がある唯一の理由が、あなたの変更に合わせてキーマップを更新していることである場合、古いキーマップが機能し続けるような方法であなたの機能を投稿できるかどうかを検討してください。
|
||||||
|
そののち、Breaking change プロセスを経て古いコードを削除する別の PR を提出してください。
|
||||||
|
|
||||||
|
### ChangeLog エントリの提供
|
||||||
|
|
||||||
|
Breaking change プロセスを経て提出する際には、変更ログのエントリを含めることを我々は要請します。
|
||||||
|
エントリーは、あなたのプルリクエストが行う変更の短い要約としてください – [ここの各セクションは changelog として開始されました](ja/ChangeLog/20190830.md "n.b. This should link to the 2019 Aug 30 Breaking Changes doc - @noroadsleft")。
|
||||||
|
|
||||||
|
変更ログは `docs/ChangeLog/YYYYMMDD/PR####.md` に置いてください。
|
||||||
|
ここで、`YYYYMMDD` は QMK の breaking change ブランチ – 通常は `develop` という名称 – が `master` ブランチにマージされる日付、`####` はプルリクエストの番号です。
|
||||||
|
|
||||||
|
ユーザー側でのアクションを必要とする場合、あなたの変更ログは、どのようなアクションを取らなければならないかをユーザーに指示するか、そのようなアクションを指示する場所にリンクする必要があります。
|
||||||
|
|
||||||
|
### 変更点を文書化する
|
||||||
|
|
||||||
|
提出物の目的を理解し、それが必要とする可能性のある意味合いやアクションを理解することで、レビュープロセスをより簡単にすることができます。この目的のためには変更履歴で十分かもしれませんが、より広範囲の変更を行う場合には、変更履歴には不向きな詳細レベルが必要になるかもしれません。
|
||||||
|
|
||||||
|
あなたのプルリクエストにコメントしたり、質問やコメント、変更要求に対応したりすることは、非常にありがたいことです。
|
||||||
|
|
||||||
|
### 助けを求める
|
||||||
|
|
||||||
|
あなたの提出物にフラグが立ったことで、あなたはびっくりしてしまったかもしれません。もし、あなた自身が脅されたり、圧倒されたりしていると感じたら、私たちに知らせてください。プルリクエストにコメントするか、[Discord で QMK チームに連絡を取ってください](https://discord.gg/Uq7gcHh)。
|
||||||
+12
-267
@@ -1,50 +1,39 @@
|
|||||||
# QMK CLI
|
# QMK CLI :id=qmk-cli
|
||||||
|
|
||||||
<!---
|
<!---
|
||||||
original document: 79e6b7866:docs/cli.md
|
original document: 0.9.19:docs/cli.md
|
||||||
git diff 79e6b7866 HEAD -- docs/cli.md | cat
|
git diff 0.9.19 HEAD -- docs/cli.md | cat
|
||||||
-->
|
-->
|
||||||
|
|
||||||
このページは QMK CLI のセットアップと使用方法について説明します。
|
## 概要 :id=overview
|
||||||
|
|
||||||
# 概要
|
|
||||||
|
|
||||||
QMK CLI を使用すると QMK キーボードの構築と作業が簡単になります。QMK ファームウェアの取得とコンパイル、キーマップの作成などのようなタスクを簡素化し合理化するためのコマンドを多く提供します。
|
QMK CLI を使用すると QMK キーボードの構築と作業が簡単になります。QMK ファームウェアの取得とコンパイル、キーマップの作成などのようなタスクを簡素化し合理化するためのコマンドを多く提供します。
|
||||||
|
|
||||||
* [グローバル CLI](#global-cli)
|
### 必要事項 :id=requirements
|
||||||
* [ローカル CLI](#local-cli)
|
|
||||||
* [CLI コマンド](#cli-commands)
|
|
||||||
|
|
||||||
# 必要事項
|
QMK は Python 3.6 以上を必要とします。我々は必要事項の数を少なくしようとしていますが、[`requirements.txt`](https://github.com/qmk/qmk_firmware/blob/master/requirements.txt) に列挙されているパッケージもインストールする必要があります。これらは QMK CLI をインストールするときに自動的にインストールされます。
|
||||||
|
|
||||||
CLI は Python 3.5 以上を必要とします。我々は必要事項の数を少なくしようとしていますが、[`requirements.txt`](https://github.com/qmk/qmk_firmware/blob/master/requirements.txt) にリストされているパッケージもインストールする必要があります。
|
### Homebrew を使ったインストール (macOS、いくつかの Linux) :id=install-using-homebrew
|
||||||
|
|
||||||
# グローバル CLI :id=global-cli
|
|
||||||
|
|
||||||
QMK は、QMK ビルド環境のセットアップ、QMK の操作、および `qmk_firmware` の複数のコピーの操作を容易にできるインストール可能な CLI を提供します。これを定期的にインストールおよび更新することをお勧めします。
|
|
||||||
|
|
||||||
## Homebrew を使ったインストール (macOS、いくつかの Linux)
|
|
||||||
|
|
||||||
[Homebrew](https://brew.sh) をインストールしている場合は、タップして QMK をインストールすることができます:
|
[Homebrew](https://brew.sh) をインストールしている場合は、タップして QMK をインストールすることができます:
|
||||||
|
|
||||||
```
|
```
|
||||||
brew tap qmk/qmk
|
brew install qmk/qmk/qmk
|
||||||
brew install qmk
|
|
||||||
export QMK_HOME='~/qmk_firmware' # オプション、`qmk_firmware` の場所を設定します
|
export QMK_HOME='~/qmk_firmware' # オプション、`qmk_firmware` の場所を設定します
|
||||||
qmk setup # これは `qmk/qmk_firmware` をクローンし、オプションでビルド環境をセットアップします
|
qmk setup # これは `qmk/qmk_firmware` をクローンし、オプションでビルド環境をセットアップします
|
||||||
```
|
```
|
||||||
|
|
||||||
## easy_install あるいは pip を使ってインストール
|
### pip を使ってインストール :id=install-using-easy_install-or-pip
|
||||||
|
|
||||||
上のリストにあなたのシステムがない場合は、QMK を手動でインストールすることができます。最初に、python 3.5 (以降)をインストールしていて、pip をインストールしていることを確認してください。次に以下のコマンドを使って QMK をインストールします:
|
上で列挙した中にあなたのシステムがない場合は、QMK を手動でインストールすることができます。最初に、python 3.6 (以降)をインストールしていて、pip をインストールしていることを確認してください。次に以下のコマンドを使って QMK をインストールします:
|
||||||
|
|
||||||
```
|
```
|
||||||
pip3 install qmk
|
python3 -m pip install qmk
|
||||||
export QMK_HOME='~/qmk_firmware' # オプション、`qmk_firmware` の場所を設定します
|
export QMK_HOME='~/qmk_firmware' # オプション、`qmk_firmware` の場所を設定します
|
||||||
qmk setup # これは `qmk/qmk_firmware` をクローンし、オプションでビルド環境をセットアップします
|
qmk setup # これは `qmk/qmk_firmware` をクローンし、オプションでビルド環境をセットアップします
|
||||||
```
|
```
|
||||||
|
|
||||||
## 他のオペレーティングシステムのためのパッケージ
|
### 他のオペレーティングシステムのためのパッケージ :id=packaging-for-other-operating-systems
|
||||||
|
|
||||||
より多くのオペレーティングシステム用に `qmk` パッケージを作成および保守する人を探しています。OS 用のパッケージを作成する場合は、以下のガイドラインに従ってください:
|
より多くのオペレーティングシステム用に `qmk` パッケージを作成および保守する人を探しています。OS 用のパッケージを作成する場合は、以下のガイドラインに従ってください:
|
||||||
|
|
||||||
@@ -52,247 +41,3 @@ qmk setup # これは `qmk/qmk_firmware` をクローンし、オプション
|
|||||||
* 逸脱する場合は、理由をコメントに文章化してください。
|
* 逸脱する場合は、理由をコメントに文章化してください。
|
||||||
* virtualenv を使ってインストールしてください
|
* virtualenv を使ってインストールしてください
|
||||||
* 環境変数 `QMK_HOME` を設定して、ファームウェアソースを `~/qmk_firmware` 以外のどこかにチェックアウトするようにユーザに指示してください。
|
* 環境変数 `QMK_HOME` を設定して、ファームウェアソースを `~/qmk_firmware` 以外のどこかにチェックアウトするようにユーザに指示してください。
|
||||||
|
|
||||||
# ローカル CLI :id=local-cli
|
|
||||||
|
|
||||||
グローバル CLI を使いたくない場合は、`qmk_firmware` に付属のローカル CLI があります。`qmk_firmware/bin/qmk` で見つけることができます。任意のディレクトリから `qmk` コマンドを実行でき、常に `qmk_firmware` のコピー上で動作します。
|
|
||||||
|
|
||||||
**例**:
|
|
||||||
|
|
||||||
```
|
|
||||||
$ ~/qmk_firmware/bin/qmk hello
|
|
||||||
Ψ Hello, World!
|
|
||||||
```
|
|
||||||
|
|
||||||
## ローカル CLI の制限
|
|
||||||
|
|
||||||
グローバル CLI と比較して、ローカル CLI には幾つかの制限があります:
|
|
||||||
|
|
||||||
* ローカル CLI は `qmk setup` あるいは `qmk clone` をサポートしません。
|
|
||||||
* 複数のリポジトリがクローンされている場合でも、ローカル CLI は常に `qmk_firmware` ツリー上で動作します。
|
|
||||||
* ローカル CLI は virtualenv で動作しません。そのため依存関係が競合する可能性があります
|
|
||||||
|
|
||||||
# CLI コマンド :id=cli-commands
|
|
||||||
|
|
||||||
## `qmk cformat`
|
|
||||||
|
|
||||||
このコマンドは clang-format を使って C コードを整形します。引数無しで実行して全てのコアコードを整形するか、コマンドラインでファイル名を渡して特定のファイルに対して実行します。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk cformat [file1] [file2] [...] [fileN]
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk compile`
|
|
||||||
|
|
||||||
このコマンドにより、任意のディレクトリからファームウェアをコンパイルすることができます。<https://config.qmk.fm> からエクスポートした JSON をコンパイルするか、リポジトリ内でキーマップをコンパイルするか、現在の作業ディレクトリでキーボードをコンパイルすることができます。
|
|
||||||
|
|
||||||
**Configurator Exports での使い方**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk compile <configuratorExport.json>
|
|
||||||
```
|
|
||||||
|
|
||||||
**キーマップでの使い方**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk compile -kb <keyboard_name> -km <keymap_name>
|
|
||||||
```
|
|
||||||
|
|
||||||
**キーボードディレクトリでの使い方**:
|
|
||||||
|
|
||||||
default キーマップのあるキーボードディレクトリ、キーボードのキーマップディレクトリ、`--keymap <keymap_name>` で与えられるキーマップディレクトリにいなければなりません。
|
|
||||||
```
|
|
||||||
qmk compile
|
|
||||||
```
|
|
||||||
|
|
||||||
**例**:
|
|
||||||
```
|
|
||||||
$ qmk config compile.keymap=default
|
|
||||||
$ cd ~/qmk_firmware/keyboards/planck/rev6
|
|
||||||
$ qmk compile
|
|
||||||
Ψ Compiling keymap with make planck/rev6:default
|
|
||||||
...
|
|
||||||
```
|
|
||||||
あるいはオプションのキーマップ引数を指定して
|
|
||||||
|
|
||||||
```
|
|
||||||
$ cd ~/qmk_firmware/keyboards/clueboard/66/rev4
|
|
||||||
$ qmk compile -km 66_iso
|
|
||||||
Ψ Compiling keymap with make clueboard/66/rev4:66_iso
|
|
||||||
...
|
|
||||||
```
|
|
||||||
あるいはキーマップディレクトリで
|
|
||||||
|
|
||||||
```
|
|
||||||
$ cd ~/qmk_firmware/keyboards/gh60/satan/keymaps/colemak
|
|
||||||
$ qmk compile
|
|
||||||
Ψ Compiling keymap with make make gh60/satan:colemak
|
|
||||||
...
|
|
||||||
```
|
|
||||||
|
|
||||||
**レイアウトディレクトリでの使い方**:
|
|
||||||
|
|
||||||
`qmk_firmware/layouts/` 以下のキーマップディレクトリにいなければなりません。
|
|
||||||
```
|
|
||||||
qmk compile -kb <keyboard_name>
|
|
||||||
```
|
|
||||||
|
|
||||||
**例**:
|
|
||||||
```
|
|
||||||
$ cd ~/qmk_firmware/layouts/community/60_ansi/mechmerlin-ansi
|
|
||||||
$ qmk compile -kb dz60
|
|
||||||
Ψ Compiling keymap with make dz60:mechmerlin-ansi
|
|
||||||
...
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk flash`
|
|
||||||
|
|
||||||
このコマンドは `qmk compile` に似ていますが、ブートローダを対象にすることもできます。ブートローダはオプションで、デフォルトでは `:flash` に設定されています。
|
|
||||||
違うブートローダを指定するには、`-bl <bootloader>` を使ってください。利用可能なブートローダの詳細については、<https://docs.qmk.fm/#/ja/flashing>
|
|
||||||
を見てください。
|
|
||||||
|
|
||||||
**Configurator Exports での使い方**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk flash <configuratorExport.json> -bl <bootloader>
|
|
||||||
```
|
|
||||||
|
|
||||||
**キーマップでの使い方**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk flash -kb <keyboard_name> -km <keymap_name> -bl <bootloader>
|
|
||||||
```
|
|
||||||
|
|
||||||
**ブートローダのリスト**
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk flash -b
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk config`
|
|
||||||
|
|
||||||
このコマンドにより QMK の挙動を設定することができます。完全な `qmk config` のドキュメントについては、[CLI 設定](ja/cli_configuration.md)を見てください。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk config [-ro] [config_token1] [config_token2] [...] [config_tokenN]
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk docs`
|
|
||||||
|
|
||||||
このコマンドは、ドキュメントを参照または改善するために使うことができるローカル HTTP サーバを起動します。デフォルトのポートは 8936 です。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk docs [-p PORT]
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk doctor`
|
|
||||||
|
|
||||||
このコマンドは環境を調査し、潜在的なビルドあるいは書き込みの問題について警告します。必要に応じてそれらの多くを修正できます。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk doctor [-y] [-n]
|
|
||||||
```
|
|
||||||
|
|
||||||
**例**:
|
|
||||||
|
|
||||||
環境に問題がないか確認し、それらを修正するよう促します:
|
|
||||||
|
|
||||||
qmk doctor
|
|
||||||
|
|
||||||
環境を確認し、見つかった問題を自動的に修正します:
|
|
||||||
|
|
||||||
qmk doctor -y
|
|
||||||
|
|
||||||
環境を確認し、問題のみをレポートします:
|
|
||||||
|
|
||||||
qmk doctor -n
|
|
||||||
|
|
||||||
## `qmk json-keymap`
|
|
||||||
|
|
||||||
QMK Configurator からエクスポートしたものから keymap.c を生成します。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk json-keymap [-o OUTPUT] filename
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk kle2json`
|
|
||||||
|
|
||||||
このコマンドにより、生の KLE データから QMK Configurator の JSON へ変換することができます。絶対パスあるいは現在のディレクトリ内のファイル名のいずれかを受け取ります。デフォルトでは、`info.json` が既に存在している場合は上書きしません。上書きするには、`-f` あるいは `--force` フラグを使ってください。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk kle2json [-f] <filename>
|
|
||||||
```
|
|
||||||
|
|
||||||
**例**:
|
|
||||||
|
|
||||||
```
|
|
||||||
$ qmk kle2json kle.txt
|
|
||||||
☒ File info.json already exists, use -f or --force to overwrite.
|
|
||||||
```
|
|
||||||
|
|
||||||
```
|
|
||||||
$ qmk kle2json -f kle.txt -f
|
|
||||||
Ψ Wrote out to info.json
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk list-keyboards`
|
|
||||||
|
|
||||||
このコマンドは現在 `qmk_firmware` で定義されている全てのキーボードをリスト化します。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk list-keyboards
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk list-keymaps`
|
|
||||||
|
|
||||||
このコマンドは指定されたキーボード(とリビジョン)の全てのキーマップをリスト化します。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk list-keymaps -kb planck/ez
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk new-keymap`
|
|
||||||
|
|
||||||
このコマンドは、キーボードの既存のデフォルトのキーマップに基づいて新しいキーマップを作成します。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk new-keymap [-kb KEYBOARD] [-km KEYMAP]
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk pyformat`
|
|
||||||
|
|
||||||
このコマンドは `qmk_firmware` 内の python コードを整形します。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk pyformat
|
|
||||||
```
|
|
||||||
|
|
||||||
## `qmk pytest`
|
|
||||||
|
|
||||||
このコマンドは python のテストスィートを実行します。python コードに変更を加えた場合、これの実行が成功することを確認する必要があります。
|
|
||||||
|
|
||||||
**使用法**:
|
|
||||||
|
|
||||||
```
|
|
||||||
qmk pytest
|
|
||||||
```
|
|
||||||
@@ -0,0 +1,296 @@
|
|||||||
|
# QMK CLI コマンド
|
||||||
|
|
||||||
|
<!---
|
||||||
|
original document: 0.9.19:docs/cli_command.md
|
||||||
|
git diff 0.9.19 HEAD -- docs/cli_command.md | cat
|
||||||
|
-->
|
||||||
|
|
||||||
|
# ユーザー用コマンド
|
||||||
|
|
||||||
|
## `qmk compile`
|
||||||
|
|
||||||
|
このコマンドにより、任意のディレクトリからファームウェアをコンパイルすることができます。<https://config.qmk.fm> からエクスポートした JSON をコンパイルするか、リポジトリ内でキーマップをコンパイルするか、現在の作業ディレクトリでキーボードをコンパイルすることができます。
|
||||||
|
|
||||||
|
このコマンドはディレクトリを認識します。キーボードやキーマップのディレクトリにいる場合、自動的に KEYBOARD や KEYMAP を入力します。
|
||||||
|
|
||||||
|
**Configurator Exports での使い方**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk compile <configuratorExport.json>
|
||||||
|
```
|
||||||
|
|
||||||
|
**キーマップでの使い方**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk compile -kb <keyboard_name> -km <keymap_name>
|
||||||
|
```
|
||||||
|
|
||||||
|
**キーボードディレクトリでの使い方**:
|
||||||
|
|
||||||
|
default キーマップのあるキーボードディレクトリ、キーボードのキーマップディレクトリ、`--keymap <keymap_name>` で与えられるキーマップディレクトリにいなければなりません。
|
||||||
|
```
|
||||||
|
qmk compile
|
||||||
|
```
|
||||||
|
|
||||||
|
**指定したキーマップをサポートする全てのキーボードをビルドする場合の使い方**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk compile -kb all -km <keymap_name>
|
||||||
|
```
|
||||||
|
|
||||||
|
**例**:
|
||||||
|
```
|
||||||
|
$ qmk config compile.keymap=default
|
||||||
|
$ cd ~/qmk_firmware/keyboards/planck/rev6
|
||||||
|
$ qmk compile
|
||||||
|
Ψ Compiling keymap with make planck/rev6:default
|
||||||
|
...
|
||||||
|
```
|
||||||
|
あるいはオプションのキーマップ引数を指定して
|
||||||
|
|
||||||
|
```
|
||||||
|
$ cd ~/qmk_firmware/keyboards/clueboard/66/rev4
|
||||||
|
$ qmk compile -km 66_iso
|
||||||
|
Ψ Compiling keymap with make clueboard/66/rev4:66_iso
|
||||||
|
...
|
||||||
|
```
|
||||||
|
あるいはキーマップディレクトリで
|
||||||
|
|
||||||
|
```
|
||||||
|
$ cd ~/qmk_firmware/keyboards/gh60/satan/keymaps/colemak
|
||||||
|
$ qmk compile
|
||||||
|
Ψ Compiling keymap with make make gh60/satan:colemak
|
||||||
|
...
|
||||||
|
```
|
||||||
|
|
||||||
|
**レイアウトディレクトリでの使い方**:
|
||||||
|
|
||||||
|
`qmk_firmware/layouts/` 以下のキーマップディレクトリにいなければなりません。
|
||||||
|
```
|
||||||
|
qmk compile -kb <keyboard_name>
|
||||||
|
```
|
||||||
|
|
||||||
|
**例**:
|
||||||
|
```
|
||||||
|
$ cd ~/qmk_firmware/layouts/community/60_ansi/mechmerlin-ansi
|
||||||
|
$ qmk compile -kb dz60
|
||||||
|
Ψ Compiling keymap with make dz60:mechmerlin-ansi
|
||||||
|
...
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk flash`
|
||||||
|
|
||||||
|
このコマンドは `qmk compile` に似ていますが、ブートローダを対象にすることもできます。ブートローダはオプションで、デフォルトでは `:flash` に設定されています。
|
||||||
|
違うブートローダを指定するには、`-bl <bootloader>` を使ってください。利用可能なブートローダの詳細については、[ファームウェアを書き込む](ja/flashing.md)を見てください。
|
||||||
|
|
||||||
|
このコマンドはディレクトリを認識します。キーボードやキーマップのディレクトリにいる場合、自動的に KEYBOARD や KEYMAP を入力します。
|
||||||
|
|
||||||
|
**Configurator Exports での使い方**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk flash <configuratorExport.json> -bl <bootloader>
|
||||||
|
```
|
||||||
|
|
||||||
|
**キーマップでの使い方**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk flash -kb <keyboard_name> -km <keymap_name> -bl <bootloader>
|
||||||
|
```
|
||||||
|
|
||||||
|
**ブートローダの列挙**
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk flash -b
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk config`
|
||||||
|
|
||||||
|
このコマンドにより QMK の挙動を設定することができます。完全な `qmk config` のドキュメントについては、[CLI 設定](ja/cli_configuration.md)を見てください。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk config [-ro] [config_token1] [config_token2] [...] [config_tokenN]
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk doctor`
|
||||||
|
|
||||||
|
このコマンドは環境を調査し、潜在的なビルドあるいは書き込みの問題について警告します。必要に応じてそれらの多くを修正できます。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk doctor [-y] [-n]
|
||||||
|
```
|
||||||
|
|
||||||
|
**例**:
|
||||||
|
|
||||||
|
環境に問題がないか確認し、それらを修正するよう促します:
|
||||||
|
|
||||||
|
qmk doctor
|
||||||
|
|
||||||
|
環境を確認し、見つかった問題を自動的に修正します:
|
||||||
|
|
||||||
|
qmk doctor -y
|
||||||
|
|
||||||
|
環境を確認し、問題のみをレポートします:
|
||||||
|
|
||||||
|
qmk doctor -n
|
||||||
|
|
||||||
|
## `qmk info`
|
||||||
|
|
||||||
|
QMK のキーボードやキーマップに関する情報を表示します。キーボードに関する情報を取得したり、レイアウトを表示したり、基礎となるキーマトリックスを表示したり、JSON キーマップをきれいに印刷したりするのに使用できます。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk info [-f FORMAT] [-m] [-l] [-km KEYMAP] [-kb KEYBOARD]
|
||||||
|
```
|
||||||
|
|
||||||
|
このコマンドはディレクトリを認識します。キーボードやキーマップのディレクトリにいる場合、自動的に KEYBOARD や KEYMAP を入力します。
|
||||||
|
|
||||||
|
**例**:
|
||||||
|
|
||||||
|
キーボードの基本情報を表示する:
|
||||||
|
|
||||||
|
qmk info -kb planck/rev5
|
||||||
|
|
||||||
|
キーボードのマトリクスを表示する:
|
||||||
|
|
||||||
|
qmk info -kb ergodox_ez -m
|
||||||
|
|
||||||
|
キーボードの JSON キーマップを表示する:
|
||||||
|
|
||||||
|
qmk info -kb clueboard/california -km default
|
||||||
|
|
||||||
|
## `qmk json2c`
|
||||||
|
|
||||||
|
QMK Configurator からエクスポートしたものから keymap.c を生成します。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk json2c [-o OUTPUT] filename
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk list-keyboards`
|
||||||
|
|
||||||
|
このコマンドは現在 `qmk_firmware` で定義されている全てのキーボードを列挙します。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk list-keyboards
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk list-keymaps`
|
||||||
|
|
||||||
|
このコマンドは指定されたキーボード(とリビジョン)の全てのキーマップを列挙します。
|
||||||
|
|
||||||
|
このコマンドはディレクトリを認識します。キーボードのディレクトリにいる場合、自動的に KEYBOARD を入力します。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk list-keymaps -kb planck/ez
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk new-keymap`
|
||||||
|
|
||||||
|
このコマンドは、キーボードの既存のデフォルトのキーマップに基づいて新しいキーマップを作成します。
|
||||||
|
|
||||||
|
このコマンドはディレクトリを認識します。キーボードやキーマップのディレクトリにいる場合、自動的に KEYBOARD や KEYMAP を入力します。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk new-keymap [-kb KEYBOARD] [-km KEYMAP]
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
# 開発者用コマンド
|
||||||
|
|
||||||
|
## `qmk cformat`
|
||||||
|
|
||||||
|
このコマンドは clang-format を使って C コードを整形します。
|
||||||
|
|
||||||
|
引数無しで実行すると、変更された全てのコアコードを整形します。デフォルトでは `git diff` で `origin/master` をチェックし、ブランチは `-b <branch_name>` を使って変更できます。
|
||||||
|
|
||||||
|
`-a` で全てのコアコードを整形するか、コマンドラインでファイル名を渡して特定のファイルに対して実行します。
|
||||||
|
|
||||||
|
**指定したファイルに対する使い方**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk cformat [file1] [file2] [...] [fileN]
|
||||||
|
```
|
||||||
|
|
||||||
|
**全てのコアファイルに対する使い方**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk cformat -a
|
||||||
|
```
|
||||||
|
|
||||||
|
**origin/master で変更されたファイルのみに対する使い方**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk cformat
|
||||||
|
```
|
||||||
|
|
||||||
|
**branch_name で変更されたファイルのみに対する使い方**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk cformat -b branch_name
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk docs`
|
||||||
|
|
||||||
|
このコマンドは、ドキュメントを参照または改善するために使うことができるローカル HTTP サーバを起動します。デフォルトのポートは 8936 です。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk docs [-p PORT]
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk kle2json`
|
||||||
|
|
||||||
|
このコマンドにより、生の KLE データから QMK Configurator の JSON へ変換することができます。絶対パスあるいは現在のディレクトリ内のファイル名のいずれかを受け取ります。デフォルトでは、`info.json` が既に存在している場合は上書きしません。上書きするには、`-f` あるいは `--force` フラグを使ってください。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk kle2json [-f] <filename>
|
||||||
|
```
|
||||||
|
|
||||||
|
**例**:
|
||||||
|
|
||||||
|
```
|
||||||
|
$ qmk kle2json kle.txt
|
||||||
|
☒ File info.json already exists, use -f or --force to overwrite.
|
||||||
|
```
|
||||||
|
|
||||||
|
```
|
||||||
|
$ qmk kle2json -f kle.txt -f
|
||||||
|
Ψ Wrote out to info.json
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk pyformat`
|
||||||
|
|
||||||
|
このコマンドは `qmk_firmware` 内の python コードを整形します。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk pyformat
|
||||||
|
```
|
||||||
|
|
||||||
|
## `qmk pytest`
|
||||||
|
|
||||||
|
このコマンドは python のテストスィートを実行します。python コードに変更を加えた場合、これの実行が成功することを確認する必要があります。
|
||||||
|
|
||||||
|
**使用法**:
|
||||||
|
|
||||||
|
```
|
||||||
|
qmk pytest
|
||||||
|
```
|
||||||
@@ -1,8 +1,8 @@
|
|||||||
# QMK CLI 設定
|
# QMK CLI 設定
|
||||||
|
|
||||||
<!---
|
<!---
|
||||||
original document: d598f01cb:docs/cli_configuration.md
|
original document: 0.9.0:docs/cli_configuration.md
|
||||||
git diff d598f01cb HEAD -- docs/cli_configuration.md | cat
|
git diff 0.9.0 HEAD -- docs/cli_configuration.md | cat
|
||||||
-->
|
-->
|
||||||
|
|
||||||
このドキュメントは `qmk config` がどのように動作するかを説明します。
|
このドキュメントは `qmk config` がどのように動作するかを説明します。
|
||||||
@@ -113,7 +113,7 @@ compile.keymap: skully -> None
|
|||||||
|-----|---------------|-------------|
|
|-----|---------------|-------------|
|
||||||
| user.keyboard | None | キーボードのパス (例: `clueboard/66/rev4`) |
|
| user.keyboard | None | キーボードのパス (例: `clueboard/66/rev4`) |
|
||||||
| user.keymap | None | キーマップ名 (例: `default`) |
|
| user.keymap | None | キーマップ名 (例: `default`) |
|
||||||
| user.name | None | ユーザの github のユーザ名。 |
|
| user.name | None | ユーザの GitHub のユーザ名。 |
|
||||||
|
|
||||||
# 全ての設定オプション
|
# 全ての設定オプション
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,42 @@
|
|||||||
|
# 互換性のあるマイクロコントローラ
|
||||||
|
|
||||||
|
<!---
|
||||||
|
original document: 0.9.19:docs/compatible_microcontrollers.md
|
||||||
|
git diff 0.9.19 HEAD -- docs/compatible_microcontrollers.md | cat
|
||||||
|
-->
|
||||||
|
|
||||||
|
QMK は十分な容量のフラッシュメモリを備えた USB 対応 AVR または ARM マイクロコントローラで実行されます - 一般的に 32kB 以上ですが、ほとんどの機能を無効にすると*ほんの* 16kB に詰め込むことができます。
|
||||||
|
|
||||||
|
## Atmel AVR
|
||||||
|
|
||||||
|
以下は、USB スタックとして [LUFA](https://www.fourwalledcubicle.com/LUFA.php) を使います:
|
||||||
|
|
||||||
|
* [ATmega16U2](https://www.microchip.com/wwwproducts/en/ATmega16U2) / [ATmega32U2](https://www.microchip.com/wwwproducts/en/ATmega32U2)
|
||||||
|
* [ATmega16U4](https://www.microchip.com/wwwproducts/en/ATmega16U4) / [ATmega32U4](https://www.microchip.com/wwwproducts/en/ATmega32U4)
|
||||||
|
* [AT90USB64](https://www.microchip.com/wwwproducts/en/AT90USB646) / [AT90USB128](https://www.microchip.com/wwwproducts/en/AT90USB1286)
|
||||||
|
|
||||||
|
組み込みの USB インターフェースを持たない、いくつかの MCU は代わりに [V-USB](https://www.obdev.at/products/vusb/index.html) を使います:
|
||||||
|
|
||||||
|
* [ATmega32A](https://www.microchip.com/wwwproducts/en/ATmega32A)
|
||||||
|
* [ATmega328P](https://www.microchip.com/wwwproducts/en/ATmega328P)
|
||||||
|
* [ATmega328](https://www.microchip.com/wwwproducts/en/ATmega328)
|
||||||
|
|
||||||
|
## ARM
|
||||||
|
|
||||||
|
[ChibiOS](http://www.chibios.org) がサポートする USB 付きの ARM チップを使うこともできます。ほとんどのチップには十分な容量のフラッシュメモリがあります。動作するとわかっているのは:
|
||||||
|
|
||||||
|
### STMicroelectronics (STM32)
|
||||||
|
|
||||||
|
* [STM32F0x2](https://www.st.com/en/microcontrollers-microprocessors/stm32f0x2.html)
|
||||||
|
* [STM32F103](https://www.st.com/en/microcontrollers-microprocessors/stm32f103.html)
|
||||||
|
* [STM32F303](https://www.st.com/en/microcontrollers-microprocessors/stm32f303.html)
|
||||||
|
|
||||||
|
### NXP (Kinetis)
|
||||||
|
|
||||||
|
* [MKL26Z64](https://www.nxp.com/products/processors-and-microcontrollers/arm-microcontrollers/general-purpose-mcus/kl-series-cortex-m0-plus/kinetis-kl2x-72-96-mhz-usb-ultra-low-power-microcontrollers-mcus-based-on-arm-cortex-m0-plus-core:KL2x)
|
||||||
|
* [MK20DX128](https://www.nxp.com/products/processors-and-microcontrollers/arm-microcontrollers/general-purpose-mcus/k-series-cortex-m4/k2x-usb/kinetis-k20-50-mhz-full-speed-usb-mixed-signal-integration-microcontrollers-based-on-arm-cortex-m4-core:K20_50)
|
||||||
|
* [MK20DX256](https://www.nxp.com/products/processors-and-microcontrollers/arm-microcontrollers/general-purpose-mcus/k-series-cortex-m4/k2x-usb/kinetis-k20-72-mhz-full-speed-usb-mixed-signal-integration-microcontrollers-mcus-based-on-arm-cortex-m4-core:K20_72)
|
||||||
|
|
||||||
|
## Atmel ATSAM
|
||||||
|
|
||||||
|
Atmel の ATSAM マイクロコントローラの一つである、[Massdrop keyboards](https://github.com/qmk/qmk_firmware/tree/master/keyboards/massdrop) で使用されている [ATSAMD51J18A](https://www.microchip.com/wwwproducts/en/ATSAMD51J18A) には限定的なサポートがあります。
|
||||||
+140
-134
@@ -1,8 +1,8 @@
|
|||||||
# QMK の設定
|
# QMK の設定
|
||||||
|
|
||||||
<!---
|
<!---
|
||||||
original document: 2fe288d01:docs/config_options.md
|
original document: 0.8.62:docs/config_options.md
|
||||||
git diff 2fe288d01 HEAD -- docs/config_options.md | cat
|
git diff 0.8.62 HEAD -- docs/config_options.md | cat
|
||||||
-->
|
-->
|
||||||
|
|
||||||
QMK はほぼ無制限に設定可能です。可能なところはいかなるところでも、やりすぎな程、ユーザーがコードサイズを犠牲にしてでも彼らのキーボードをカスタマイズをすることを許しています。ただし、このレベルの柔軟性により設定が困難になります。
|
QMK はほぼ無制限に設定可能です。可能なところはいかなるところでも、やりすぎな程、ユーザーがコードサイズを犠牲にしてでも彼らのキーボードをカスタマイズをすることを許しています。ただし、このレベルの柔軟性により設定が困難になります。
|
||||||
@@ -39,167 +39,173 @@ QMK での全ての利用可能な設定にはデフォルトがあります。
|
|||||||
|
|
||||||
## ハードウェアオプション
|
## ハードウェアオプション
|
||||||
* `#define VENDOR_ID 0x1234`
|
* `#define VENDOR_ID 0x1234`
|
||||||
* VID を定義します。ほとんどの DIY プロジェクトにおいて、任意のものを定義できます
|
* VID を定義します。ほとんどの DIY プロジェクトにおいて、任意のものを定義できます
|
||||||
* `#define PRODUCT_ID 0x5678`
|
* `#define PRODUCT_ID 0x5678`
|
||||||
* PID を定義します。ほとんどの DIY プロジェクトでは、任意のものを定義できます
|
* PID を定義します。ほとんどの DIY プロジェクトでは、任意のものを定義できます
|
||||||
* `#define DEVICE_VER 0`
|
* `#define DEVICE_VER 0`
|
||||||
* デバイスのバージョンを定義します (多くの場合リビジョンに使われます)
|
* デバイスのバージョンを定義します (多くの場合リビジョンに使われます)
|
||||||
* `#define MANUFACTURER Me`
|
* `#define MANUFACTURER Me`
|
||||||
* 一般的に、誰もしくはどのブランドがボードを作成したか
|
* 一般的に、誰もしくはどのブランドがボードを作成したか
|
||||||
* `#define PRODUCT Board`
|
* `#define PRODUCT Board`
|
||||||
* キーボードの名前
|
* キーボードの名前
|
||||||
* `#define DESCRIPTION a keyboard`
|
* `#define DESCRIPTION a keyboard`
|
||||||
* キーボードの簡単な説明
|
* キーボードの簡単な説明
|
||||||
* `#define MATRIX_ROWS 5`
|
* `#define MATRIX_ROWS 5`
|
||||||
* キーボードのマトリックスの行の数
|
* キーボードのマトリックスの行の数
|
||||||
* `#define MATRIX_COLS 15`
|
* `#define MATRIX_COLS 15`
|
||||||
* キーボードのマトリックスの列の数
|
* キーボードのマトリックスの列の数
|
||||||
* `#define MATRIX_ROW_PINS { D0, D5, B5, B6 }`
|
* `#define MATRIX_ROW_PINS { D0, D5, B5, B6 }`
|
||||||
* 行のピン、上から下へ
|
* 行のピン、上から下へ
|
||||||
* `#define MATRIX_COL_PINS { F1, F0, B0, C7, F4, F5, F6, F7, D4, D6, B4, D7 }`
|
* `#define MATRIX_COL_PINS { F1, F0, B0, C7, F4, F5, F6, F7, D4, D6, B4, D7 }`
|
||||||
* 列のピン、左から右へ
|
* 列のピン、左から右へ
|
||||||
|
* `#define MATRIX_IO_DELAY 30`
|
||||||
|
* マトリックスピン状態の変更と値の読み取り間のマイクロ秒単位の遅延
|
||||||
* `#define UNUSED_PINS { D1, D2, D3, B1, B2, B3 }`
|
* `#define UNUSED_PINS { D1, D2, D3, B1, B2, B3 }`
|
||||||
* 参考として、キーボードで使われていないピン
|
* 参考として、キーボードで使われていないピン
|
||||||
* `#define MATRIX_HAS_GHOST`
|
* `#define MATRIX_HAS_GHOST`
|
||||||
* マトリックスにゴーストがあるか(ありそうにないか)定義します
|
* マトリックスにゴーストがあるか(ありそうにないか)定義します
|
||||||
* `#define DIODE_DIRECTION COL2ROW`
|
* `#define DIODE_DIRECTION COL2ROW`
|
||||||
* COL2ROW あるいは ROW2COL - マトリックスがどのように設定されているか。COL2ROW は、スイッチとロウ(行)ラインの間にダイオードが黒い印をロウ(行)ラインに向けて置いてあることを意味します。
|
* COL2ROW あるいは ROW2COL - マトリックスがどのように設定されているか。COL2ROW は、スイッチとロウ(行)ラインの間にダイオードが黒い印をロウ(行)ラインに向けて置いてあることを意味します。
|
||||||
* `#define DIRECT_PINS { { F1, F0, B0, C7 }, { F4, F5, F6, F7 } }`
|
* `#define DIRECT_PINS { { F1, F0, B0, C7 }, { F4, F5, F6, F7 } }`
|
||||||
* ロウ(行)ラインとカラム(列)ラインにマップされているピンを左から右に。各スイッチが個別のピンとグラウンドに接続されているマトリックスを定義します。
|
* ロウ(行)ラインとカラム(列)ラインにマップされているピンを左から右に。各スイッチが個別のピンとグラウンドに接続されているマトリックスを定義します。
|
||||||
* `#define AUDIO_VOICES`
|
* `#define AUDIO_VOICES`
|
||||||
* (循環させるために)代替音声を有効にします
|
* (循環させるために)代替音声を有効にします
|
||||||
* `#define C4_AUDIO`
|
* `#define C4_AUDIO`
|
||||||
* ピン C4 のオーディオを有効にします
|
* ピン C4 のオーディオを有効にします
|
||||||
* `#define C5_AUDIO`
|
* `#define C5_AUDIO`
|
||||||
* ピン C5 のオーディオを有効にします
|
* ピン C5 のオーディオを有効にします
|
||||||
* `#define C6_AUDIO`
|
* `#define C6_AUDIO`
|
||||||
* ピン C6 のオーディオを有効にします
|
* ピン C6 のオーディオを有効にします
|
||||||
* `#define B5_AUDIO`
|
* `#define B5_AUDIO`
|
||||||
* ピン B5 のオーディオを有効にします (C[4-6]\_AUDIO の1つとともに B[5-7]\_AUDIO の1つが有効にされている場合、疑似ステレオが有効にされます)
|
* ピン B5 のオーディオを有効にします (C[4-6]\_AUDIO の1つとともに B[5-7]\_AUDIO の1つが有効にされている場合、疑似ステレオが有効にされます)
|
||||||
* `#define B6_AUDIO`
|
* `#define B6_AUDIO`
|
||||||
* ピン B6 のオーディオを有効にします (C[4-6]\_AUDIO の1つとともに B[5-7]\_AUDIO の1つが有効にされている場合、疑似ステレオが有効にされます)
|
* ピン B6 のオーディオを有効にします (C[4-6]\_AUDIO の1つとともに B[5-7]\_AUDIO の1つが有効にされている場合、疑似ステレオが有効にされます)
|
||||||
* `#define B7_AUDIO`
|
* `#define B7_AUDIO`
|
||||||
* ピン B7 のオーディオを有効にします (C[4-6]\_AUDIO の1つとともに B[5-7]\_AUDIO の1つが有効にされている場合、疑似ステレオが有効にされます)
|
* ピン B7 のオーディオを有効にします (C[4-6]\_AUDIO の1つとともに B[5-7]\_AUDIO の1つが有効にされている場合、疑似ステレオが有効にされます)
|
||||||
* `#define BACKLIGHT_PIN B7`
|
* `#define BACKLIGHT_PIN B7`
|
||||||
* バックライトのピン
|
* バックライトのピン
|
||||||
* `#define BACKLIGHT_LEVELS 3`
|
* `#define BACKLIGHT_LEVELS 3`
|
||||||
* バックライトのレベル数 (off を除いて最大31)
|
* バックライトのレベル数 (off を除いて最大31)
|
||||||
* `#define BACKLIGHT_BREATHING`
|
* `#define BACKLIGHT_BREATHING`
|
||||||
* バックライトのブレスを有効にします
|
* バックライトのブレスを有効にします
|
||||||
* `#define BREATHING_PERIOD 6`
|
* `#define BREATHING_PERIOD 6`
|
||||||
* 1つのバックライトの "ブレス" の長さの秒数
|
* 1つのバックライトの "ブレス" の長さの秒数
|
||||||
* `#define DEBOUNCE 5`
|
* `#define DEBOUNCE 5`
|
||||||
* ピンの値を読み取る時の遅延 (5がデフォルト)
|
* ピンの値を読み取る時の遅延 (5がデフォルト)
|
||||||
* `#define LOCKING_SUPPORT_ENABLE`
|
* `#define LOCKING_SUPPORT_ENABLE`
|
||||||
* メカニカルロックのサポート。キーマップで KC_LCAP、 KC_LNUM そして KC_LSCR を使えるようにします
|
* メカニカルロックのサポート。キーマップで KC_LCAP、 KC_LNUM そして KC_LSCR を使えるようにします
|
||||||
* `#define LOCKING_RESYNC_ENABLE`
|
* `#define LOCKING_RESYNC_ENABLE`
|
||||||
* キーボードの LED の状態をスイッチの状態と一致させ続けようとします
|
* キーボードの LED の状態をスイッチの状態と一致させ続けようとします
|
||||||
* `#define IS_COMMAND() (get_mods() == MOD_MASK_SHIFT)`
|
* `#define IS_COMMAND() (get_mods() == MOD_MASK_SHIFT)`
|
||||||
* マジックコマンドの使用を可能にするキーの組み合わせ (デバッグに便利です)
|
* マジックコマンドの使用を可能にするキーの組み合わせ (デバッグに便利です)
|
||||||
* `#define USB_MAX_POWER_CONSUMPTION 500`
|
* `#define USB_MAX_POWER_CONSUMPTION 500`
|
||||||
* デバイスの USB 経由の最大電力(mA) を設定します (デフォルト: 500)
|
* デバイスの USB 経由の最大電力(mA) を設定します (デフォルト: 500)
|
||||||
* `#define USB_POLLING_INTERVAL_MS 10`
|
* `#define USB_POLLING_INTERVAL_MS 10`
|
||||||
* キーボード、マウス および 共有 (NKRO/メディアキー) インタフェースのための USB ポーリングレートをミリ秒で設定します
|
* キーボード、マウス および 共有 (NKRO/メディアキー) インタフェースのための USB ポーリングレートをミリ秒で設定します
|
||||||
* `#define F_SCL 100000L`
|
* `#define F_SCL 100000L`
|
||||||
* I2C を使用するキーボードのための I2C クロックレート速度を設定します。デフォルトは `400000L` ですが、`split_common` を使っているキーボードは別でデフォルトは `100000L` です。
|
* I2C を使用するキーボードのための I2C クロックレート速度を設定します。デフォルトは `400000L` ですが、`split_common` を使っているキーボードは別でデフォルトは `100000L` です。
|
||||||
|
|
||||||
## 無効にできる機能
|
## 無効にできる機能
|
||||||
|
|
||||||
これらのオプションを定義すると、関連する機能が無効になり、コードサイズを節約できます。
|
これらのオプションを定義すると、関連する機能が無効になり、コードサイズを節約できます。
|
||||||
|
|
||||||
* `#define NO_DEBUG`
|
* `#define NO_DEBUG`
|
||||||
* デバッグを無効にします
|
* デバッグを無効にします
|
||||||
* `#define NO_PRINT`
|
* `#define NO_PRINT`
|
||||||
* hid_listen を使った出力やデバッグを無効にします
|
* hid_listen を使った出力やデバッグを無効にします
|
||||||
* `#define NO_ACTION_LAYER`
|
* `#define NO_ACTION_LAYER`
|
||||||
* レイヤーを無効にします
|
* レイヤーを無効にします
|
||||||
* `#define NO_ACTION_TAPPING`
|
* `#define NO_ACTION_TAPPING`
|
||||||
* タップダンスと他のタップ機能を無効にします
|
* タップダンスと他のタップ機能を無効にします
|
||||||
* `#define NO_ACTION_ONESHOT`
|
* `#define NO_ACTION_ONESHOT`
|
||||||
* ワンショットモディファイアを無効にします
|
* ワンショットモディファイアを無効にします
|
||||||
* `#define NO_ACTION_MACRO`
|
* `#define NO_ACTION_MACRO`
|
||||||
* 古い形式のマクロ処理を無効にします: MACRO() & action_get_macro
|
* 古い形式のマクロ処理を無効にします: MACRO() & action_get_macro
|
||||||
* `#define NO_ACTION_FUNCTION`
|
* `#define NO_ACTION_FUNCTION`
|
||||||
* fn_actions 配列(非推奨)からの action_function() の呼び出しを無効にします
|
* fn_actions 配列(非推奨)からの action_function() の呼び出しを無効にします
|
||||||
|
|
||||||
## 有効にできる機能
|
## 有効にできる機能
|
||||||
|
|
||||||
これらのオプションを定義すると、関連する機能が有効になり、コードサイズが大きくなるかもしれません。
|
これらのオプションを定義すると、関連する機能が有効になり、コードサイズが大きくなるかもしれません。
|
||||||
|
|
||||||
* `#define FORCE_NKRO`
|
* `#define FORCE_NKRO`
|
||||||
* NKRO をデフォルトでオンにする必要があります。これにより EEPROM の設定に関係なく、キーボードの起動時に NKRO が強制的にオンになります。NKRO は引き続きオフにできますが、キーボードを再起動すると再びオンになります。
|
* NKRO をデフォルトでオンにする必要があります。これにより EEPROM の設定に関係なく、キーボードの起動時に NKRO が強制的にオンになります。NKRO は引き続きオフにできますが、キーボードを再起動すると再びオンになります。
|
||||||
* `#define STRICT_LAYER_RELEASE`
|
* `#define STRICT_LAYER_RELEASE`
|
||||||
* キーリリースがどのレイヤーから来たのかを覚えるのではなく、現在のレイヤースタックを使って強制的に評価されるようにします (高度なケースに使われます)
|
* キーリリースがどのレイヤーから来たのかを覚えるのではなく、現在のレイヤースタックを使って強制的に評価されるようにします (高度なケースに使われます)
|
||||||
|
|
||||||
## 設定可能な挙動
|
## 設定可能な挙動
|
||||||
|
|
||||||
* `#define TAPPING_TERM 200`
|
* `#define TAPPING_TERM 200`
|
||||||
* タップがホールドになるまでの時間。500以上に設定された場合、タップ期間中にタップされたキーもホールドになります。(訳注: PERMISSIVE_HOLDも参照)
|
* タップがホールドになるまでの時間。500以上に設定された場合、タップ期間中にタップされたキーもホールドになります。(訳注: PERMISSIVE_HOLDも参照)
|
||||||
* `#define TAPPING_TERM_PER_KEY`
|
* `#define TAPPING_TERM_PER_KEY`
|
||||||
* キーごとの `TAPPING_TERM` 設定の処理を有効にします
|
* キーごとの `TAPPING_TERM` 設定の処理を有効にします
|
||||||
* `#define RETRO_TAPPING`
|
* `#define RETRO_TAPPING`
|
||||||
* 押下とリリースの間に他のキーによる中断がなければ、TAPPING_TERM の後であってもとにかくタップします
|
* 押下とリリースの間に他のキーによる中断がなければ、TAPPING_TERM の後であってもとにかくタップします
|
||||||
* 詳細は [Retro Tapping](ja/feature_advanced_keycodes.md#retro-tapping) を見てください
|
* 詳細は [Retro Tapping](ja/tap_hold.md#retro-tapping) を見てください
|
||||||
* `#define TAPPING_TOGGLE 2`
|
* `#define TAPPING_TOGGLE 2`
|
||||||
* トグルを引き起こす前のタップ数
|
* トグルを引き起こす前のタップ数
|
||||||
* `#define PERMISSIVE_HOLD`
|
* `#define PERMISSIVE_HOLD`
|
||||||
* `TAPPING_TERM` にヒットしていなくても、リリースする前に別のキーが押されると、タップとフォールドキーがホールドを引き起こします
|
* `TAPPING_TERM` にヒットしていなくても、リリースする前に別のキーが押されると、タップとホールドキーがホールドを引き起こします
|
||||||
* 詳細は [Permissive Hold](ja/feature_advanced_keycodes.md#permissive-hold) を見てください
|
* 詳細は [Permissive Hold](ja/tap_hold.md#permissive-hold) を見てください
|
||||||
|
* `#define PERMISSIVE_HOLD_PER_KEY`
|
||||||
|
* キーごとの `PERMISSIVE_HOLD` 設定の処理を有効にします
|
||||||
* `#define IGNORE_MOD_TAP_INTERRUPT`
|
* `#define IGNORE_MOD_TAP_INTERRUPT`
|
||||||
* 両方のキーに `TAPPING_TERM` を適用することで、ホールド時に他のキーに変換するキーを使ってローリングコンボ (zx) をすることができるようにします
|
* 両方のキーに `TAPPING_TERM` を適用することで、ホールド時に他のキーに変換するキーを使ってローリングコンボ (zx) をすることができるようにします
|
||||||
* 詳細は [Mod tap interrupt](ja/feature_advanced_keycodes.md#ignore-mod-tap-interrupt) を見てください
|
* 詳細は [Ignore Mod Tap Interrupt](ja/tap_hold.md#ignore-mod-tap-interrupt) を見てください
|
||||||
* `#define IGNORE_MOD_TAP_INTERRUPT_PER_KEY`
|
* `#define IGNORE_MOD_TAP_INTERRUPT_PER_KEY`
|
||||||
* キーごとの `IGNORE_MOD_TAP_INTERRUPT` 設定の処理を有効にします
|
* キーごとの `IGNORE_MOD_TAP_INTERRUPT` 設定の処理を有効にします
|
||||||
* `#define TAPPING_FORCE_HOLD`
|
* `#define TAPPING_FORCE_HOLD`
|
||||||
* タップされた直後に、デュアルロールキーを修飾子として使用できるようにします
|
* タップされた直後に、デュアルロールキーを修飾子として使用できるようにします
|
||||||
* [Hold after tap](ja/feature_advanced_keycodes.md#tapping-force-hold)を見てください
|
* [Tapping Force Hold](ja/tap_hold.md#tapping-force-hold)を見てください
|
||||||
* タップトグル機能を無効にします (`TT` あるいは One Shot Tap Toggle)
|
* タップトグル機能を無効にします (`TT` あるいは One Shot Tap Toggle)
|
||||||
* `#define TAPPING_FORCE_HOLD_PER_KEY`
|
* `#define TAPPING_FORCE_HOLD_PER_KEY`
|
||||||
* キーごとの `TAPPING_FORCE_HOLD` 設定処理を有効にします。
|
* キーごとの `TAPPING_FORCE_HOLD` 設定処理を有効にします。
|
||||||
* `#define LEADER_TIMEOUT 300`
|
* `#define LEADER_TIMEOUT 300`
|
||||||
* リーダーキーがタイムアウトするまでの時間
|
* リーダーキーがタイムアウトするまでの時間
|
||||||
* タイムアウトする前にシーケンスを終了できない場合は、タイムアウトの設定を増やす必要があるかもしれません。あるいは、`LEADER_PER_KEY_TIMING` オプションを有効にすると良いでしょう。これは各キーがタップされた後でタイムアウトを再設定します。
|
* タイムアウトする前にシーケンスを終了できない場合は、タイムアウトの設定を増やす必要があるかもしれません。あるいは、`LEADER_PER_KEY_TIMING` オプションを有効にすると良いでしょう。これは各キーがタップされた後でタイムアウトを再設定します。
|
||||||
* `#define LEADER_PER_KEY_TIMING`
|
* `#define LEADER_PER_KEY_TIMING`
|
||||||
* 全体では無く各キーを押すたびに実行されるリーダーキーコードのタイマーを設定します
|
* 全体では無く各キーを押すたびに実行されるリーダーキーコードのタイマーを設定します
|
||||||
* `#define LEADER_KEY_STRICT_KEY_PROCESSING`
|
* `#define LEADER_KEY_STRICT_KEY_PROCESSING`
|
||||||
* Mod-Tap および Layer-Tap キーコードのためのキーコードフィルタリングを無効にします。例えば、これを有効にすると、`KC_A` を使いたい場合は `MT(MOD_CTL, KC_A)` を指定する必要があります。
|
* Mod-Tap および Layer-Tap キーコードのためのキーコードフィルタリングを無効にします。例えば、これを有効にすると、`KC_A` を使いたい場合は `MT(MOD_CTL, KC_A)` を指定する必要があります。
|
||||||
* `#define ONESHOT_TIMEOUT 300`
|
* `#define ONESHOT_TIMEOUT 300`
|
||||||
* ワンショットがタイムアウトするまでの時間
|
* ワンショットがタイムアウトするまでの時間
|
||||||
* `#define ONESHOT_TAP_TOGGLE 2`
|
* `#define ONESHOT_TAP_TOGGLE 2`
|
||||||
* ワンショットトグルが引き起こされるまでのタップ数
|
* ワンショットトグルが引き起こされるまでのタップ数
|
||||||
* `#define QMK_KEYS_PER_SCAN 4`
|
* `#define QMK_KEYS_PER_SCAN 4`
|
||||||
* 走査ごとに1つ以上のキーを送信できるようにします。デフォルトでは、走査ごとに `process_record()` 経由で1つのキーイベントのみが送信されます。これはほとんどのタイピングにほとんど影響しませんが、多くのコードを入力しているか、走査レートが最初から遅い場合、キーイベントの処理に多少の遅延が生じる可能性があります。それぞれのプレスとリリースは別のイベントです。スキャン時間が 1ms 程度のキーボードの場合、とても高速なタイピストでさえ、実際にキーボードから数 ms 以上の遅延を発生させるのに必要な 500 キーストロークを1秒間に生成することはないでしょう。しかし、3~4ms の走査時間でコードを入力している場合はどうでしょうか?おそらくこれが必要です。
|
* 走査ごとに1つ以上のキーを送信できるようにします。デフォルトでは、走査ごとに `process_record()` 経由で1つのキーイベントのみが送信されます。これはほとんどのタイピングにほとんど影響しませんが、多くのコードを入力しているか、走査レートが最初から遅い場合、キーイベントの処理に多少の遅延が生じる可能性があります。それぞれのプレスとリリースは別のイベントです。スキャン時間が 1ms 程度のキーボードの場合、とても高速なタイピストでさえ、実際にキーボードから数 ms 以上の遅延を発生させるのに必要な 500 キーストロークを1秒間に生成することはないでしょう。しかし、3~4ms の走査時間でコードを入力している場合はどうでしょうか?おそらくこれが必要です。
|
||||||
* `#define COMBO_COUNT 2`
|
* `#define COMBO_COUNT 2`
|
||||||
* [コンボ](ja/feature_combo.md)機能で使っているコンボの数にこれを設定します。
|
* [コンボ](ja/feature_combo.md)機能で使っているコンボの数にこれを設定します。
|
||||||
* `#define COMBO_TERM 200`
|
* `#define COMBO_TERM 200`
|
||||||
* コンボキーが検出されるまでの時間。定義されていない場合は、デフォルトは `TAPPING_TERM` です。
|
* コンボキーが検出されるまでの時間。定義されていない場合は、デフォルトは `TAPPING_TERM` です。
|
||||||
* `#define TAP_CODE_DELAY 100`
|
* `#define TAP_CODE_DELAY 100`
|
||||||
* 適切な登録に問題がある場合(VUSB ボードで珍しくない)、`register_code` と `unregister_code` の間の遅延を設定します。値はミリ秒です。
|
* 適切な登録に問題がある場合(VUSB ボードで珍しくない)、`register_code` と `unregister_code` の間の遅延を設定します。値はミリ秒です。
|
||||||
* `#define TAP_HOLD_CAPS_DELAY 80`
|
* `#define TAP_HOLD_CAPS_DELAY 80`
|
||||||
* MacOS で特別な処理が行われるため、`KC_CAPSLOCK` を使う時にタップホールドキー (`LT`, `MT`) に遅延を設定します。この値はミリ秒で、定義されていない場合はデフォルトは80msです。macOS については、これを200以上に設定すると良いでしょう。
|
* MacOS で特別な処理が行われるため、`KC_CAPSLOCK` を使う時にタップホールドキー (`LT`, `MT`) に遅延を設定します。この値はミリ秒で、定義されていない場合はデフォルトは80msです。macOS については、これを200以上に設定すると良いでしょう。
|
||||||
|
|
||||||
## RGB ライト設定 :id=rgb-light-configuration
|
## RGB ライト設定 :id=rgb-light-configuration
|
||||||
|
|
||||||
* `#define RGB_DI_PIN D7`
|
* `#define RGB_DI_PIN D7`
|
||||||
* WS2812 の DI 端子につなぐピン
|
* WS2812 の DI 端子につなぐピン
|
||||||
* `#define RGBLIGHT_ANIMATIONS`
|
* `#define RGBLIGHT_ANIMATIONS`
|
||||||
* RGB アニメーションを実行します
|
* RGB アニメーションを実行します
|
||||||
|
* `#define RGBLIGHT_LAYERS`
|
||||||
|
* オンとオフを切り替えることができる [ライトレイヤー](ja/feature_rgblight.md) を定義できます。現在のキーボードレイヤーまたは Caps Lock 状態を表示するのに最適です。
|
||||||
* `#define RGBLED_NUM 12`
|
* `#define RGBLED_NUM 12`
|
||||||
* LED の数
|
* LED の数
|
||||||
* `#define RGBLIGHT_SPLIT`
|
* `#define RGBLIGHT_SPLIT`
|
||||||
* 分割キーボードの左半分の RGB LED の出力を右半分の RGB LED の入力につなげるかわりに、それぞれの側で個別にコントローラの出力ピンが直接 RGB LED の入力に繋がっているときは、この定義が必要です。
|
* 分割キーボードの左半分の RGB LED の出力を右半分の RGB LED の入力につなげるかわりに、それぞれの側で個別にコントローラの出力ピンが直接 RGB LED の入力に繋がっているときは、この定義が必要です。
|
||||||
* `#define RGBLED_SPLIT { 6, 6 }`
|
* `#define RGBLED_SPLIT { 6, 6 }`
|
||||||
* 分割キーボードの各半分の `RGB_DI_PIN` に直接配線されている接続されている LED の数
|
* 分割キーボードの各半分の `RGB_DI_PIN` に直接配線されている接続されている LED の数
|
||||||
* 最初の値は左半分の LED の数を示し、2番目の値は右半分です。
|
* 最初の値は左半分の LED の数を示し、2番目の値は右半分です。
|
||||||
* RGBLED_SPLIT が定義されている場合、RGBLIGHT_SPLIT は暗黙的に定義されます。
|
* RGBLED_SPLIT が定義されている場合、RGBLIGHT_SPLIT は暗黙的に定義されます。
|
||||||
* `#define RGBLIGHT_HUE_STEP 12`
|
* `#define RGBLIGHT_HUE_STEP 12`
|
||||||
* 色相の増減時のステップ単位
|
* 色相の増減時のステップ単位
|
||||||
* `#define RGBLIGHT_SAT_STEP 25`
|
* `#define RGBLIGHT_SAT_STEP 25`
|
||||||
* 彩度の増減時のステップ単位
|
* 彩度の増減時のステップ単位
|
||||||
* `#define RGBLIGHT_VAL_STEP 12`
|
* `#define RGBLIGHT_VAL_STEP 12`
|
||||||
* 値(明度)の増減時のステップ単位
|
* 値(明度)の増減時のステップ単位
|
||||||
* `#define RGBW`
|
* `#define RGBW`
|
||||||
* RGBW LED のサポートを有効にします
|
* RGBW LED のサポートを有効にします
|
||||||
|
|
||||||
## マウスキーオプション
|
## マウスキーオプション
|
||||||
|
|
||||||
@@ -214,7 +220,7 @@ QMK での全ての利用可能な設定にはデフォルトがあります。
|
|||||||
分割キーボード固有のオプション。あなたの rules.mk に 'SPLIT_KEYBOARD = yes' が有ることを確認してください。
|
分割キーボード固有のオプション。あなたの rules.mk に 'SPLIT_KEYBOARD = yes' が有ることを確認してください。
|
||||||
|
|
||||||
* `SPLIT_TRANSPORT = custom`
|
* `SPLIT_TRANSPORT = custom`
|
||||||
* 標準の分割通信ルーチンをカスタムのものに置き換えることができます。現在、ARM ベースの分割キーボードはこれを使わなければなりません。
|
* 標準の分割通信ルーチンをカスタムのものに置き換えることができます。現在、ARM ベースの分割キーボードはこれを使わなければなりません。
|
||||||
|
|
||||||
### 左右の設定
|
### 左右の設定
|
||||||
|
|
||||||
@@ -233,52 +239,52 @@ QMK での全ての利用可能な設定にはデフォルトがあります。
|
|||||||
#### 左右を定義します
|
#### 左右を定義します
|
||||||
|
|
||||||
* `#define SPLIT_HAND_PIN B7`
|
* `#define SPLIT_HAND_PIN B7`
|
||||||
* high/low ピンを使って左右を決定します。low = 右手、high = 左手。`B7` を使っているピンに置き換えます。これはオプションで、`SPLIT_HAND_PIN` が未定義のままである場合、EE_HANDS メソッドまたは標準の Let's Splitが使っている MASTER_LEFT / MASTER_RIGHT 定義をまだ使うことができます。
|
* high/low ピンを使って左右を決定します。low = 右手、high = 左手。`B7` を使っているピンに置き換えます。これはオプションで、`SPLIT_HAND_PIN` が未定義のままである場合、EE_HANDS メソッドまたは標準の Let's Splitが使っている MASTER_LEFT / MASTER_RIGHT 定義をまだ使うことができます。
|
||||||
|
|
||||||
* `#define EE_HANDS` (`SPLIT_HAND_PIN` が定義されていない場合のみ動作します)
|
* `#define EE_HANDS` (`SPLIT_HAND_PIN` が定義されていない場合のみ動作します)
|
||||||
* `eeprom-lefthand.eep`/`eeprom-righthand.eep` がそれぞれの半分に書き込まれた後で、EEPROM 内に格納されている左右の設定の値を読み込みます。
|
* `eeprom-lefthand.eep`/`eeprom-righthand.eep` がそれぞれの半分に書き込まれた後で、EEPROM 内に格納されている左右の設定の値を読み込みます。
|
||||||
|
|
||||||
* `#define MASTER_RIGHT`
|
* `#define MASTER_RIGHT`
|
||||||
* マスター側が右側と定義されます。
|
* マスター側が右側と定義されます。
|
||||||
|
|
||||||
### 他のオプション
|
### 他のオプション
|
||||||
|
|
||||||
* `#define USE_I2C`
|
* `#define USE_I2C`
|
||||||
* Serial の代わりに I2C を使う場合 (デフォルトは serial)
|
* Serial の代わりに I2C を使う場合 (デフォルトは serial)
|
||||||
|
|
||||||
* `#define SOFT_SERIAL_PIN D0`
|
* `#define SOFT_SERIAL_PIN D0`
|
||||||
* serial を使う場合、これを定義します。`D0` あるいは `D1`,`D2`,`D3`,`E6`。
|
* serial を使う場合、これを定義します。`D0` あるいは `D1`,`D2`,`D3`,`E6`。
|
||||||
|
|
||||||
* `#define MATRIX_ROW_PINS_RIGHT { <row pins> }`
|
* `#define MATRIX_ROW_PINS_RIGHT { <row pins> }`
|
||||||
* `#define MATRIX_COL_PINS_RIGHT { <col pins> }`
|
* `#define MATRIX_COL_PINS_RIGHT { <col pins> }`
|
||||||
* 右半分に左半分と異なるピン配置を指定したい場合は、`MATRIX_ROW_PINS_RIGHT`/`MATRIX_COL_PINS_RIGHT` を定義することができます。現在のところ、`MATRIX_ROW_PINS` のサイズは `MATRIX_ROW_PINS_RIGHT` と同じでなければならず、列の定義も同様です。
|
* 右半分に左半分と異なるピン配置を指定したい場合は、`MATRIX_ROW_PINS_RIGHT`/`MATRIX_COL_PINS_RIGHT` を定義することができます。現在のところ、`MATRIX_ROW_PINS` のサイズは `MATRIX_ROW_PINS_RIGHT` と同じでなければならず、列の定義も同様です。
|
||||||
|
|
||||||
* `#define DIRECT_PINS_RIGHT { { F1, F0, B0, C7 }, { F4, F5, F6, F7 } }`
|
* `#define DIRECT_PINS_RIGHT { { F1, F0, B0, C7 }, { F4, F5, F6, F7 } }`
|
||||||
* 右半分に左半分と異なる直接ピン配置を指定したい場合は、`DIRECT_PINS_RIGHT` を定義することができます。現在のところ、`DIRECT_PINS` のサイズは `DIRECT_PINS_RIGHT` と同じでなければなりません。
|
* 右半分に左半分と異なる直接ピン配置を指定したい場合は、`DIRECT_PINS_RIGHT` を定義することができます。現在のところ、`DIRECT_PINS` のサイズは `DIRECT_PINS_RIGHT` と同じでなければなりません。
|
||||||
|
|
||||||
* `#define RGBLED_SPLIT { 6, 6 }`
|
* `#define RGBLED_SPLIT { 6, 6 }`
|
||||||
* [RGB ライト設定](#rgb-light-configuration)を見てください。
|
* [RGB ライト設定](#rgb-light-configuration)を見てください。
|
||||||
|
|
||||||
* `#define SELECT_SOFT_SERIAL_SPEED <speed>` (デフォルトの速度は1です)
|
* `#define SELECT_SOFT_SERIAL_SPEED <speed>` (デフォルトの速度は1です)
|
||||||
* serial 通信を使う時のプロトコルの速度を設定します。
|
* serial 通信を使う時のプロトコルの速度を設定します。
|
||||||
* 速度:
|
* 速度:
|
||||||
* 0: 約 189kbps (実験目的のみ)
|
* 0: 約 189kbps (実験目的のみ)
|
||||||
* 1: 約 137kbps (デフォルト)
|
* 1: 約 137kbps (デフォルト)
|
||||||
* 2: 約 75kbps
|
* 2: 約 75kbps
|
||||||
* 3: 約 39kbps
|
* 3: 約 39kbps
|
||||||
* 4: 約 26kbps
|
* 4: 約 26kbps
|
||||||
* 5: 約 20kbps
|
* 5: 約 20kbps
|
||||||
|
|
||||||
* `#define SPLIT_USB_DETECT`
|
* `#define SPLIT_USB_DETECT`
|
||||||
* マスタ/スレーブを委任する時に(タイムアウト付きで) USB 接続を検出します
|
* マスタ/スレーブを委任する時に(タイムアウト付きで) USB 接続を検出します
|
||||||
* ARM についてはデフォルトの挙動
|
* ARM についてはデフォルトの挙動
|
||||||
* AVR Teensy については必須
|
* AVR Teensy については必須
|
||||||
|
|
||||||
* `#define SPLIT_USB_TIMEOUT 2000`
|
* `#define SPLIT_USB_TIMEOUT 2000`
|
||||||
* `SPLIT_USB_DETECT` を使う時のマスタ/スレーブを検出する場合の最大タイムアウト
|
* `SPLIT_USB_DETECT` を使う時のマスタ/スレーブを検出する場合の最大タイムアウト
|
||||||
|
|
||||||
* `#define SPLIT_USB_TIMEOUT_POLL 10`
|
* `#define SPLIT_USB_TIMEOUT_POLL 10`
|
||||||
* `SPLIT_USB_DETECT` を使う時のマスタ/スレーブを検出する場合のポーリング頻度
|
* `SPLIT_USB_DETECT` を使う時のマスタ/スレーブを検出する場合のポーリング頻度
|
||||||
|
|
||||||
# `rules.mk` ファイル
|
# `rules.mk` ファイル
|
||||||
|
|
||||||
@@ -287,11 +293,11 @@ QMK での全ての利用可能な設定にはデフォルトがあります。
|
|||||||
## ビルドオプション
|
## ビルドオプション
|
||||||
|
|
||||||
* `DEFAULT_FOLDER`
|
* `DEFAULT_FOLDER`
|
||||||
* キーボードに1つ以上のサブフォルダがある場合にデフォルトのフォルダを指定するために使われます。
|
* キーボードに1つ以上のサブフォルダがある場合にデフォルトのフォルダを指定するために使われます。
|
||||||
* `FIRMWARE_FORMAT`
|
* `FIRMWARE_FORMAT`
|
||||||
* ビルドの後でルート `qmk_firmware` フォルダにコピーされる形式 (bin, hex) を定義します。
|
* ビルドの後でルート `qmk_firmware` フォルダにコピーされる形式 (bin, hex) を定義します。
|
||||||
* `SRC`
|
* `SRC`
|
||||||
* コンパイル・リンクリストにファイルを追加するために使われます。
|
* コンパイル・リンクリストにファイルを追加するために使われます。
|
||||||
* `LIB_SRC`
|
* `LIB_SRC`
|
||||||
* コンパイル・リンクリストにライブラリとしてファイルを追加するために使われます。
|
* コンパイル・リンクリストにライブラリとしてファイルを追加するために使われます。
|
||||||
`LIB_SRC` で指定されたファイルは、`SRC` で指定されたファイルの後にリンクされます。
|
`LIB_SRC` で指定されたファイルは、`SRC` で指定されたファイルの後にリンクされます。
|
||||||
@@ -307,11 +313,11 @@ QMK での全ての利用可能な設定にはデフォルトがあります。
|
|||||||
... a.o c.o ... lib_b.a lib_d.a ...
|
... a.o c.o ... lib_b.a lib_d.a ...
|
||||||
```
|
```
|
||||||
* `LAYOUTS`
|
* `LAYOUTS`
|
||||||
* このキーボードがサポートする[レイアウト](ja/feature_layouts.md)のリスト
|
* このキーボードがサポートする[レイアウト](ja/feature_layouts.md)のリスト
|
||||||
* `LINK_TIME_OPTIMIZATION_ENABLE`
|
* `LINK_TIME_OPTIMIZATION_ENABLE`
|
||||||
* キーボードをコンパイルする時に、Link Time Optimization (`LTO`) を有効にします。これは処理に時間が掛かりますが、コンパイルされたサイズを大幅に減らします (そして、ファームウェアが小さいため、追加の時間は分からないくらいです)。ただし、`LTO` が有効な場合、古いマクロと関数の機能が壊れるため、自動的にこれらの機能を無効にします。これは `NO_ACTION_MACRO` と `NO_ACTION_FUNCTION` を自動的に定義することで行われます。
|
* キーボードをコンパイルする時に、Link Time Optimization (`LTO`) を有効にします。これは処理に時間が掛かりますが、コンパイルされたサイズを大幅に減らします (そして、ファームウェアが小さいため、追加の時間は分からないくらいです)。ただし、`LTO` が有効な場合、古いマクロと関数の機能が壊れるため、自動的にこれらの機能を無効にします。これは `NO_ACTION_MACRO` と `NO_ACTION_FUNCTION` を自動的に定義することで行われます。
|
||||||
* `LTO_ENABLE`
|
* `LTO_ENABLE`
|
||||||
* LINK_TIME_OPTIMIZATION_ENABLE と同じ意味です。`LINK_TIME_OPTIMIZATION_ENABLE` の代わりに `LTO_ENABLE` を使うことができます。
|
* LINK_TIME_OPTIMIZATION_ENABLE と同じ意味です。`LINK_TIME_OPTIMIZATION_ENABLE` の代わりに `LTO_ENABLE` を使うことができます。
|
||||||
|
|
||||||
## AVR MCU オプション
|
## AVR MCU オプション
|
||||||
* `MCU = atmega32u4`
|
* `MCU = atmega32u4`
|
||||||
@@ -320,56 +326,56 @@ QMK での全ての利用可能な設定にはデフォルトがあります。
|
|||||||
* `F_USB = $(F_CPU)`
|
* `F_USB = $(F_CPU)`
|
||||||
* `OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT`
|
* `OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT`
|
||||||
* `BOOTLOADER = atmel-dfu` と以下のオプション:
|
* `BOOTLOADER = atmel-dfu` と以下のオプション:
|
||||||
* `atmel-dfu`
|
* `atmel-dfu`
|
||||||
* `lufa-dfu`
|
* `lufa-dfu`
|
||||||
* `qmk-dfu`
|
* `qmk-dfu`
|
||||||
* `halfkay`
|
* `halfkay`
|
||||||
* `caterina`
|
* `caterina`
|
||||||
* `bootloadHID`
|
* `bootloadHID`
|
||||||
* `USBasp`
|
* `USBasp`
|
||||||
|
|
||||||
## 機能オプション
|
## 機能オプション :id=feature-options
|
||||||
|
|
||||||
これらを使って特定の機能のビルドを有効または無効にします。有効にすればするほどファームウェアが大きくなり、MCU には大きすぎるファームウェアを構築するリスクがあります。
|
これらを使って特定の機能のビルドを有効または無効にします。有効にすればするほどファームウェアが大きくなり、MCU には大きすぎるファームウェアを構築するリスクがあります。
|
||||||
|
|
||||||
* `BOOTMAGIC_ENABLE`
|
* `BOOTMAGIC_ENABLE`
|
||||||
* 仮想 DIP スイッチ設定
|
* 仮想 DIP スイッチ設定
|
||||||
* `MOUSEKEY_ENABLE`
|
* `MOUSEKEY_ENABLE`
|
||||||
* マウスキー
|
* マウスキー
|
||||||
* `EXTRAKEY_ENABLE`
|
* `EXTRAKEY_ENABLE`
|
||||||
* オーディオ制御とシステム制御
|
* オーディオ制御とシステム制御
|
||||||
* `CONSOLE_ENABLE`
|
* `CONSOLE_ENABLE`
|
||||||
* デバッグ用コンソール
|
* デバッグ用コンソール
|
||||||
* `COMMAND_ENABLE`
|
* `COMMAND_ENABLE`
|
||||||
* デバッグ及び設定用のコマンド
|
* デバッグ及び設定用のコマンド
|
||||||
* `COMBO_ENABLE`
|
* `COMBO_ENABLE`
|
||||||
* キーコンボ機能
|
* キーコンボ機能
|
||||||
* `NKRO_ENABLE`
|
* `NKRO_ENABLE`
|
||||||
* USB N-キーロールオーバー - これが動作しない場合は、ここを見てください: https://github.com/tmk/tmk_keyboard/wiki/FAQ#nkro-doesnt-work
|
* USB N-キーロールオーバー - これが動作しない場合は、ここを見てください: https://github.com/tmk/tmk_keyboard/wiki/FAQ#nkro-doesnt-work
|
||||||
* `AUDIO_ENABLE`
|
* `AUDIO_ENABLE`
|
||||||
* オーディオサブシステムを有効にします。
|
* オーディオサブシステムを有効にします。
|
||||||
* `RGBLIGHT_ENABLE`
|
* `RGBLIGHT_ENABLE`
|
||||||
* キーボードアンダーライト機能を有効にします
|
* キーボードアンダーライト機能を有効にします
|
||||||
* `LEADER_ENABLE`
|
* `LEADER_ENABLE`
|
||||||
* リーダーキーコードを有効にします
|
* リーダーキーコードを有効にします
|
||||||
* `MIDI_ENABLE`
|
* `MIDI_ENABLE`
|
||||||
* MIDI 制御
|
* MIDI 制御
|
||||||
* `UNICODE_ENABLE`
|
* `UNICODE_ENABLE`
|
||||||
* Unicode
|
* Unicode
|
||||||
* `BLUETOOTH_ENABLE`
|
* `BLUETOOTH_ENABLE`
|
||||||
* Adafruit EZ-Key HID で Bluetooth を有効にするレガシーオプション。BLUETOOTH を見てください
|
* Adafruit EZ-Key HID で Bluetooth を有効にするレガシーオプション。BLUETOOTH を見てください
|
||||||
* `BLUETOOTH`
|
* `BLUETOOTH`
|
||||||
* 現在のオプションは、AdafruitEzKey、AdafruitBLE、RN42
|
* 現在のオプションは、AdafruitEzKey、AdafruitBLE、RN42
|
||||||
* `SPLIT_KEYBOARD`
|
* `SPLIT_KEYBOARD`
|
||||||
* 分割キーボード (let's split や bakingpy のキーボードのようなデュアル MCU) のサポートを有効にし、quantum/split_common にある全ての必要なファイルをインクルードします
|
* 分割キーボード (let's split や bakingpy のキーボードのようなデュアル MCU) のサポートを有効にし、quantum/split_common にある全ての必要なファイルをインクルードします
|
||||||
* `CUSTOM_MATRIX`
|
* `CUSTOM_MATRIX`
|
||||||
* 標準マトリックス走査ルーチンを独自のものに置き換えることができます。
|
* 標準マトリックス走査ルーチンを独自のものに置き換えることができます。
|
||||||
* `DEBOUNCE_TYPE`
|
* `DEBOUNCE_TYPE`
|
||||||
* 標準キーデバウンスルーチンを代替または独自のものに置き換えることができます。
|
* 標準キーデバウンスルーチンを代替または独自のものに置き換えることができます。
|
||||||
* `WAIT_FOR_USB`
|
* `WAIT_FOR_USB`
|
||||||
* キーボードが起動する前に、USB 接続が確立されるのをキーボードに待機させます
|
* キーボードが起動する前に、USB 接続が確立されるのをキーボードに待機させます
|
||||||
* `NO_USB_STARTUP_CHECK`
|
* `NO_USB_STARTUP_CHECK`
|
||||||
* キーボードの起動後の usb サスペンドチェックを無効にします。通常、キーボードはタスクが実行される前にホストがウェイク アップするのを待ちます。分割キーボードは半分はウェイクアップコールを取得できませんが、マスタにコマンドを送信する必要があるため、役に立ちます。
|
* キーボードの起動後の usb サスペンドチェックを無効にします。通常、キーボードはタスクが実行される前にホストがウェイク アップするのを待ちます。分割キーボードは半分はウェイクアップコールを取得できませんが、マスタにコマンドを送信する必要があるため、役に立ちます。
|
||||||
|
|
||||||
## USB エンドポイントの制限
|
## USB エンドポイントの制限
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,67 @@
|
|||||||
|
# QMK Configurator: ステップ・バイ・ステップ
|
||||||
|
|
||||||
|
<!---
|
||||||
|
grep --no-filename "^[ ]*git diff" docs/ja/*.md | sh
|
||||||
|
original document: 0.9.0:docs/configurator_step_by_step.md
|
||||||
|
git diff 0.9.0 HEAD -- docs/configurator_step_by_step.md | cat
|
||||||
|
-->
|
||||||
|
|
||||||
|
このページでは、QMK Configurator でファームウェアを構築する手順を説明します。
|
||||||
|
|
||||||
|
## ステップ 1: キーボードを選ぶ
|
||||||
|
|
||||||
|
ドロップダウンボックスをクリックして、キーマップを作成するキーボードを選択します。
|
||||||
|
|
||||||
|
?> **キーボードに複数のバージョンがある場合は、正しいバージョンを選択してください。**
|
||||||
|
|
||||||
|
大事なことなのでもう一度言います。
|
||||||
|
|
||||||
|
!> **正しいバージョンを選択してください!**
|
||||||
|
|
||||||
|
キーボードが QMK を搭載していると宣伝されていてもリストにない場合は、開発者がまだ作業中か、私たちがまだマージするきっかけがなかった可能性があります。
|
||||||
|
アクティブな [プルリクエスト](https://github.com/qmk/qmk_firmware/pulls?q=is%3Aopen+is%3Apr+label%3Akeyboard) がない場合、[qmk_firmware](https://github.com/qmk/qmk_firmware/issues)で報告して、その特定のキーボードのサポートをリクエストします。
|
||||||
|
製作者自身の GitHub アカウントにある QMK 搭載キーボードもあります。
|
||||||
|
それも再確認してください。
|
||||||
|
|
||||||
|
## ステップ2: キーボードのレイアウトを選択する
|
||||||
|
|
||||||
|
作成したいと思うキーマップに最も近いレイアウトを選択します。一部のキーボードには、まだ十分なレイアウトや正しいレイアウトが定義されていません。これらは将来サポートされる予定です。
|
||||||
|
|
||||||
|
## ステップ3: キーマップの名前を決める
|
||||||
|
|
||||||
|
お好みの名前をキーマップにつけます。
|
||||||
|
|
||||||
|
?> コンパイル時に問題が発生した場合は、もしかすると QMK ファームウェアリポジトリに既に同じ名前が存在しているのかもしれません。名前を変更してみてください。
|
||||||
|
|
||||||
|
## ステップ4: キーマップを定義する
|
||||||
|
|
||||||
|
キーコードの入力は、3つの方法のいずれかで行います。
|
||||||
|
|
||||||
|
1. ドラッグ・アンド・ドロップ
|
||||||
|
2. レイアウト上の空の場所をクリックして、希望するキーコードをクリックします
|
||||||
|
3. レイアウト上の空の場所をクリックして、キーボードの物理キーを押します
|
||||||
|
|
||||||
|
?> マウスをキーの上に置くと、そのキーコードの機能の短い説明文が出ます。より詳細な説明については以下を見てください:
|
||||||
|
|
||||||
|
* [基本的なキーコードリファレンス](ja/keycodes_basic.md)
|
||||||
|
* [高度なキーコードリファレンス](ja/feature_advanced_keycodes.md)
|
||||||
|
|
||||||
|
!> 選択したレイアウトが物理的なビルドと一致しない場合は、使用していないキーは空白のままにしておきます。どのキーが使用されているかわからない場合、例えば、バックスペースキーは1つだが `LAYOUT_all` には2つのキーがある場合は、同じキーコードを両方の場所に配置してください。
|
||||||
|
|
||||||
|
## ステップ5: 後日のためにキーマップを保存する
|
||||||
|
|
||||||
|
キーマップに満足するか、または後で作業したい場合は、`Export Keymap' ボタンを押します。
|
||||||
|
これでキーマップがあなたのコンピュータに保存されます。
|
||||||
|
その後、`Import Keymap` ボタンを押すことで、この .json ファイルを後で読み込むことができます。
|
||||||
|
|
||||||
|
!> **注意:** このファイルは、kbfirmware.com またはその他のツールに使用される .json ファイルと同じ形式ではありません。これらのツールにこの .json を使用したり、QMK Configurator でこれらのツールの .json を使用しようとすると、問題が発生します。
|
||||||
|
|
||||||
|
## ステップ6: ファームウェアをコンパイルする
|
||||||
|
|
||||||
|
緑色の `Compile` ボタンを押します。
|
||||||
|
|
||||||
|
コンパイルが完了すると、緑色の `Download Firmware` ボタンを押すことができます。
|
||||||
|
|
||||||
|
## 次のステップ: キーボードに書き込む(フラッシュする)
|
||||||
|
|
||||||
|
[ファームウェアを書きこむ](ja/newbs_flashing.md) を参照してください。
|
||||||
@@ -0,0 +1,32 @@
|
|||||||
|
# Configurator トラブルシューティング
|
||||||
|
|
||||||
|
<!---
|
||||||
|
grep --no-filename "^[ ]*git diff" docs/ja/*.md | sh
|
||||||
|
original document: 0.9.0:docs/configurator_troubleshooting.md
|
||||||
|
git diff 0.9.0 HEAD -- docs/configurator_troubleshooting.md | cat
|
||||||
|
-->
|
||||||
|
|
||||||
|
## 私の .json ファイルが動きません
|
||||||
|
|
||||||
|
.json ファイルが QMK Configurator で作ったものの場合、おめでとうございます。バグに遭遇しました。 [qmk_configurator](https://github.com/qmk/qmk_configurator/issues) で報告してください。
|
||||||
|
|
||||||
|
そうでない場合は、... 他の .json ファイルを使用しないようにという、上に書いた注意書きを見逃してませんか?
|
||||||
|
|
||||||
|
#### レイアウトに余分なスペースがありますか?どうすればいいですか?
|
||||||
|
|
||||||
|
もしスペースバーが3つに分かれている場合は、全てスペースバーで埋めるのが最善の方法です。バックスペースや Shift キーについても同じことができます。
|
||||||
|
|
||||||
|
#### キーコードってなに?
|
||||||
|
|
||||||
|
以下を見てください。
|
||||||
|
|
||||||
|
* [基本的なキーコードリファレンス](ja/keycodes_basic.md)
|
||||||
|
* [高度なキーコードリファレンス](ja/feature_advanced_keycodes.md)
|
||||||
|
|
||||||
|
#### コンパイルできません
|
||||||
|
|
||||||
|
キーマップの他のレイヤーを再確認して、おかしなキーが存在しないことを確認してください。
|
||||||
|
|
||||||
|
## 問題とバグ
|
||||||
|
|
||||||
|
私たちは利用者の依頼やバグレポートを常に受け入れています。[qmk_configurator](https://github.com/qmk/qmk_configurator/issues) で報告してください。
|
||||||
Loaded 100 of 4204 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user