Skip to main content

smart_keymap_core/
key.rs

1use core::fmt::Debug;
2
3use serde::{Deserialize, Serialize};
4
5use crate::input;
6
7/// Automation (macro) keys.
8pub mod automation;
9/// Keymap Callback keys
10pub mod callback;
11/// CapsWord key(s).
12pub mod caps_word;
13/// Chorded keys. (Chording functionality).
14pub mod chorded;
15/// Consumer keys.
16pub mod consumer;
17/// Custom keys.
18pub mod custom;
19/// History keys (e.g. Repeat last output).
20pub mod history;
21/// HID Keyboard keys.
22pub mod keyboard;
23/// Layered keys. (Layering functionality).
24pub mod layered;
25/// Mouse keys.
26pub mod mouse;
27/// Sticky Modifier keys.
28pub mod sticky;
29/// Tap-Dance keys.
30pub mod tap_dance;
31/// Tap-Hold keys.
32pub mod tap_hold;
33
34/// The maximum number of key events that are emitted by [crate::key::System] implementations.
35pub const MAX_KEY_EVENTS: usize = 4;
36
37/// Events emitted when a key is pressed.
38#[derive(Debug, PartialEq, Eq)]
39pub struct KeyEvents<E, const M: usize = { MAX_KEY_EVENTS }>(heapless::Vec<ScheduledEvent<E>, M>);
40
41impl<E: Copy + Debug> KeyEvents<E> {
42    /// Constructs a [KeyEvents] with no events scheduled.
43    pub fn no_events() -> Self {
44        KeyEvents(None.into_iter().collect())
45    }
46
47    /// Constructs a [KeyEvents] with an immediate [Event].
48    pub fn event(event: Event<E>) -> Self {
49        KeyEvents(Some(ScheduledEvent::immediate(event)).into_iter().collect())
50    }
51
52    /// Constructs a [KeyEvents] with an [Event] scheduled after a delay.
53    pub fn scheduled_event(sch_event: ScheduledEvent<E>) -> Self {
54        KeyEvents(Some(sch_event).into_iter().collect())
55    }
56
57    /// Adds an event with the schedule to the [KeyEvents].
58    pub fn schedule_event(&mut self, delay: u16, event: Event<E>) {
59        let _ = self.0.push(ScheduledEvent::after(delay, event));
60    }
61
62    /// Adds events from the other [KeyEvents] to the [KeyEvents].
63    pub fn extend(&mut self, other: KeyEvents<E>) {
64        other.0.into_iter().for_each(|ev| {
65            let _ = self.0.push(ev);
66        });
67    }
68
69    /// Adds an event from to the [KeyEvents].
70    pub fn add_event(&mut self, ev: ScheduledEvent<E>) {
71        let _ = self.0.push(ev);
72    }
73
74    /// Maps over the KeyEvents.
75    pub fn map_events<F>(&self, f: fn(E) -> F) -> KeyEvents<F> {
76        KeyEvents(
77            self.0
78                .as_slice()
79                .iter()
80                .map(|sch_ev| sch_ev.map_scheduled_event(f))
81                .collect(),
82        )
83    }
84
85    /// Maps the KeyEvents to a new type.
86    pub fn into_events<F>(&self) -> KeyEvents<F>
87    where
88        E: Into<F>,
89    {
90        KeyEvents(
91            self.0
92                .as_slice()
93                .iter()
94                .map(|sch_ev| sch_ev.map_scheduled_event(|ev| ev.into()))
95                .collect(),
96        )
97    }
98}
99
100impl<E: Debug, const M: usize> IntoIterator for KeyEvents<E, M> {
101    type Item = ScheduledEvent<E>;
102    type IntoIter = <heapless::Vec<ScheduledEvent<E>, M> as IntoIterator>::IntoIter;
103
104    fn into_iter(self) -> Self::IntoIter {
105        self.0.into_iter()
106    }
107}
108
109/// Newtype for invoking new_pressed_key on the key for the given ref.
110#[derive(Debug, PartialEq)]
111pub enum NewPressedKey<R> {
112    /// Invoke new_pressed_key on the key at the given ref.
113    Key(R),
114    /// For keys which do nothing when pressed.
115    NoOp,
116}
117
118impl<R> NewPressedKey<R> {
119    /// Constructs a NewPressedKey value.
120    pub fn key(key_ref: R) -> Self {
121        NewPressedKey::Key(key_ref)
122    }
123
124    /// Constructs a NoOp NewPressedKey value.
125    pub fn no_op() -> Self {
126        NewPressedKey::NoOp
127    }
128
129    /// Maps the NewPressedKey into a new type.
130    pub fn map<TR>(self, f: fn(R) -> TR) -> NewPressedKey<TR> {
131        match self {
132            NewPressedKey::Key(r) => NewPressedKey::Key(f(r)),
133            NewPressedKey::NoOp => NewPressedKey::NoOp,
134        }
135    }
136}
137
138/// Pressed Key which may be pending, or a resolved key state.
139#[derive(Debug, PartialEq)]
140pub enum PressedKeyResult<R, PKS, KS> {
141    /// Unresolved key state. (e.g. tap-hold or chorded keys when first pressed).
142    Pending(PKS),
143    /// Resolved as a new pressed key.
144    NewPressedKey(NewPressedKey<R>),
145    /// Resolved key state.
146    Resolved(KS),
147}
148
149impl<R, PKS, KS> PressedKeyResult<R, PKS, KS> {
150    /// Returns the Resolved variant, or else panics.
151    #[cfg(feature = "std")]
152    pub fn unwrap_resolved(self) -> KS {
153        match self {
154            PressedKeyResult::Resolved(r) => r,
155            _ => panic!("PressedKeyResult::unwrap_resolved: not Resolved"),
156        }
157    }
158
159    /// Maps the PressedKeyResult into a new type.
160    pub fn map<TPKS, TKS>(
161        self,
162        f: fn(PKS) -> TPKS,
163        g: fn(KS) -> TKS,
164    ) -> PressedKeyResult<R, TPKS, TKS> {
165        match self {
166            PressedKeyResult::Pending(pks) => PressedKeyResult::Pending(f(pks)),
167            PressedKeyResult::NewPressedKey(npk) => PressedKeyResult::NewPressedKey(npk),
168            PressedKeyResult::Resolved(ks) => PressedKeyResult::Resolved(g(ks)),
169        }
170    }
171
172    /// Maps the PressedKeyResult into a new type.
173    pub fn into_result<TPKS, TKS>(self) -> PressedKeyResult<R, TPKS, TKS>
174    where
175        PKS: Into<TPKS>,
176        KS: Into<TKS>,
177    {
178        self.map(|pks| pks.into(), |ks| ks.into())
179    }
180}
181
182/// Outcome of [System::new_pressed_key].
183pub type NewPressedKeyOutput<R, PKS, KS, E> = (PressedKeyResult<R, PKS, KS>, KeyEvents<E>);
184
185/// The interface for key `System` behaviour.
186///
187/// A `System` has an associated `Ref`, [Context], `Event`, and [KeyState].
188///
189/// The generic `PK` is used as the type of the `PressedKey` that the `Key`
190///  produces.
191/// (e.g. [layered::LayeredKey]'s pressed key state passes-through to
192///  the keys of its layers).
193pub trait System<R>: Debug {
194    /// Used to identify the key definition in the keymap.
195    type Ref: Copy;
196
197    /// The associated [Context] is used to provide state that
198    ///  may affect behaviour when pressing the key.
199    /// (e.g. the behaviour of [layered::LayeredKey] depends on which
200    ///  layers are active in [layered::Context]).
201    type Context: Copy;
202
203    /// The associated `Event` is to be handled by the associated [Context],
204    ///  pending key states, and key states.
205    type Event: Copy + Debug + PartialEq;
206
207    /// Associated pending key state.
208    type PendingKeyState;
209
210    /// Associated key state type.
211    type KeyState;
212
213    /// Produces a pressed key value, and may
214    ///  yield some [ScheduledEvent]s.
215    /// (e.g. [tap_hold::Key] may schedule a [tap_hold::Event::TapHoldTimeout]
216    ///  so that holding the key resolves as a hold,
217    ///  when a timeout is configured).
218    fn new_pressed_key(
219        &self,
220        keymap_index: u16,
221        context: &Self::Context,
222        key_ref: Self::Ref,
223    ) -> NewPressedKeyOutput<R, Self::PendingKeyState, Self::KeyState, Self::Event>;
224
225    /// Update the given pending key state with the given impl.
226    fn update_pending_state(
227        &self,
228        pending_state: &mut Self::PendingKeyState,
229        keymap_index: u16,
230        context: &Self::Context,
231        key_ref: Self::Ref,
232        event: Event<Self::Event>,
233    ) -> (Option<NewPressedKey<R>>, KeyEvents<Self::Event>);
234
235    /// Used to update the [KeyState]'s state, and possibly yield event(s).
236    fn update_state(
237        &self,
238        _key_state: &mut Self::KeyState,
239        _ref: &Self::Ref,
240        _context: &Self::Context,
241        _keymap_index: u16,
242        _event: Event<Self::Event>,
243    ) -> KeyEvents<Self::Event> {
244        KeyEvents::no_events()
245    }
246
247    /// Output for the pressed key state.
248    fn key_output(&self, _ref: &Self::Ref, _key_state: &Self::KeyState) -> Option<KeyOutput> {
249        None
250    }
251}
252
253/// Used to provide state that may affect behaviour when pressing the key.
254///
255/// e.g. the behaviour of [layered::LayeredKey] depends on which
256///  layers are active in [layered::Context].
257pub trait Context: Clone + Copy {
258    /// The type of `Event` the context handles.
259    type Event;
260
261    /// Used to update the [Context]'s state.
262    fn handle_event(&mut self, event: Event<Self::Event>) -> KeyEvents<Self::Event>;
263
264    /// Restore runtime state from this context's keymap config.
265    ///
266    /// Config data (timeouts, chords, …) is preserved; ephemeral state
267    /// (active layers, sticky mods, queues, …) is cleared.
268    fn reset(&mut self);
269}
270
271/// Bool flags for each of the modifier keys (left ctrl, etc.).
272#[derive(Deserialize, Serialize, Default, Clone, Copy, PartialEq, Eq)]
273pub struct KeyboardModifiers(u8);
274
275impl core::ops::Deref for KeyboardModifiers {
276    type Target = u8;
277
278    fn deref(&self) -> &Self::Target {
279        &self.0
280    }
281}
282
283impl core::fmt::Debug for KeyboardModifiers {
284    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
285        let mut ds = f.debug_struct("KeyboardModifiers");
286        if self.0 & Self::LEFT_CTRL_U8 != 0 {
287            ds.field("left_ctrl", &true);
288        }
289        if self.0 & Self::LEFT_SHIFT_U8 != 0 {
290            ds.field("left_shift", &true);
291        }
292        if self.0 & Self::LEFT_ALT_U8 != 0 {
293            ds.field("left_alt", &true);
294        }
295        if self.0 & Self::LEFT_GUI_U8 != 0 {
296            ds.field("left_gui", &true);
297        }
298        if self.0 & Self::RIGHT_CTRL_U8 != 0 {
299            ds.field("right_ctrl", &true);
300        }
301        if self.0 & Self::RIGHT_SHIFT_U8 != 0 {
302            ds.field("right_shift", &true);
303        }
304        if self.0 & Self::RIGHT_ALT_U8 != 0 {
305            ds.field("right_alt", &true);
306        }
307        if self.0 & Self::RIGHT_GUI_U8 != 0 {
308            ds.field("right_gui", &true);
309        }
310        ds.finish_non_exhaustive()
311    }
312}
313
314impl KeyboardModifiers {
315    /// Byte value for left ctrl.
316    pub const LEFT_CTRL_U8: u8 = 0x01;
317    /// Byte value for left shift.
318    pub const LEFT_SHIFT_U8: u8 = 0x02;
319    /// Byte value for left alt.
320    pub const LEFT_ALT_U8: u8 = 0x04;
321    /// Byte value for left gui.
322    pub const LEFT_GUI_U8: u8 = 0x08;
323    /// Byte value for right ctrl.
324    pub const RIGHT_CTRL_U8: u8 = 0x10;
325    /// Byte value for right shift.
326    pub const RIGHT_SHIFT_U8: u8 = 0x20;
327    /// Byte value for right alt.
328    pub const RIGHT_ALT_U8: u8 = 0x40;
329    /// Byte value for right gui.
330    pub const RIGHT_GUI_U8: u8 = 0x80;
331
332    /// Constructs with modifiers defaulting to false.
333    pub const fn new() -> Self {
334        KeyboardModifiers(0x00)
335    }
336
337    /// Constructs with modifiers with the given byte.
338    pub const fn from_byte(b: u8) -> Self {
339        KeyboardModifiers(b)
340    }
341
342    /// Constructs with the given key_code.
343    ///
344    /// Returns None if the key_code is not a modifier key code.
345    pub const fn from_key_code(key_code: u8) -> Option<Self> {
346        match key_code {
347            0xE0 => Some(Self::LEFT_CTRL),
348            0xE1 => Some(Self::LEFT_SHIFT),
349            0xE2 => Some(Self::LEFT_ALT),
350            0xE3 => Some(Self::LEFT_GUI),
351            0xE4 => Some(Self::RIGHT_CTRL),
352            0xE5 => Some(Self::RIGHT_SHIFT),
353            0xE6 => Some(Self::RIGHT_ALT),
354            0xE7 => Some(Self::RIGHT_GUI),
355            _ => None,
356        }
357    }
358
359    /// Const for no modifiers
360    pub const NONE: KeyboardModifiers = KeyboardModifiers {
361        ..KeyboardModifiers::new()
362    };
363
364    /// Const for left ctrl.
365    pub const LEFT_CTRL: KeyboardModifiers = KeyboardModifiers(Self::LEFT_CTRL_U8);
366
367    /// Const for left shift.
368    pub const LEFT_SHIFT: KeyboardModifiers = KeyboardModifiers(Self::LEFT_SHIFT_U8);
369
370    /// Const for left alt.
371    pub const LEFT_ALT: KeyboardModifiers = KeyboardModifiers(Self::LEFT_ALT_U8);
372
373    /// Const for left gui.
374    pub const LEFT_GUI: KeyboardModifiers = KeyboardModifiers(Self::LEFT_GUI_U8);
375
376    /// Const for right ctrl.
377    pub const RIGHT_CTRL: KeyboardModifiers = KeyboardModifiers(Self::RIGHT_CTRL_U8);
378
379    /// Const for right shift.
380    pub const RIGHT_SHIFT: KeyboardModifiers = KeyboardModifiers(Self::RIGHT_SHIFT_U8);
381
382    /// Const for right alt.
383    pub const RIGHT_ALT: KeyboardModifiers = KeyboardModifiers(Self::RIGHT_ALT_U8);
384
385    /// Const for right gui.
386    pub const RIGHT_GUI: KeyboardModifiers = KeyboardModifiers(Self::RIGHT_GUI_U8);
387
388    /// Predicate for whether the key code is a modifier key code.
389    pub const fn is_modifier_key_code(key_code: u8) -> bool {
390        matches!(key_code, 0xE0..=0xE7)
391    }
392
393    /// Constructs a Vec of key codes from the modifiers.
394    pub fn as_key_codes(&self) -> heapless::Vec<u8, 8> {
395        let mut key_codes = heapless::Vec::new();
396
397        if self.0 & Self::LEFT_CTRL_U8 != 0 {
398            let _ = key_codes.push(0xE0);
399        }
400        if self.0 & Self::LEFT_SHIFT_U8 != 0 {
401            let _ = key_codes.push(0xE1);
402        }
403        if self.0 & Self::LEFT_ALT_U8 != 0 {
404            let _ = key_codes.push(0xE2);
405        }
406        if self.0 & Self::LEFT_GUI_U8 != 0 {
407            let _ = key_codes.push(0xE3);
408        }
409        if self.0 & Self::RIGHT_CTRL_U8 != 0 {
410            let _ = key_codes.push(0xE4);
411        }
412        if self.0 & Self::RIGHT_SHIFT_U8 != 0 {
413            let _ = key_codes.push(0xE5);
414        }
415        if self.0 & Self::RIGHT_ALT_U8 != 0 {
416            let _ = key_codes.push(0xE6);
417        }
418        if self.0 & Self::RIGHT_GUI_U8 != 0 {
419            let _ = key_codes.push(0xE7);
420        }
421
422        key_codes
423    }
424
425    /// Constructs the byte for the modifiers of an HID keyboard report.
426    pub fn as_byte(&self) -> u8 {
427        self.as_key_codes()
428            .iter()
429            .fold(0u8, |acc, &kc| acc | (1 << (kc - 0xE0)))
430    }
431
432    /// Union of two KeyboardModifiers, taking "or" of each modifier.
433    pub const fn union(&self, other: &KeyboardModifiers) -> KeyboardModifiers {
434        KeyboardModifiers(self.0 | other.0)
435    }
436
437    /// Whether this keyboard modifiers includes all the other modifiers.
438    pub const fn has_modifiers(&self, other: &KeyboardModifiers) -> bool {
439        self.0 & other.0 != 0
440    }
441}
442
443/// Enum for the different types of key codes.
444#[derive(Deserialize, Serialize, Debug, Clone, Copy, PartialEq, Eq)]
445pub enum KeyUsage {
446    /// Key usage code.
447    Keyboard(u8),
448    /// Consumer usage code.
449    Consumer(u8),
450    /// Custom code. (Behaviour defined by firmware implementation).
451    Custom(u8),
452    /// Mouse usage.
453    Mouse(MouseOutput),
454}
455
456impl KeyUsage {
457    /// A key usage with no key code.
458    pub const NO_USAGE: KeyUsage = KeyUsage::Keyboard(0x00);
459}
460
461impl Default for KeyUsage {
462    fn default() -> Self {
463        KeyUsage::NO_USAGE
464    }
465}
466
467/// Struct for the output from [KeyState].
468#[derive(Deserialize, Serialize, Clone, Copy, PartialEq, Eq)]
469pub struct KeyOutput {
470    #[serde(default)]
471    key_code: KeyUsage,
472    #[serde(default)]
473    key_modifiers: KeyboardModifiers,
474}
475
476impl core::fmt::Debug for KeyOutput {
477    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
478        match (
479            self.key_code != KeyUsage::NO_USAGE,
480            self.key_modifiers != KeyboardModifiers::NONE,
481        ) {
482            (true, true) => f
483                .debug_struct("KeyOutput")
484                .field("key_code", &self.key_code)
485                .field("key_modifiers", &self.key_modifiers)
486                .finish(),
487            (false, true) => f
488                .debug_struct("KeyOutput")
489                .field("key_modifiers", &self.key_modifiers)
490                .finish(),
491            _ => f
492                .debug_struct("KeyOutput")
493                .field("key_code", &self.key_code)
494                .finish(),
495        }
496    }
497}
498
499impl KeyOutput {
500    /// A key output with no key code and no modifiers.
501    pub const NO_OUTPUT: KeyOutput = KeyOutput {
502        key_code: KeyUsage::Keyboard(0x00),
503        key_modifiers: KeyboardModifiers::new(),
504    };
505
506    /// Constructs a [KeyOutput] from a key usage.
507    pub const fn from_usage(key_usage: KeyUsage) -> Self {
508        match key_usage {
509            KeyUsage::Keyboard(kc) => Self::from_key_code(kc),
510            KeyUsage::Consumer(cc) => Self::from_consumer_code(cc),
511            KeyUsage::Custom(cu) => Self::from_custom_code(cu),
512            KeyUsage::Mouse(mo) => Self::from_mouse_output(mo),
513        }
514    }
515
516    /// Constructs a [KeyOutput] from a key usage.
517    pub const fn from_usage_with_modifiers(
518        key_usage: KeyUsage,
519        key_modifiers: KeyboardModifiers,
520    ) -> Self {
521        match key_usage {
522            KeyUsage::Keyboard(kc) => {
523                if let Some(usage_key_modifiers) = KeyboardModifiers::from_key_code(kc) {
524                    KeyOutput {
525                        key_code: KeyUsage::Keyboard(0x00),
526                        key_modifiers: usage_key_modifiers.union(&key_modifiers),
527                    }
528                } else {
529                    KeyOutput {
530                        key_code: KeyUsage::Keyboard(kc),
531                        key_modifiers,
532                    }
533                }
534            }
535            _ => KeyOutput {
536                key_code: key_usage,
537                key_modifiers,
538            },
539        }
540    }
541
542    /// Constructs a [KeyOutput] from a key code.
543    pub const fn from_key_code(key_code: u8) -> Self {
544        if let Some(key_modifiers) = KeyboardModifiers::from_key_code(key_code) {
545            KeyOutput {
546                key_code: KeyUsage::Keyboard(0x00),
547                key_modifiers,
548            }
549        } else {
550            KeyOutput {
551                key_code: KeyUsage::Keyboard(key_code),
552                key_modifiers: KeyboardModifiers::new(),
553            }
554        }
555    }
556
557    /// Constructs a [KeyOutput] from a key code with the given keyboard modifiers.
558    pub const fn from_key_code_with_modifiers(
559        key_code: u8,
560        key_modifiers: KeyboardModifiers,
561    ) -> Self {
562        let KeyOutput {
563            key_code,
564            key_modifiers: km,
565        } = Self::from_key_code(key_code);
566        KeyOutput {
567            key_code,
568            key_modifiers: km.union(&key_modifiers),
569        }
570    }
571
572    /// Constructs a [KeyOutput] for just the given keyboard modifiers.
573    pub const fn from_key_modifiers(key_modifiers: KeyboardModifiers) -> Self {
574        KeyOutput {
575            key_code: KeyUsage::Keyboard(0x00),
576            key_modifiers,
577        }
578    }
579
580    /// Constructs a [KeyOutput] from a consumer code.
581    pub const fn from_consumer_code(usage_code: u8) -> Self {
582        KeyOutput {
583            key_code: KeyUsage::Consumer(usage_code),
584            key_modifiers: KeyboardModifiers::new(),
585        }
586    }
587
588    /// Constructs a [KeyOutput] from a custom code.
589    pub const fn from_custom_code(custom_code: u8) -> Self {
590        KeyOutput {
591            key_code: KeyUsage::Custom(custom_code),
592            key_modifiers: KeyboardModifiers::new(),
593        }
594    }
595
596    /// Constructs a [KeyOutput] from a mouse output.
597    pub const fn from_mouse_output(mouse_output: MouseOutput) -> Self {
598        KeyOutput {
599            key_code: KeyUsage::Mouse(mouse_output),
600            key_modifiers: KeyboardModifiers::new(),
601        }
602    }
603
604    /// Returns the key code value.
605    pub const fn key_code(&self) -> KeyUsage {
606        self.key_code
607    }
608
609    /// Returns the keyboard modifiers of the key output.
610    pub const fn key_modifiers(&self) -> KeyboardModifiers {
611        self.key_modifiers
612    }
613}
614
615/// Struct for the mouse output.
616#[derive(Deserialize, Serialize, Debug, Clone, Copy, PartialEq, Eq)]
617pub struct MouseOutput {
618    /// Bitmask of pressed buttons.
619    pub pressed_buttons: u8,
620    /// X direction.
621    pub x: i8,
622    /// Y direction.
623    pub y: i8,
624    /// Vertical scroll.
625    pub vertical_scroll: i8,
626    /// Horizontal scroll.
627    pub horizontal_scroll: i8,
628}
629
630impl MouseOutput {
631    /// A mouse output with no buttons pressed and no movement.
632    pub const NO_OUTPUT: MouseOutput = MouseOutput {
633        pressed_buttons: 0,
634        x: 0,
635        y: 0,
636        vertical_scroll: 0,
637        horizontal_scroll: 0,
638    };
639
640    /// Combines two mouse output values into one.
641    pub fn combine(&self, other: &Self) -> Self {
642        Self {
643            pressed_buttons: self.pressed_buttons | other.pressed_buttons,
644            x: self.x.saturating_add(other.x),
645            y: self.y.saturating_add(other.y),
646            vertical_scroll: self.vertical_scroll.saturating_add(other.vertical_scroll),
647            horizontal_scroll: self
648                .horizontal_scroll
649                .saturating_add(other.horizontal_scroll),
650        }
651    }
652}
653
654/// Implements functionality for the pressed key.
655pub trait KeyState: Debug {
656    /// The type of `Context` the pressed key state handles.
657    type Context;
658    /// The type of `Event` the pressed key state handles.
659    type Event: Copy + Debug;
660
661    /// Used to update the [KeyState]'s state, and possibly yield event(s).
662    fn handle_event(
663        &mut self,
664        _context: &Self::Context,
665        _keymap_index: u16,
666        _event: Event<Self::Event>,
667    ) -> KeyEvents<Self::Event> {
668        KeyEvents::no_events()
669    }
670
671    /// Output for the pressed key state.
672    fn key_output(&self) -> Option<KeyOutput> {
673        None
674    }
675}
676
677/// A NoOp key state, for keys which do nothing when pressed.
678#[derive(Debug, Clone, Copy, PartialEq, Eq)]
679pub struct NoOpKeyState;
680
681/// Errors for [TryFrom] implementations.
682#[allow(unused)]
683pub enum EventError {
684    /// Error when mapping isn't possible.
685    ///
686    /// e.g. trying to map variants of key system `Event` to [tap_hold::Event].
687    UnmappableEvent,
688}
689
690/// Convenience alias for a [Result] with an [EventError].
691type EventResult<T> = Result<T, EventError>;
692
693/// Events which are either input, or for a particular [System::Event].
694///
695/// It's useful for key implementations to use [Event] with [System::Event],
696///  and map [System::Event] to and partially from a key system `Event`.
697#[derive(Debug, Clone, Copy, PartialEq, Eq)]
698pub enum Event<T> {
699    /// Keymap input events, such as physical key presses.
700    Input(input::Event),
701    /// Key implementation specific events.
702    Key {
703        /// The keymap index the event was generated from.
704        keymap_index: u16,
705        /// A [System::Event] event.
706        key_event: T,
707    },
708    /// Invoke a keymap callback
709    Keymap(crate::keymap::KeymapEvent),
710}
711
712impl<T: Copy> Event<T> {
713    /// Constructs an [Event] from an [System::Event].
714    pub fn key_event(keymap_index: u16, key_event: T) -> Self {
715        Event::Key {
716            keymap_index,
717            key_event,
718        }
719    }
720
721    /// Maps the Event into a new type.
722    pub fn map_key_event<U>(self, f: fn(T) -> U) -> Event<U> {
723        match self {
724            Event::Input(event) => Event::Input(event),
725            Event::Key {
726                key_event,
727                keymap_index,
728            } => Event::Key {
729                key_event: f(key_event),
730                keymap_index,
731            },
732            Event::Keymap(cb) => Event::Keymap(cb),
733        }
734    }
735
736    /// Maps the Event into a new type.
737    pub fn into_key_event<U>(self) -> Event<U>
738    where
739        T: Into<U>,
740    {
741        self.map_key_event(|ke| ke.into())
742    }
743
744    /// Maps the Event into a new type.
745    pub fn try_into_key_event<U, E>(self) -> EventResult<Event<U>>
746    where
747        T: TryInto<U, Error = E>,
748    {
749        match self {
750            Event::Input(event) => Ok(Event::Input(event)),
751            Event::Key {
752                key_event,
753                keymap_index,
754            } => key_event
755                .try_into()
756                .map(|key_event| Event::Key {
757                    key_event,
758                    keymap_index,
759                })
760                .map_err(|_| EventError::UnmappableEvent),
761            Event::Keymap(cb) => Ok(Event::Keymap(cb)),
762        }
763    }
764
765    /// Whether this event targets the given `keymap_index`.
766    ///
767    /// Input press/release and key-specific events carry a `keymap_index`;
768    /// keymap callbacks and other variants do not.
769    pub(crate) fn targets_keymap_index(&self, keymap_index: u16) -> bool {
770        match self {
771            Event::Input(input::Event::Press {
772                keymap_index: queued_kmi,
773            })
774            | Event::Input(input::Event::Release {
775                keymap_index: queued_kmi,
776            }) => *queued_kmi == keymap_index,
777            Event::Key {
778                keymap_index: queued_kmi,
779                ..
780            } => *queued_kmi == keymap_index,
781            _ => false,
782        }
783    }
784}
785
786/// Returns the events that should be replayed when a pending key resolves.
787///
788/// Resolution filter:
789/// - All queued events **not** targeting `keymap_index` are included.
790/// - Only the **last** event targeting `keymap_index` is included (if any).
791///
792/// **Example:**
793///  session log `[Press(1), Press(0), Release(0)]` for resolving key 0:
794///   yields `[Press(1), Release(0)]`
795///   — other-key inputs are kept,
796///   - but only the final self-event (`Release(0)`) remains from key 0's own press/release pair.
797pub(crate) fn pending_resolution_events<Ev: Copy, const N: usize>(
798    queued_events: &heapless::Vec<Event<Ev>, N>,
799    keymap_index: u16,
800) -> heapless::Vec<Event<Ev>, N> {
801    let (self_events, other_events): (heapless::Vec<Event<Ev>, N>, heapless::Vec<Event<Ev>, N>) =
802        queued_events
803            .iter()
804            .partition(|ev| ev.targets_keymap_index(keymap_index));
805
806    let mut result = heapless::Vec::new();
807    for ev in other_events.iter().chain(self_events.last()) {
808        let _ = result.push(*ev);
809    }
810    result
811}
812
813impl<T> From<input::Event> for Event<T> {
814    fn from(event: input::Event) -> Self {
815        Event::Input(event)
816    }
817}
818
819/// Schedule for a [ScheduledEvent].
820#[allow(unused)]
821#[derive(Debug, Clone, Copy, PartialEq, PartialOrd, Eq, Ord)]
822pub enum Schedule {
823    /// Immediately.
824    Immediate,
825    /// After a given number of `tick`s.
826    After(u16),
827}
828
829/// Schedules a given `T` with [Event], for some [Schedule].
830#[derive(Debug, Clone, Copy, PartialEq, Eq)]
831pub struct ScheduledEvent<T> {
832    /// Whether to handle the event immediately, or after some delay.
833    pub schedule: Schedule,
834    /// The event.
835    pub event: Event<T>,
836}
837
838impl<T: Copy> ScheduledEvent<T> {
839    /// Constructs a [ScheduledEvent] with [Schedule::Immediate].
840    #[allow(unused)]
841    pub fn immediate(event: Event<T>) -> Self {
842        ScheduledEvent {
843            schedule: Schedule::Immediate,
844            event,
845        }
846    }
847
848    /// Constructs a [ScheduledEvent] with [Schedule::After].
849    pub fn after(delay: u16, event: Event<T>) -> Self {
850        ScheduledEvent {
851            schedule: Schedule::After(delay),
852            event,
853        }
854    }
855
856    /// Maps the Event of the ScheduledEvent into a new type.
857    pub fn map_scheduled_event<U>(self, f: fn(T) -> U) -> ScheduledEvent<U> {
858        ScheduledEvent {
859            event: self.event.map_key_event(f),
860            schedule: self.schedule,
861        }
862    }
863
864    /// Maps the ScheduledEvent into a new type.
865    pub fn into_scheduled_event<U>(self) -> ScheduledEvent<U>
866    where
867        T: Into<U>,
868    {
869        self.map_scheduled_event(|e| e.into())
870    }
871}
872
873#[cfg(test)]
874#[allow(clippy::unwrap_used, clippy::expect_used)]
875mod tests {
876    use super::*;
877
878    #[test]
879    fn pending_resolution_events_empty_returns_empty() {
880        let queued: heapless::Vec<Event<()>, 16> = heapless::Vec::new();
881        let result = pending_resolution_events(&queued, 0);
882        assert!(result.is_empty());
883    }
884
885    #[test]
886    fn pending_resolution_events_other_key_events_all_included() {
887        let mut queued: heapless::Vec<Event<()>, 16> = heapless::Vec::new();
888        queued.push(input::Event::press(1).into()).unwrap();
889        queued.push(input::Event::release(2).into()).unwrap();
890        let result = pending_resolution_events(&queued, 0);
891        assert_eq!(2, result.len());
892    }
893
894    #[test]
895    fn pending_resolution_events_resolving_key_only_last_included() {
896        let mut queued: heapless::Vec<Event<()>, 16> = heapless::Vec::new();
897        queued.push(input::Event::press(0).into()).unwrap();
898        queued.push(input::Event::release(0).into()).unwrap();
899        let result = pending_resolution_events(&queued, 0);
900        assert_eq!(1, result.len());
901        assert_eq!(Event::from(input::Event::release(0)), result[0]);
902    }
903
904    #[test]
905    fn pending_resolution_events_mix_other_and_resolving_key() {
906        let mut queued: heapless::Vec<Event<()>, 16> = heapless::Vec::new();
907        queued.push(input::Event::press(1).into()).unwrap();
908        queued.push(input::Event::press(0).into()).unwrap();
909        queued.push(input::Event::release(0).into()).unwrap();
910        let result = pending_resolution_events(&queued, 0);
911        assert_eq!(2, result.len());
912        assert_eq!(Event::from(input::Event::press(1)), result[0]);
913        assert_eq!(Event::from(input::Event::release(0)), result[1]);
914    }
915}