Skip to main content

openlogi_core/binding/action_ring/
icon.rs

1use serde::{Deserialize, Serialize};
2
3use super::super::Action;
4
5/// Presentation icon for an Actions Ring slot.
6///
7/// Variant names are persisted in TOML and declaration order is part of the
8/// agent IPC wire format, so variants are append-only.
9#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, Serialize, Deserialize)]
10pub enum ActionRingIcon {
11    /// Pointer click glyph.
12    Pointer,
13    /// Physical mouse glyph.
14    Mouse,
15    /// Copy glyph.
16    Copy,
17    /// Clipboard/paste glyph.
18    Paste,
19    /// Scissors/cut glyph.
20    Cut,
21    /// Search glyph.
22    Search,
23    /// Save glyph.
24    Save,
25    /// Keyboard glyph.
26    Keyboard,
27    /// Application grid glyph.
28    Applications,
29    /// Actions grid glyph.
30    Grid,
31    /// Layer stack glyph.
32    Layers,
33    /// Display glyph.
34    Monitor,
35    /// Lock glyph.
36    Lock,
37    /// Camera glyph.
38    Camera,
39    /// Playback glyph.
40    Play,
41    /// Audio glyph.
42    Volume,
43    /// Gauge glyph.
44    Gauge,
45    /// Refresh glyph.
46    Refresh,
47    /// Up arrow glyph.
48    ArrowUp,
49    /// Down arrow glyph.
50    ArrowDown,
51    /// Left arrow glyph.
52    ArrowLeft,
53    /// Right arrow glyph.
54    ArrowRight,
55    /// Undo glyph.
56    Undo,
57    /// Redo glyph.
58    Redo,
59    /// Selection checklist glyph.
60    SelectAll,
61    /// Circular back glyph.
62    MouseBack,
63    /// Circular forward glyph.
64    MouseForward,
65    /// New-tab glyph.
66    NewTab,
67    /// Close-tab glyph.
68    CloseTab,
69    /// Reopen-tab glyph.
70    ReopenTab,
71    /// Next-tab glyph.
72    NextTab,
73    /// Previous-tab glyph.
74    PreviousTab,
75    /// Reload glyph.
76    Reload,
77    /// Previous-desktop glyph.
78    PreviousDesktop,
79    /// Next-desktop glyph.
80    NextDesktop,
81    /// Previous-track glyph.
82    PreviousTrack,
83    /// Next-track glyph.
84    NextTrack,
85    /// Lower-volume glyph.
86    VolumeDown,
87    /// Muted-volume glyph.
88    Mute,
89    /// Horizontal scroll-left glyph.
90    ScrollLeft,
91    /// Horizontal scroll-right glyph.
92    ScrollRight,
93    /// Folder glyph.
94    Folder,
95    /// File glyph.
96    File,
97    /// Globe glyph.
98    Globe,
99    /// Terminal glyph.
100    Terminal,
101    /// Settings glyph.
102    Settings,
103    /// Star glyph.
104    Star,
105    /// Heart glyph.
106    Heart,
107    /// Calendar glyph.
108    Calendar,
109    /// Notification bell glyph.
110    Bell,
111    /// User glyph.
112    User,
113    /// Color palette glyph.
114    Palette,
115    /// Open book glyph.
116    Book,
117    /// Prohibited action glyph.
118    Ban,
119}
120
121impl ActionRingIcon {
122    /// Every icon offered by the Actions Ring editor.
123    pub const ALL: [Self; 54] = [
124        Self::Pointer,
125        Self::Mouse,
126        Self::Copy,
127        Self::Paste,
128        Self::Cut,
129        Self::Search,
130        Self::Save,
131        Self::Keyboard,
132        Self::Applications,
133        Self::Grid,
134        Self::Layers,
135        Self::Monitor,
136        Self::Lock,
137        Self::Camera,
138        Self::Play,
139        Self::Volume,
140        Self::Gauge,
141        Self::Refresh,
142        Self::ArrowUp,
143        Self::ArrowDown,
144        Self::ArrowLeft,
145        Self::ArrowRight,
146        Self::Undo,
147        Self::Redo,
148        Self::SelectAll,
149        Self::MouseBack,
150        Self::MouseForward,
151        Self::NewTab,
152        Self::CloseTab,
153        Self::ReopenTab,
154        Self::NextTab,
155        Self::PreviousTab,
156        Self::Reload,
157        Self::PreviousDesktop,
158        Self::NextDesktop,
159        Self::PreviousTrack,
160        Self::NextTrack,
161        Self::VolumeDown,
162        Self::Mute,
163        Self::ScrollLeft,
164        Self::ScrollRight,
165        Self::Folder,
166        Self::File,
167        Self::Globe,
168        Self::Terminal,
169        Self::Settings,
170        Self::Star,
171        Self::Heart,
172        Self::Calendar,
173        Self::Bell,
174        Self::User,
175        Self::Palette,
176        Self::Book,
177        Self::Ban,
178    ];
179
180    /// Existing localization key used as this icon's accessible label.
181    #[must_use]
182    pub fn label(self) -> &'static str {
183        match self {
184            Self::Pointer => "Left Click",
185            Self::Mouse => "Middle Click",
186            Self::Copy => "Copy",
187            Self::Paste => "Paste",
188            Self::Cut => "Cut",
189            Self::Search => "Find",
190            Self::Save => "Save",
191            Self::Keyboard => "Custom shortcut",
192            Self::Applications => "Open application or folder",
193            Self::Grid => "Actions Ring",
194            Self::Layers => "App Exposé",
195            Self::Monitor => "Show Desktop",
196            Self::Lock => "Lock Screen",
197            Self::Camera => "Screenshot",
198            Self::Play => "Play / Pause",
199            Self::Volume => "Volume Up",
200            Self::Gauge => "Cycle DPI Presets",
201            Self::Refresh => "Toggle SmartShift",
202            Self::ArrowUp => "Scroll Up",
203            Self::ArrowDown => "Scroll Down",
204            Self::ArrowLeft | Self::ScrollLeft => "Scroll Left",
205            Self::ArrowRight | Self::ScrollRight => "Scroll Right",
206            Self::Undo => "Undo",
207            Self::Redo => "Redo",
208            Self::SelectAll => "Select All",
209            Self::MouseBack => "Back (Button 4)",
210            Self::MouseForward => "Forward (Button 5)",
211            Self::NewTab => "New Tab",
212            Self::CloseTab => "Close Tab",
213            Self::ReopenTab => "Reopen Tab",
214            Self::NextTab => "Next Tab",
215            Self::PreviousTab => "Previous Tab",
216            Self::Reload => "Reload Page",
217            Self::PreviousDesktop => "Previous Desktop",
218            Self::NextDesktop => "Next Desktop",
219            Self::PreviousTrack => "Previous Track",
220            Self::NextTrack => "Next Track",
221            Self::VolumeDown => "Volume Down",
222            Self::Mute => "Mute",
223            Self::Folder => "Folder",
224            Self::File => "File",
225            Self::Globe => "Globe",
226            Self::Terminal => "Terminal",
227            Self::Settings => "Settings",
228            Self::Star => "Star",
229            Self::Heart => "Heart",
230            Self::Calendar => "Calendar",
231            Self::Bell => "Bell",
232            Self::User => "User",
233            Self::Palette => "Palette",
234            Self::Book => "Book",
235            Self::Ban => "Do Nothing",
236        }
237    }
238}
239
240/// Builds [`ActionRingIcon::for_action`] from
241/// [`for_each_unit_action!`](super::super::action::for_each_unit_action)'s
242/// rows, splicing in the hand-written arms for payload-carrying variants so
243/// the generated `match` still covers every [`Action`] variant exhaustively.
244macro_rules! derive_action_icon {
245    ( $( $variant:ident $label:literal $category:ident $icon:ident $( $tag:ident )? ),* $(,)? ) => {
246        impl ActionRingIcon {
247            /// Default icon for an executable action.
248            #[must_use]
249            pub fn for_action(action: &Action) -> Self {
250                match action {
251                    $( Action::$variant => Self::$icon, )*
252                    Action::SetDpiPreset(_) => Self::Gauge,
253                    Action::CustomShortcut(_) | Action::TypeText(_) | Action::Workflow(_) => {
254                        Self::Keyboard
255                    }
256                    Action::RunAppleScript(_) | Action::RunShellCommand(_) => Self::Terminal,
257                    Action::OpenApplication(_) => Self::Applications,
258                }
259            }
260        }
261    };
262}
263
264super::super::action::for_each_unit_action!(derive_action_icon);