Skip to main content

teksilo_core/styles/
toggle_style.rs

1// SPDX-License-Identifier: MPL-2.0
2// SPDX-FileCopyrightText: 2026 FernTech
3
4//! Tier-3 style protocol for `Toggle`. See `docs/styling-system.md`.
5
6use std::rc::Rc;
7
8use serde::{Deserialize, Serialize};
9
10use crate::build_context::BuildContext;
11use crate::signal::Signal;
12use crate::widget_id::WidgetId;
13
14/// Toggle visual archetype. Most styles compose Switch; the others
15/// give designers explicit alternates without forking the widget.
16#[derive(Copy, Clone, Debug, Eq, PartialEq, Hash, Default, Serialize, Deserialize)]
17pub enum ToggleVariant {
18    /// Capsule track + circular knob that slides on (the IntUI default
19    /// and most other 2026-era look-and-feels).
20    #[default]
21    Switch,
22    /// Pill-shaped track without a sliding knob — a colored / muted
23    /// fill toggles instead.
24    Pill,
25    /// Square track with a square knob (brutalist / 8-bit aesthetic).
26    Square,
27    /// Inset toggle — the entire control is a flat surface that
28    /// recesses on activation.
29    Inset,
30}
31
32#[derive(Clone, Debug)]
33pub struct ToggleStyleConfig {
34    /// Whether the toggle is currently on. The style usually animates
35    /// the knob position from this signal directly via
36    /// [`Signal::animate_to`](crate::signal::Signal).
37    pub is_on: Signal<bool>,
38    pub is_hovered: Signal<bool>,
39    /// Pointer-pressed (down). IntUI ignores it; design languages with
40    /// press feedback (e.g. the Material 3 switch thumb-grow) read it.
41    pub is_pressed: Signal<bool>,
42    pub is_focused: Signal<bool>,
43    /// Input-modality "focus-visible": `true` after keyboard input. The focus
44    /// ring shows only when this and `is_focused` are both true, so a pointer
45    /// click focuses without a ring while keyboard navigation reveals one.
46    pub is_focus_visible: Signal<bool>,
47    pub is_disabled: Signal<bool>,
48    pub variant: ToggleVariant,
49}
50
51pub trait ToggleStyle: 'static {
52    fn make_body(&self, cfg: &ToggleStyleConfig, ctx: &mut BuildContext) -> WidgetId;
53}
54
55pub type SharedToggleStyle = Rc<dyn ToggleStyle>;