]> git.gir.st - tmk_keyboard.git/blob - common/action.c
Rewrite layer action with layer_switch
[tmk_keyboard.git] / common / action.c
1 /*
2 Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
3
4 This program is free software: you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation, either version 2 of the License, or
7 (at your option) any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program. If not, see <http://www.gnu.org/licenses/>.
16 */
17 #include "host.h"
18 #include "timer.h"
19 #include "keymap.h"
20 #include "keycode.h"
21 #include "keyboard.h"
22 #include "mousekey.h"
23 #include "command.h"
24 #include "util.h"
25 #include "debug.h"
26 #include "action.h"
27 #include "layer_switch.h"
28
29
30 static void process_action(keyrecord_t *record);
31 static bool process_tapping(keyrecord_t *record);
32 static void waiting_buffer_scan_tap(void);
33
34 static void debug_event(keyevent_t event);
35 static void debug_record(keyrecord_t record);
36 static void debug_action(action_t action);
37 static void debug_tapping_key(void);
38 static void debug_waiting_buffer(void);
39
40
41 /*
42 * Tapping
43 */
44 /* period of tapping(ms) */
45 #ifndef TAPPING_TERM
46 #define TAPPING_TERM 200
47 #endif
48
49 /* tap count needed for toggling a feature */
50 #ifndef TAPPING_TOGGLE
51 #define TAPPING_TOGGLE 5
52 #endif
53
54 /* stores a key event of current tap. */
55 static keyrecord_t tapping_key = {};
56
57 #define IS_TAPPING() !IS_NOEVENT(tapping_key.event)
58 #define IS_TAPPING_PRESSED() (IS_TAPPING() && tapping_key.event.pressed)
59 #define IS_TAPPING_RELEASED() (IS_TAPPING() && !tapping_key.event.pressed)
60 #define IS_TAPPING_KEY(k) (IS_TAPPING() && KEYEQ(tapping_key.event.key, (k)))
61 #define WITHIN_TAPPING_TERM(e) (TIMER_DIFF_16(e.time, tapping_key.event.time) < TAPPING_TERM)
62
63
64 /*
65 * Waiting buffer
66 *
67 * stores key events waiting for settling current tap.
68 */
69 #define WAITING_BUFFER_SIZE 8
70 static keyrecord_t waiting_buffer[WAITING_BUFFER_SIZE] = {};
71
72 /* point to empty cell to enq */
73 static uint8_t waiting_buffer_head = 0;
74
75 /* point to the oldest data cell to deq */
76 static uint8_t waiting_buffer_tail = 0;
77
78 static bool waiting_buffer_enq(keyrecord_t record)
79 {
80 if (IS_NOEVENT(record.event)) {
81 return true;
82 }
83
84 if ((waiting_buffer_head + 1) % WAITING_BUFFER_SIZE == waiting_buffer_tail) {
85 debug("waiting_buffer_enq: Over flow.\n");
86 return false;
87 }
88
89 waiting_buffer[waiting_buffer_head] = record;
90 waiting_buffer_head = (waiting_buffer_head + 1) % WAITING_BUFFER_SIZE;
91
92 debug("waiting_buffer_enq: "); debug_waiting_buffer();
93 return true;
94 }
95
96 static void waiting_buffer_clear(void)
97 {
98 waiting_buffer_head = 0;
99 waiting_buffer_tail = 0;
100 }
101
102 #if TAPPING_TERM >= 500
103 static bool waiting_buffer_typed(keyevent_t event)
104 {
105 for (uint8_t i = waiting_buffer_tail; i != waiting_buffer_head; i = (i + 1) % WAITING_BUFFER_SIZE) {
106 if (KEYEQ(event.key, waiting_buffer[i].event.key) && event.pressed != waiting_buffer[i].event.pressed) {
107 return true;
108 }
109 }
110 return false;
111 }
112 #endif
113
114 bool waiting_buffer_has_anykey_pressed(void)
115 {
116 for (uint8_t i = waiting_buffer_tail; i != waiting_buffer_head; i = (i + 1) % WAITING_BUFFER_SIZE) {
117 if (waiting_buffer[i].event.pressed) return true;
118 }
119 return false;
120 }
121
122
123 /* Oneshot modifier
124 *
125 * Problem: Want to capitalize like 'The' but the result tends to be 'THe'.
126 * Solution: Oneshot modifier have its effect on only one key coming next.
127 * Tap Shift, then type 't', 'h' and 'e'. Not need to hold Shift key.
128 *
129 * Hold: works as normal modifier.
130 * Tap: one shot modifier.
131 * 2 Tap: cancel one shot modifier.
132 * 5-Tap: toggles enable/disable oneshot feature.
133 */
134 static struct {
135 uint8_t mods;
136 uint8_t time;
137 bool ready;
138 bool disabled;
139 } oneshot_state;
140
141 static void oneshot_start(uint8_t mods, uint16_t time)
142 {
143 oneshot_state.mods = mods;
144 oneshot_state.time = time;
145 oneshot_state.ready = true;
146 }
147
148 static void oneshot_cancel(void)
149 {
150 oneshot_state.mods = 0;
151 oneshot_state.time = 0;
152 oneshot_state.ready = false;
153 }
154
155 static void oneshot_toggle(void)
156 {
157 oneshot_state.disabled = !oneshot_state.disabled;
158 }
159
160
161
162 void action_exec(keyevent_t event)
163 {
164 if (!IS_NOEVENT(event)) {
165 debug("\n---- action_exec: start -----\n");
166 debug("EVENT: "); debug_event(event); debug("\n");
167 }
168
169 keyrecord_t record = { .event = event };
170
171 // pre-process on tapping
172 if (process_tapping(&record)) {
173 if (!IS_NOEVENT(record.event)) {
174 debug("processed: "); debug_record(record); debug("\n");
175 }
176 } else {
177 // enqueue
178 if (!waiting_buffer_enq(record)) {
179 // clear all in case of overflow.
180 debug("OVERFLOW: CLEAR ALL STATES\n");
181 clear_keyboard();
182 waiting_buffer_clear();
183 tapping_key = (keyrecord_t){};
184 }
185 }
186
187 // process waiting_buffer
188 if (!IS_NOEVENT(event) && waiting_buffer_head != waiting_buffer_tail) {
189 debug("---- action_exec: process waiting_buffer -----\n");
190 }
191
192 for (; waiting_buffer_tail != waiting_buffer_head; waiting_buffer_tail = (waiting_buffer_tail + 1) % WAITING_BUFFER_SIZE) {
193 if (process_tapping(&waiting_buffer[waiting_buffer_tail])) {
194 debug("processed: waiting_buffer["); debug_dec(waiting_buffer_tail); debug("] = ");
195 debug_record(waiting_buffer[waiting_buffer_tail]); debug("\n\n");
196 } else {
197 break;
198 }
199 }
200 if (!IS_NOEVENT(event)) {
201 debug("\n");
202 }
203 }
204
205 static action_t get_action(key_t key)
206 {
207 action_t action;
208 action.code = ACTION_NO;
209
210 /* layer_switch */
211 action = layer_switch_get_action(key);
212 if (action.code != ACTION_TRANSPARENT) {
213 return action;
214 }
215
216 /* default layer */
217 //debug("get_aciton: default layer: "); debug_dec(default_layer); debug("\n");
218 action = action_for_key(default_layer, key);
219 return action;
220 }
221
222 static void process_action(keyrecord_t *record)
223 {
224 keyevent_t event = record->event;
225 uint8_t tap_count = record->tap_count;
226
227 if (IS_NOEVENT(event)) { return; }
228
229 action_t action = get_action(event.key);
230 debug("ACTION: "); debug_action(action); debug(" ");
231 layer_switch_debug(); debug("["); debug_dec(default_layer); debug("]\n");
232
233 switch (action.kind.id) {
234 /* Key and Mods */
235 case ACT_LMODS:
236 case ACT_RMODS:
237 {
238 uint8_t mods = (action.kind.id == ACT_LMODS) ? action.key.mods :
239 action.key.mods<<4;
240 if (event.pressed) {
241 uint8_t tmp_mods = host_get_mods();
242 if (mods) {
243 host_add_mods(mods);
244 host_send_keyboard_report();
245 }
246 register_code(action.key.code);
247 if (mods && action.key.code) {
248 host_set_mods(tmp_mods);
249 host_send_keyboard_report();
250 }
251 } else {
252 if (mods && !action.key.code) {
253 host_del_mods(mods);
254 host_send_keyboard_report();
255 }
256 unregister_code(action.key.code);
257 }
258 }
259 break;
260 case ACT_LMODS_TAP:
261 case ACT_RMODS_TAP:
262 {
263 uint8_t mods = (action.kind.id == ACT_LMODS_TAP) ? action.key.mods :
264 action.key.mods<<4;
265 switch (action.layer.code) {
266 case 0x00:
267 // Oneshot modifier
268 if (event.pressed) {
269 if (tap_count == 0) {
270 debug("MODS_TAP: Oneshot: add_mods\n");
271 add_mods(mods);
272 }
273 else if (tap_count == 1) {
274 debug("MODS_TAP: Oneshot: start\n");
275 oneshot_start(mods, event.time);
276 }
277 else if (tap_count == TAPPING_TOGGLE) {
278 debug("MODS_TAP: Oneshot: toggle\n");
279 oneshot_toggle();
280 }
281 else {
282 debug("MODS_TAP: Oneshot: cancel&add_mods\n");
283 // double tap cancels oneshot and works as normal modifier.
284 oneshot_cancel();
285 add_mods(mods);
286 }
287 } else {
288 if (tap_count == 0) {
289 debug("MODS_TAP: Oneshot: cancel/del_mods\n");
290 // cancel oneshot on hold
291 oneshot_cancel();
292 del_mods(mods);
293 }
294 else if (tap_count == 1) {
295 debug("MODS_TAP: Oneshot: del_mods\n");
296 // retain Oneshot
297 del_mods(mods);
298 }
299 else {
300 debug("MODS_TAP: Oneshot: del_mods\n");
301 // cancel Mods
302 del_mods(mods);
303 }
304 }
305 break;
306 default:
307 if (event.pressed) {
308 if (tap_count > 0) {
309 if (waiting_buffer_has_anykey_pressed()) {
310 debug("MODS_TAP: Tap: Cancel: add_mods\n");
311 // ad hoc: set 0 to cancel tap
312 record->tap_count = 0;
313 add_mods(mods);
314 } else {
315 debug("MODS_TAP: Tap: register_code\n");
316 register_code(action.key.code);
317 }
318 } else {
319 debug("MODS_TAP: No tap: add_mods\n");
320 add_mods(mods);
321 }
322 } else {
323 if (tap_count > 0) {
324 debug("MODS_TAP: Tap: unregister_code\n");
325 unregister_code(action.key.code);
326 } else {
327 debug("MODS_TAP: No tap: add_mods\n");
328 del_mods(mods);
329 }
330 }
331 break;
332 }
333 }
334 break;
335
336 /* other HID usage */
337 case ACT_USAGE:
338 #ifdef EXTRAKEY_ENABLE
339 switch (action.usage.page) {
340 case PAGE_SYSTEM:
341 if (event.pressed) {
342 host_system_send(action.usage.code);
343 } else {
344 host_system_send(0);
345 }
346 break;
347 case PAGE_CONSUMER:
348 if (event.pressed) {
349 host_consumer_send(action.usage.code);
350 } else {
351 host_consumer_send(0);
352 }
353 break;
354 }
355 #endif
356 break;
357
358 /* Mouse key */
359 case ACT_MOUSEKEY:
360 #ifdef MOUSEKEY_ENABLE
361 if (event.pressed) {
362 mousekey_on(action.key.code);
363 mousekey_send();
364 } else {
365 mousekey_off(action.key.code);
366 mousekey_send();
367 }
368 #endif
369 break;
370
371 /* Layer key */
372 case ACT_LAYER_SET:
373 switch (action.layer.code) {
374 case LAYER_MOMENTARY: /* momentary */
375 if (event.pressed) {
376 layer_switch_move(action.layer.val);
377 }
378 else {
379 // NOTE: This is needed by legacy keymap support
380 layer_switch_move(0);
381 }
382 break;
383 case LAYER_ON_PRESS:
384 if (event.pressed) {
385 layer_switch_move(action.layer.val);
386 }
387 break;
388 case LAYER_ON_RELEASE:
389 if (!event.pressed) {
390 layer_switch_move(action.layer.val);
391 }
392 break;
393 case LAYER_ON_BOTH:
394 layer_switch_move(action.layer.val);
395 break;
396 case LAYER_TAP_TOGGLE: /* switch on hold and toggle on several taps */
397 if (event.pressed) {
398 if (tap_count < TAPPING_TOGGLE) {
399 layer_switch_move(action.layer.val);
400 }
401 } else {
402 if (tap_count >= TAPPING_TOGGLE) {
403 debug("LAYER_PRESSED: tap toggle.\n");
404 layer_switch_move(action.layer.val);
405 }
406 }
407 break;
408 case LAYER_SET_DEFAULT_ON_PRESS:
409 if (event.pressed) {
410 default_layer = action.layer.val;
411 layer_switch_move(0);
412 }
413 break;
414 case LAYER_SET_DEFAULT_ON_RELEASE:
415 if (!event.pressed) {
416 default_layer = action.layer.val;
417 layer_switch_move(0);
418 }
419 break;
420 case LAYER_SET_DEFAULT_ON_BOTH:
421 default_layer = action.layer.val;
422 layer_switch_move(0);
423 break;
424 default:
425 /* tap key */
426 if (event.pressed) {
427 if (IS_TAPPING_KEY(event.key) && tap_count > 0) {
428 debug("LAYER_SET: Tap: register_code\n");
429 register_code(action.layer.code);
430 } else {
431 debug("LAYER_SET: No tap: layer_set(on press)\n");
432 layer_switch_move(action.layer.val);
433 }
434 } else {
435 if (IS_TAPPING_KEY(event.key) && tap_count > 0) {
436 debug("LAYER_SET: Tap: unregister_code\n");
437 unregister_code(action.layer.code);
438 } else {
439 // NOTE: This is needed by legacy keymap support
440 debug("LAYER_SET: No tap: return to default layer(on release)\n");
441 layer_switch_move(0);
442 }
443 }
444 break;
445 }
446 break;
447 case ACT_LAYER_BIT:
448 switch (action.layer.code) {
449 case LAYER_MOMENTARY: /* momentary */
450 if (event.pressed) {
451 layer_switch_move(layer_switch_get_layer() | action.layer.val);
452 } else {
453 layer_switch_move(layer_switch_get_layer() & ~action.layer.val);
454 }
455 break;
456 case LAYER_ON_PRESS:
457 if (event.pressed) {
458 layer_switch_move(layer_switch_get_layer() ^ action.layer.val);
459 }
460 break;
461 case LAYER_ON_RELEASE:
462 if (!event.pressed) {
463 layer_switch_move(layer_switch_get_layer() ^ action.layer.val);
464 }
465 break;
466 case LAYER_ON_BOTH:
467 layer_switch_move(layer_switch_get_layer() ^ action.layer.val);
468 break;
469 case LAYER_TAP_TOGGLE: /* switch on hold and toggle on several taps */
470 if (event.pressed) {
471 if (tap_count < TAPPING_TOGGLE) {
472 debug("LAYER_BIT: tap toggle(press).\n");
473 layer_switch_move(layer_switch_get_layer() ^ action.layer.val);
474 }
475 } else {
476 if (tap_count <= TAPPING_TOGGLE) {
477 debug("LAYER_BIT: tap toggle(release).\n");
478 layer_switch_move(layer_switch_get_layer() ^ action.layer.val);
479 }
480 }
481 break;
482 case LAYER_SET_DEFAULT_ON_PRESS:
483 if (event.pressed) {
484 default_layer = default_layer ^ action.layer.val;
485 layer_switch_move(default_layer);
486 }
487 break;
488 case LAYER_SET_DEFAULT_ON_RELEASE:
489 if (!event.pressed) {
490 default_layer = default_layer ^ action.layer.val;
491 layer_switch_move(default_layer);
492 }
493 break;
494 case LAYER_SET_DEFAULT_ON_BOTH:
495 default_layer = default_layer ^ action.layer.val;
496 layer_switch_move(default_layer);
497 break;
498 default:
499 // tap key
500 if (event.pressed) {
501 if (IS_TAPPING_KEY(event.key) && tap_count > 0) {
502 debug("LAYER_BIT: Tap: register_code\n");
503 register_code(action.layer.code);
504 } else {
505 debug("LAYER_BIT: No tap: layer_bit(on press)\n");
506 layer_switch_move(layer_switch_get_layer() ^ action.layer.val);
507 }
508 } else {
509 if (IS_TAPPING_KEY(event.key) && tap_count > 0) {
510 debug("LAYER_BIT: Tap: unregister_code\n");
511 unregister_code(action.layer.code);
512 } else {
513 debug("LAYER_BIT: No tap: layer_bit(on release)\n");
514 layer_switch_move(layer_switch_get_layer() ^ action.layer.val);
515 }
516 }
517 break;
518 }
519 break;
520 case ACT_LAYER_SWITCH:
521 switch (action.layer.code) {
522 case LAYER_MOMENTARY: /* momentary */
523 if (event.pressed) {
524 layer_switch_on(action.layer.val);
525 } else {
526 layer_switch_off(action.layer.val);
527 }
528 break;
529 case LAYER_ON_PRESS:
530 if (event.pressed) {
531 layer_switch_invert(action.layer.val);
532 }
533 break;
534 case LAYER_ON_RELEASE:
535 if (!event.pressed) {
536 layer_switch_invert(action.layer.val);
537 }
538 break;
539 case LAYER_ON_BOTH:
540 layer_switch_invert(action.layer.val);
541 break;
542 case LAYER_TAP_TOGGLE: /* switch on hold and toggle on several taps */
543 if (event.pressed) {
544 if (tap_count < TAPPING_TOGGLE) {
545 debug("LAYER_SWITCH: tap toggle(press).\n");
546 layer_switch_invert(action.layer.val);
547 }
548 } else {
549 if (tap_count <= TAPPING_TOGGLE) {
550 debug("LAYER_SWITCH: tap toggle(release).\n");
551 layer_switch_invert(action.layer.val);
552 }
553 }
554 break;
555 default:
556 // tap key
557 if (event.pressed) {
558 if (IS_TAPPING_KEY(event.key) && tap_count > 0) {
559 debug("LAYER_SWITCH: Tap: register_code\n");
560 register_code(action.layer.code);
561 } else {
562 debug("LAYER_SWITCH: No tap: layer_switch on press\n");
563 layer_switch_invert(action.layer.val);
564 }
565 } else {
566 if (IS_TAPPING_KEY(event.key) && tap_count > 0) {
567 debug("LAYER_SWITCH: Tap: unregister_code\n");
568 unregister_code(action.layer.code);
569 } else {
570 debug("LAYER_SWITCH: No tap: layer_switch on release\n");
571 layer_switch_invert(action.layer.val);
572 }
573 }
574 break;
575 }
576 break;
577
578 /* Extentions */
579 case ACT_MACRO:
580 // TODO
581 break;
582 case ACT_COMMAND:
583 break;
584 case ACT_FUNCTION:
585 action_function(record, action.func.id, action.func.opt);
586 break;
587 default:
588 break;
589 }
590 }
591
592 /* Tapping
593 *
594 * Rule: Tap key is typed(pressed and released) within TAPPING_TERM.
595 * (without interfering by typing other key)
596 */
597 /* return true when key event is processed or consumed. */
598 static bool process_tapping(keyrecord_t *keyp)
599 {
600 keyevent_t event = keyp->event;
601
602 // if tapping
603 if (IS_TAPPING_PRESSED()) {
604 if (WITHIN_TAPPING_TERM(event)) {
605 if (tapping_key.tap_count == 0) {
606 if (IS_TAPPING_KEY(event.key) && !event.pressed) {
607 // first tap!
608 debug("Tapping: First tap(0->1).\n");
609 tapping_key.tap_count = 1;
610 debug_tapping_key();
611 process_action(&tapping_key);
612
613 // enqueue
614 keyp->tap_count = tapping_key.tap_count;
615 return false;
616 }
617 #if TAPPING_TERM >= 500
618 /* This can prevent from typing some tap keys in a row at a time. */
619 else if (!event.pressed && waiting_buffer_typed(event)) {
620 // other key typed. not tap.
621 debug("Tapping: End. No tap. Interfered by typing key\n");
622 process_action(&tapping_key);
623 tapping_key = (keyrecord_t){};
624 debug_tapping_key();
625
626 // enqueue
627 return false;
628 }
629 #endif
630 else {
631 // other key events shall be enq'd till tapping state settles.
632 return false;
633 }
634 }
635 // tap_count > 0
636 else {
637 if (IS_TAPPING_KEY(event.key) && !event.pressed) {
638 debug("Tapping: Tap release("); debug_dec(tapping_key.tap_count); debug(")\n");
639 keyp->tap_count = tapping_key.tap_count;
640 process_action(keyp);
641 tapping_key = *keyp;
642 debug_tapping_key();
643 return true;
644 }
645 else if (is_tap_key(keyp->event.key) && event.pressed) {
646 if (tapping_key.tap_count > 1) {
647 debug("Tapping: Start new tap with releasing last tap(>1).\n");
648 // unregister key
649 process_action(&(keyrecord_t){
650 .tap_count = tapping_key.tap_count,
651 .event.key = tapping_key.event.key,
652 .event.time = event.time,
653 .event.pressed = false
654 });
655 } else {
656 debug("Tapping: Start while last tap(1).\n");
657 }
658 tapping_key = *keyp;
659 waiting_buffer_scan_tap();
660 debug_tapping_key();
661 return true;
662 }
663 else {
664 if (!IS_NOEVENT(keyp->event)) {
665 debug("Tapping: key event while last tap(>0).\n");
666 }
667 process_action(keyp);
668 return true;
669 }
670 }
671 }
672 // after TAPPING_TERM
673 else {
674 if (tapping_key.tap_count == 0) {
675 debug("Tapping: End. Timeout. Not tap(0): ");
676 debug_event(event); debug("\n");
677 process_action(&tapping_key);
678 tapping_key = (keyrecord_t){};
679 debug_tapping_key();
680 return false;
681 } else {
682 if (IS_TAPPING_KEY(event.key) && !event.pressed) {
683 debug("Tapping: End. last timeout tap release(>0).");
684 keyp->tap_count = tapping_key.tap_count;
685 process_action(keyp);
686 tapping_key = (keyrecord_t){};
687 return true;
688 }
689 else if (is_tap_key(keyp->event.key) && event.pressed) {
690 if (tapping_key.tap_count > 1) {
691 debug("Tapping: Start new tap with releasing last timeout tap(>1).\n");
692 // unregister key
693 process_action(&(keyrecord_t){
694 .tap_count = tapping_key.tap_count,
695 .event.key = tapping_key.event.key,
696 .event.time = event.time,
697 .event.pressed = false
698 });
699 } else {
700 debug("Tapping: Start while last timeout tap(1).\n");
701 }
702 tapping_key = *keyp;
703 waiting_buffer_scan_tap();
704 debug_tapping_key();
705 return true;
706 }
707 else {
708 if (!IS_NOEVENT(keyp->event)) {
709 debug("Tapping: key event while last timeout tap(>0).\n");
710 }
711 process_action(keyp);
712 return true;
713 }
714 }
715 }
716 } else if (IS_TAPPING_RELEASED()) {
717 if (WITHIN_TAPPING_TERM(event)) {
718 if (tapping_key.tap_count > 0 && IS_TAPPING_KEY(event.key) && event.pressed) {
719 // sequential tap.
720 keyp->tap_count = tapping_key.tap_count + 1;
721 debug("Tapping: Tap press("); debug_dec(keyp->tap_count); debug(")\n");
722 process_action(keyp);
723 tapping_key = *keyp;
724 debug_tapping_key();
725 return true;
726 } else if (event.pressed && is_tap_key(event.key)) {
727 // Sequential tap can be interfered with other tap key.
728 debug("Tapping: Start with interfering other tap.\n");
729 tapping_key = *keyp;
730 waiting_buffer_scan_tap();
731 debug_tapping_key();
732 return true;
733 } else {
734 if (!IS_NOEVENT(keyp->event)) debug("Tapping: other key just after tap.\n");
735 process_action(keyp);
736 return true;
737 }
738 } else {
739 // timeout. no sequential tap.
740 debug("Tapping: End(Timeout after releasing last tap): ");
741 debug_event(event); debug("\n");
742 tapping_key = (keyrecord_t){};
743 debug_tapping_key();
744 return false;
745 }
746 }
747 // not tapping satate
748 else {
749 if (event.pressed && is_tap_key(event.key)) {
750 debug("Tapping: Start(Press tap key).\n");
751 tapping_key = *keyp;
752 waiting_buffer_scan_tap();
753 debug_tapping_key();
754 return true;
755 } else {
756 process_action(keyp);
757 return true;
758 }
759 }
760 }
761
762 /* scan buffer for tapping */
763 static void waiting_buffer_scan_tap(void)
764 {
765 // tapping already is settled
766 if (tapping_key.tap_count > 0) return;
767 // invalid state: tapping_key released && tap_count == 0
768 if (!tapping_key.event.pressed) return;
769
770 for (uint8_t i = waiting_buffer_tail; i != waiting_buffer_head; i = (i + 1) % WAITING_BUFFER_SIZE) {
771 if (IS_TAPPING_KEY(waiting_buffer[i].event.key) &&
772 !waiting_buffer[i].event.pressed &&
773 WITHIN_TAPPING_TERM(waiting_buffer[i].event)) {
774 tapping_key.tap_count = 1;
775 waiting_buffer[i].tap_count = 1;
776 process_action(&tapping_key);
777
778 debug("waiting_buffer_scan_tap: found at ["); debug_dec(i); debug("]\n");
779 debug_waiting_buffer();
780 return;
781 }
782 }
783 }
784
785
786
787 /*
788 * Utilities for actions.
789 */
790 void register_code(uint8_t code)
791 {
792 if (code == KC_NO) {
793 return;
794 }
795 else if IS_KEY(code) {
796 // TODO: should push command_proc out of this block?
797 if (command_proc(code)) return;
798
799 if (oneshot_state.mods && oneshot_state.ready && !oneshot_state.disabled) {
800 uint8_t tmp_mods = host_get_mods();
801 host_add_mods(oneshot_state.mods);
802 host_add_key(code);
803 host_send_keyboard_report();
804
805 host_set_mods(tmp_mods);
806 oneshot_state.ready = false;
807 } else {
808 host_add_key(code);
809 host_send_keyboard_report();
810 }
811 }
812 else if IS_MOD(code) {
813 host_add_mods(MOD_BIT(code));
814 host_send_keyboard_report();
815 }
816 }
817
818 void unregister_code(uint8_t code)
819 {
820 if IS_KEY(code) {
821 host_del_key(code);
822 host_send_keyboard_report();
823 }
824 else if IS_MOD(code) {
825 host_del_mods(MOD_BIT(code));
826 host_send_keyboard_report();
827 }
828 }
829
830 void add_mods(uint8_t mods)
831 {
832 if (mods) {
833 host_add_mods(mods);
834 host_send_keyboard_report();
835 }
836 }
837
838 void del_mods(uint8_t mods)
839 {
840 if (mods) {
841 host_del_mods(mods);
842 host_send_keyboard_report();
843 }
844 }
845
846 void set_mods(uint8_t mods)
847 {
848 host_set_mods(mods);
849 host_send_keyboard_report();
850 }
851
852 void clear_keyboard(void)
853 {
854 host_clear_mods();
855 clear_keyboard_but_mods();
856 }
857
858 void clear_keyboard_but_mods(void)
859 {
860 host_clear_keys();
861 host_send_keyboard_report();
862 #ifdef MOUSEKEY_ENABLE
863 mousekey_clear();
864 mousekey_send();
865 #endif
866 #ifdef EXTRAKEY_ENABLE
867 host_system_send(0);
868 host_consumer_send(0);
869 #endif
870 }
871
872 bool sending_anykey(void)
873 {
874 return (host_has_anykey() || host_mouse_in_use() ||
875 host_last_sysytem_report() || host_last_consumer_report());
876 }
877
878 bool is_tap_key(key_t key)
879 {
880 action_t action = get_action(key);
881
882 switch (action.kind.id) {
883 case ACT_LMODS_TAP:
884 case ACT_RMODS_TAP:
885 return true;
886 case ACT_LAYER_SET:
887 case ACT_LAYER_BIT:
888 switch (action.layer.code) {
889 case LAYER_MOMENTARY:
890 case LAYER_ON_PRESS:
891 case LAYER_ON_RELEASE:
892 case LAYER_ON_BOTH:
893 case LAYER_SET_DEFAULT_ON_PRESS:
894 case LAYER_SET_DEFAULT_ON_RELEASE:
895 case LAYER_SET_DEFAULT_ON_BOTH:
896 return false;
897 case LAYER_TAP_TOGGLE:
898 default: /* tap key */
899 return true;
900 }
901 return false;
902 case ACT_FUNCTION:
903 if (action.func.opt & FUNC_TAP) { return true; }
904 return false;
905 }
906 return false;
907 }
908
909
910 /*
911 * debug print
912 */
913 static void debug_event(keyevent_t event)
914 {
915 debug_hex16((event.key.row<<8) | event.key.col);
916 if (event.pressed) debug("d("); else debug("u(");
917 debug_dec(event.time); debug(")");
918 }
919 static void debug_record(keyrecord_t record)
920 {
921 debug_event(record.event); debug(":"); debug_dec(record.tap_count);
922 }
923 static void debug_action(action_t action)
924 {
925 switch (action.kind.id) {
926 case ACT_LMODS: debug("ACT_LMODS"); break;
927 case ACT_RMODS: debug("ACT_RMODS"); break;
928 case ACT_LMODS_TAP: debug("ACT_LMODS_TAP"); break;
929 case ACT_RMODS_TAP: debug("ACT_RMODS_TAP"); break;
930 case ACT_USAGE: debug("ACT_USAGE"); break;
931 case ACT_MOUSEKEY: debug("ACT_MOUSEKEY"); break;
932 case ACT_LAYER_SET: debug("ACT_LAYER_SET"); break;
933 case ACT_LAYER_BIT: debug("ACT_LAYER_BIT"); break;
934 case ACT_LAYER_SWITCH: debug("ACT_LAYER_SWITCH"); break;
935 case ACT_MACRO: debug("ACT_MACRO"); break;
936 case ACT_COMMAND: debug("ACT_COMMAND"); break;
937 case ACT_FUNCTION: debug("ACT_FUNCTION"); break;
938 default: debug("UNKNOWN"); break;
939 }
940 debug("[");
941 debug_hex4(action.kind.param>>8);
942 debug(":");
943 debug_hex8(action.kind.param & 0xff);
944 debug("]");
945 }
946 static void debug_tapping_key(void)
947 {
948 debug("TAPPING_KEY="); debug_record(tapping_key); debug("\n");
949 }
950 static void debug_waiting_buffer(void)
951 {
952 debug("{ ");
953 for (uint8_t i = waiting_buffer_tail; i != waiting_buffer_head; i = (i + 1) % WAITING_BUFFER_SIZE) {
954 debug("["); debug_dec(i); debug("]="); debug_record(waiting_buffer[i]); debug(" ");
955 }
956 debug("}\n");
957 }
Imprint / Impressum