smart_keymap/key/composite/
tap_hold.rs

1use core::fmt::Debug;
2
3#[cfg(feature = "std")]
4use serde::Deserialize;
5
6use crate::key;
7
8use super::BaseKey;
9use super::{Context, Event, KeyState, PendingKeyState, PressedKeyResult};
10
11/// Trait for types which can be nested in [TapHoldKey] variants.
12pub trait TapHoldNestable:
13    key::Key<
14        Context = Context,
15        Event = Event,
16        KeyState = KeyState,
17        PendingKeyState = PendingKeyState,
18    > + Copy
19    + PartialEq
20{
21}
22
23impl TapHoldNestable for key::layered::ModifierKey {}
24impl TapHoldNestable for key::callback::Key {}
25impl TapHoldNestable for key::caps_word::Key {}
26impl TapHoldNestable for key::custom::Key {}
27impl TapHoldNestable for key::sticky::Key {}
28impl TapHoldNestable for key::keyboard::Key {}
29impl TapHoldNestable for BaseKey {}
30
31/// An aggregate of [key::Key] types.
32#[derive(Debug, Clone, Copy, PartialEq)]
33#[cfg_attr(feature = "std", derive(Deserialize))]
34#[cfg_attr(feature = "std", serde(untagged))]
35pub enum TapHoldKey<K: TapHoldNestable> {
36    /// A tap-dance key.
37    TapDance(key::tap_dance::Key<K>),
38    /// A tap-hold key.
39    TapHold(key::tap_hold::Key<K>),
40    /// A non-tap-hold key.
41    Pass(K),
42}
43
44/// Newtype for [TapHoldNestable] keys so they can implement [key::Key].
45#[derive(Debug, Clone, Copy, PartialEq)]
46pub struct TapHold<K: TapHoldNestable>(pub K);
47
48impl<K: TapHoldNestable> key::Key for TapHoldKey<K> {
49    type Context = Context;
50    type Event = Event;
51    type PendingKeyState = PendingKeyState;
52    type KeyState = KeyState;
53
54    fn new_pressed_key(
55        &self,
56        context: &Self::Context,
57        key_path: key::KeyPath,
58    ) -> (PressedKeyResult, key::KeyEvents<Self::Event>) {
59        match self {
60            TapHoldKey::TapDance(key) => key.new_pressed_key(context, key_path),
61            TapHoldKey::TapHold(key) => key.new_pressed_key(context, key_path),
62            TapHoldKey::Pass(key) => key.new_pressed_key(context, key_path),
63        }
64    }
65
66    fn handle_event(
67        &self,
68        pending_state: &mut Self::PendingKeyState,
69        context: &Self::Context,
70        key_path: key::KeyPath,
71        event: key::Event<Self::Event>,
72    ) -> (
73        Option<key::PressedKeyResult<Self::PendingKeyState, Self::KeyState>>,
74        key::KeyEvents<Self::Event>,
75    ) {
76        match self {
77            TapHoldKey::TapDance(key) => key.handle_event(pending_state, context, key_path, event),
78            TapHoldKey::TapHold(key) => key.handle_event(pending_state, context, key_path, event),
79            TapHoldKey::Pass(key) => key.handle_event(pending_state, context, key_path, event),
80        }
81    }
82
83    fn lookup(
84        &self,
85        path: &[u16],
86    ) -> &dyn key::Key<
87        Context = Self::Context,
88        Event = Self::Event,
89        PendingKeyState = Self::PendingKeyState,
90        KeyState = Self::KeyState,
91    > {
92        match self {
93            TapHoldKey::TapDance(key) => key.lookup(path),
94            TapHoldKey::TapHold(key) => key.lookup(path),
95            TapHoldKey::Pass(key) => key.lookup(path),
96        }
97    }
98}
99
100impl<K: TapHoldNestable> key::Key for TapHold<K> {
101    type Context = Context;
102    type Event = Event;
103    type PendingKeyState = PendingKeyState;
104    type KeyState = KeyState;
105
106    fn new_pressed_key(
107        &self,
108        context: &Self::Context,
109        key_path: key::KeyPath,
110    ) -> (PressedKeyResult, key::KeyEvents<Self::Event>) {
111        let TapHold(key) = self;
112        key.new_pressed_key(context, key_path)
113    }
114
115    fn handle_event(
116        &self,
117        pending_state: &mut Self::PendingKeyState,
118        context: &Self::Context,
119        key_path: key::KeyPath,
120        event: key::Event<Self::Event>,
121    ) -> (
122        Option<key::PressedKeyResult<Self::PendingKeyState, Self::KeyState>>,
123        key::KeyEvents<Self::Event>,
124    ) {
125        let TapHold(key) = self;
126        key.handle_event(pending_state, context, key_path, event)
127    }
128
129    fn lookup(
130        &self,
131        path: &[u16],
132    ) -> &dyn key::Key<
133        Context = Self::Context,
134        Event = Self::Event,
135        PendingKeyState = Self::PendingKeyState,
136        KeyState = Self::KeyState,
137    > {
138        let TapHold(key) = self;
139        key.lookup(path)
140    }
141}
142
143impl<K: TapHoldNestable> From<key::tap_hold::Key<K>> for TapHoldKey<K> {
144    fn from(key: key::tap_hold::Key<K>) -> Self {
145        TapHoldKey::TapHold(key)
146    }
147}
148
149impl<K: Into<BaseKey>> From<K> for TapHoldKey<BaseKey> {
150    fn from(key: K) -> Self {
151        TapHoldKey::Pass(key.into())
152    }
153}
154
155impl TapHoldKey<BaseKey> {
156    /// Constructs a [TapHoldKey] from the given [key::keyboard::Key].
157    pub const fn keyboard(key: key::keyboard::Key) -> Self {
158        Self::Pass(BaseKey::Keyboard(key))
159    }
160
161    /// Constructs a [TapHoldKey] from the given [key::tap_hold::Key].
162    pub const fn tap_hold(key: key::tap_hold::Key<BaseKey>) -> Self {
163        Self::TapHold(key)
164    }
165
166    /// Constructs a [TapHoldKey] from the given [key::layered::ModifierKey].
167    pub const fn layer_modifier(key: key::layered::ModifierKey) -> Self {
168        Self::Pass(BaseKey::LayerModifier(key))
169    }
170}
171
172impl TapHold<key::keyboard::Key> {
173    /// Constructs a [TapHold] newtype from the given key.
174    pub const fn keyboard(key: key::keyboard::Key) -> Self {
175        Self(key)
176    }
177}
178
179impl TapHold<key::layered::ModifierKey> {
180    /// Constructs a [TapHold] newtypefrom the given key.
181    pub const fn layer_modifier(key: key::layered::ModifierKey) -> Self {
182        Self(key)
183    }
184}
185
186impl TapHold<BaseKey> {
187    /// Constructs a [TapHold] newtype from the given key.
188    pub const fn base_key(key: BaseKey) -> Self {
189        Self(key)
190    }
191}