1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
//! `frust-glyph`: the Glyph design system, packaged as a design-system plugin.
//!
//! Glyph is a terminal-native, **dark-first**, monospace-led design language —
//! "inspired by Material 3 Expressive, Liquid Glass, and Yaru research ·
//! original tokens". This crate is the whole system: the [`tokens`] module
//! (color schemes, type/shape/elevation/motion/glass scales, the
//! brightness-invariant [`GlyphInk`] extension, the assembled [`baseline`]
//! theme), the bundled monospace faces, the two Glyph [`motion`] patterns, and
//! the widget catalog.
//!
//! The catalog holds two kinds of component. Most are terminal-native ones with
//! no Material or Cupertino equivalent (badges/tags/alerts, loaders + toast, nav
//! chrome, content cards, the terminal block + tooltip, and the command-palette
//! overlay). The rest are ordinary controls whose *authored Glyph design*
//! diverges from what re-theming a baseline widget would produce — the baseline
//! set is token-themed, not re-designed, per design language. [`toggle`] is the
//! first of those: Glyph authors its own switch (a hairline-bordered pill with a
//! constant-diameter springing knob and an accent wash), and the baseline
//! deliberately ships no `Switch` at all for it to re-theme.
//!
//! # Installing it
//!
//! [`install`] is the one-line entry point, and it must run **before the first
//! frame**: a shell reads the default-theme slot and drains the font registry
//! once, at construction. The supported place is `app!`'s `setup` block, which
//! runs before any shell construction:
//!
//! ```no_run
//! use frust::{AnyView, Component, any, text};
//!
//! #[derive(Default)]
//! struct MyApp;
//!
//! impl Component for MyApp {
//! type State = ();
//! fn init(&self) -> Self::State {}
//! fn build(&self, _state: &mut Self::State) -> AnyView<Self::State> {
//! any(text("glyph"))
//! }
//! }
//!
//! frust::app!(MyApp, setup = { frust_glyph::install(); });
//! # fn main() {}
//! ```
//!
//! # Namespace
//!
//! Every catalog module is re-exported wholesale from this root, so app code
//! names one flat namespace — `frust_glyph::GlyphBadge`,
//! `frust_glyph::show_glyph_dialog`, `frust_glyph::baseline()` — alongside the
//! `frust::*` baseline widgets a Glyph screen composes with.
//!
//! # Charter
//!
//! - **Token-driven, never design-language-branching.** A Glyph widget
//! resolves `Theme::from_paint_ctx`/`from_layout_ctx` and reads the Glyph
//! token tables ([`tokens`]' color schemes, type scale, status palette,
//! [`GlyphInk`], …) with an unthemed-fallback constant per resolved value —
//! exactly like every baseline widget. It never matches on `DesignLanguage`;
//! a Glyph theme is just a `Theme` whose token tables happen to be the Glyph
//! ones.
//! - **Facade-only.** Widgets are `View`/`Widget` pairs authored against
//! `frust::authoring` (plus `kurbo`/`peniko` for geometry and color); this
//! crate names no other framework crate, and nothing reactive.
//!
//! # Fonts
//!
//! The Space Mono and IBM Plex Mono faces the Glyph type scale names are
//! compiled in and registered by [`install`] behind the crate's
//! `bundled-fonts` feature (default on); an app that sets
//! `default-features = false` on this dependency compiles in no font bytes,
//! `install()` registers none, and text falls back to the platform's system
//! faces through fontique (Roboto on Android). Both families are OFL-1.1 and
//! ship with their license text and provenance record
//! (`plugins/glyph/fonts/README.md`). [`font_data`] exposes the raw bytes for
//! a host that wants them directly.
//! Each family's italic face ships too, even though the catalog itself never
//! requests `FontStyle::Italic` — see [`tokens::fonts`]'s module doc for the
//! measurement behind keeping them (dropping them would silently fall back
//! to plain upright text for an app's own italic request, not a synthesized
//! oblique).
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
pub use *;
/// The design language itself, flattened to the root alongside the catalog:
/// the assembled [`baseline`] theme, its bundled [`font_data`], the
/// brightness-invariant [`GlyphInk`] extension, and the
/// [`native_typefaces`](tokens::native_typefaces) binding [`baseline`]
/// attaches. The per-scale constructors stay behind [`tokens`].
pub use ;
/// Make the Glyph design system this app's starting point.
///
/// Two process-global pushes, both public `frust` seams:
///
/// 1. `frust::set_default_theme(`[`baseline()`](baseline)`)` — the *base* a
/// shell seeds itself with instead of its built-in `Theme::neutral()`
/// fallback. Deliberately not `set_app_theme`: a seeded default does not pin
/// brightness, so a Glyph app still follows system dark mode.
/// 2. `frust::register_app_fonts` for every bundled Glyph face, so the Glyph
/// type scale's families actually resolve. The faces are compiled in
/// behind the crate's `bundled-fonts` feature (default on) — see the
/// crate docs' *Fonts* section for the `default-features = false`
/// opt-out.
///
/// # Timing: must run before the first frame
///
/// A shell reads the default-theme slot and drains the font registry **once,
/// at construction**, before its first rebuild. A call after that takes effect
/// only on a later `clear_app_theme`-driven reseed, which may never happen — so
/// a late call silently does nothing visible.
///
/// The supported way to get the timing right on all three platforms is
/// `frust::app!`'s setup block, which runs immediately before the root
/// component's `Component::init` and therefore before any shell construction —
/// see the crate docs for the full example. Calling it from `Component::init`
/// itself also happens to be early enough today, but that is not a contract
/// this crate keeps; the setup block is.
///
/// # Thread contract and repeat calls
///
/// Both underlying seams are plain `Mutex`-guarded process-globals callable
/// from any thread. Calling `install` twice is harmless but wasteful: the
/// second `set_default_theme` replaces an identical value, and the font bytes
/// are pushed (and later re-registered, shadowing the same family names) a
/// second time. Call it once.