@tenphi/tasty 0.0.0-snapshot.c8bdaeb → 0.0.0-snapshot.cae4fee

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (303) hide show
  1. package/README.md +314 -159
  2. package/dist/async-storage-B7_o6FKt.js +44 -0
  3. package/dist/async-storage-B7_o6FKt.js.map +1 -0
  4. package/dist/collector-C-keQH9m.js +243 -0
  5. package/dist/collector-C-keQH9m.js.map +1 -0
  6. package/dist/collector-osfWTeRd.d.ts +108 -0
  7. package/dist/config-BBiyxMCe.js +10559 -0
  8. package/dist/config-BBiyxMCe.js.map +1 -0
  9. package/dist/config-BoZDUHW5.d.ts +945 -0
  10. package/dist/context-CkSg-kDT.js +24 -0
  11. package/dist/context-CkSg-kDT.js.map +1 -0
  12. package/dist/core/index.d.ts +5 -33
  13. package/dist/core/index.js +6 -26
  14. package/dist/core-BO4319td.js +1598 -0
  15. package/dist/core-BO4319td.js.map +1 -0
  16. package/dist/css-writer-BWvwQzz0.js +351 -0
  17. package/dist/css-writer-BWvwQzz0.js.map +1 -0
  18. package/dist/format-global-rules-Dbc_1tc3.js +22 -0
  19. package/dist/format-global-rules-Dbc_1tc3.js.map +1 -0
  20. package/dist/format-rules-BSjeH4Z7.js +143 -0
  21. package/dist/format-rules-BSjeH4Z7.js.map +1 -0
  22. package/dist/hydrate-CcvrP4qJ.js +45 -0
  23. package/dist/hydrate-CcvrP4qJ.js.map +1 -0
  24. package/dist/index-B_k47mc_.d.ts +1655 -0
  25. package/dist/index-tcHuMPFt.d.ts +1286 -0
  26. package/dist/index.d.ts +5 -48
  27. package/dist/index.js +731 -32
  28. package/dist/index.js.map +1 -0
  29. package/dist/keyframes-BUQhdOSJ.js +588 -0
  30. package/dist/keyframes-BUQhdOSJ.js.map +1 -0
  31. package/dist/{utils/merge-styles.d.ts → merge-styles-BMWcH6MF.d.ts} +3 -3
  32. package/dist/{utils/merge-styles.js → merge-styles-Cd2vBl9b.js} +4 -6
  33. package/dist/merge-styles-Cd2vBl9b.js.map +1 -0
  34. package/dist/{utils/resolve-recipes.js → resolve-recipes-C1nrvnYh.js} +5 -8
  35. package/dist/resolve-recipes-C1nrvnYh.js.map +1 -0
  36. package/dist/ssr/astro-client.d.ts +1 -0
  37. package/dist/ssr/astro-client.js +19 -0
  38. package/dist/ssr/astro-client.js.map +1 -0
  39. package/dist/ssr/astro-middleware.d.ts +15 -0
  40. package/dist/ssr/astro-middleware.js +19 -0
  41. package/dist/ssr/astro-middleware.js.map +1 -0
  42. package/dist/ssr/astro.d.ts +97 -0
  43. package/dist/ssr/astro.js +149 -0
  44. package/dist/ssr/astro.js.map +1 -0
  45. package/dist/ssr/index.d.ts +44 -0
  46. package/dist/ssr/index.js +10 -0
  47. package/dist/ssr/index.js.map +1 -0
  48. package/dist/ssr/next.d.ts +46 -0
  49. package/dist/ssr/next.js +75 -0
  50. package/dist/ssr/next.js.map +1 -0
  51. package/dist/static/index.d.ts +91 -5
  52. package/dist/static/index.js +49 -4
  53. package/dist/static/index.js.map +1 -0
  54. package/dist/static/inject.d.ts +5 -0
  55. package/dist/static/inject.js +17 -0
  56. package/dist/static/inject.js.map +1 -0
  57. package/dist/zero/babel.d.ts +57 -84
  58. package/dist/zero/babel.js +232 -40
  59. package/dist/zero/babel.js.map +1 -1
  60. package/dist/zero/index.d.ts +67 -3
  61. package/dist/zero/index.js +2 -4
  62. package/dist/zero/next.d.ts +56 -30
  63. package/dist/zero/next.js +105 -40
  64. package/dist/zero/next.js.map +1 -1
  65. package/docs/README.md +31 -0
  66. package/docs/adoption.md +298 -0
  67. package/docs/comparison.md +419 -0
  68. package/docs/configuration.md +438 -0
  69. package/docs/debug.md +320 -0
  70. package/docs/design-system.md +436 -0
  71. package/docs/dsl.md +690 -0
  72. package/docs/getting-started.md +217 -0
  73. package/docs/injector.md +544 -0
  74. package/docs/methodology.md +642 -0
  75. package/docs/pipeline.md +699 -0
  76. package/docs/react-api.md +581 -0
  77. package/docs/ssr.md +444 -0
  78. package/docs/styles.md +598 -0
  79. package/docs/tasty-static.md +547 -0
  80. package/package.json +70 -37
  81. package/tasty.config.ts +1 -0
  82. package/dist/_virtual/_rolldown/runtime.js +0 -8
  83. package/dist/chunks/cacheKey.js +0 -70
  84. package/dist/chunks/cacheKey.js.map +0 -1
  85. package/dist/chunks/definitions.d.ts +0 -37
  86. package/dist/chunks/definitions.js +0 -260
  87. package/dist/chunks/definitions.js.map +0 -1
  88. package/dist/chunks/renderChunk.js +0 -61
  89. package/dist/chunks/renderChunk.js.map +0 -1
  90. package/dist/config.d.ts +0 -280
  91. package/dist/config.js +0 -403
  92. package/dist/config.js.map +0 -1
  93. package/dist/debug.d.ts +0 -204
  94. package/dist/debug.js +0 -733
  95. package/dist/debug.js.map +0 -1
  96. package/dist/hooks/useGlobalStyles.d.ts +0 -27
  97. package/dist/hooks/useGlobalStyles.js +0 -56
  98. package/dist/hooks/useGlobalStyles.js.map +0 -1
  99. package/dist/hooks/useKeyframes.d.ts +0 -56
  100. package/dist/hooks/useKeyframes.js +0 -54
  101. package/dist/hooks/useKeyframes.js.map +0 -1
  102. package/dist/hooks/useProperty.d.ts +0 -79
  103. package/dist/hooks/useProperty.js +0 -91
  104. package/dist/hooks/useProperty.js.map +0 -1
  105. package/dist/hooks/useRawCSS.d.ts +0 -53
  106. package/dist/hooks/useRawCSS.js +0 -28
  107. package/dist/hooks/useRawCSS.js.map +0 -1
  108. package/dist/hooks/useStyles.d.ts +0 -40
  109. package/dist/hooks/useStyles.js +0 -169
  110. package/dist/hooks/useStyles.js.map +0 -1
  111. package/dist/injector/index.d.ts +0 -157
  112. package/dist/injector/index.js +0 -154
  113. package/dist/injector/index.js.map +0 -1
  114. package/dist/injector/injector.d.ts +0 -139
  115. package/dist/injector/injector.js +0 -404
  116. package/dist/injector/injector.js.map +0 -1
  117. package/dist/injector/sheet-manager.d.ts +0 -127
  118. package/dist/injector/sheet-manager.js +0 -714
  119. package/dist/injector/sheet-manager.js.map +0 -1
  120. package/dist/injector/types.d.ts +0 -135
  121. package/dist/keyframes/index.js +0 -206
  122. package/dist/keyframes/index.js.map +0 -1
  123. package/dist/parser/classify.js +0 -319
  124. package/dist/parser/classify.js.map +0 -1
  125. package/dist/parser/const.js +0 -33
  126. package/dist/parser/const.js.map +0 -1
  127. package/dist/parser/lru.js +0 -109
  128. package/dist/parser/lru.js.map +0 -1
  129. package/dist/parser/parser.d.ts +0 -25
  130. package/dist/parser/parser.js +0 -116
  131. package/dist/parser/parser.js.map +0 -1
  132. package/dist/parser/tokenizer.js +0 -69
  133. package/dist/parser/tokenizer.js.map +0 -1
  134. package/dist/parser/types.d.ts +0 -51
  135. package/dist/parser/types.js +0 -46
  136. package/dist/parser/types.js.map +0 -1
  137. package/dist/pipeline/conditions.d.ts +0 -134
  138. package/dist/pipeline/conditions.js +0 -406
  139. package/dist/pipeline/conditions.js.map +0 -1
  140. package/dist/pipeline/exclusive.js +0 -231
  141. package/dist/pipeline/exclusive.js.map +0 -1
  142. package/dist/pipeline/index.d.ts +0 -53
  143. package/dist/pipeline/index.js +0 -660
  144. package/dist/pipeline/index.js.map +0 -1
  145. package/dist/pipeline/materialize.js +0 -844
  146. package/dist/pipeline/materialize.js.map +0 -1
  147. package/dist/pipeline/parseStateKey.d.ts +0 -15
  148. package/dist/pipeline/parseStateKey.js +0 -438
  149. package/dist/pipeline/parseStateKey.js.map +0 -1
  150. package/dist/pipeline/simplify.js +0 -516
  151. package/dist/pipeline/simplify.js.map +0 -1
  152. package/dist/pipeline/warnings.js +0 -18
  153. package/dist/pipeline/warnings.js.map +0 -1
  154. package/dist/plugins/okhsl-plugin.d.ts +0 -35
  155. package/dist/plugins/okhsl-plugin.js +0 -371
  156. package/dist/plugins/okhsl-plugin.js.map +0 -1
  157. package/dist/plugins/types.d.ts +0 -69
  158. package/dist/properties/index.js +0 -158
  159. package/dist/properties/index.js.map +0 -1
  160. package/dist/states/index.d.ts +0 -49
  161. package/dist/states/index.js +0 -416
  162. package/dist/states/index.js.map +0 -1
  163. package/dist/static/tastyStatic.d.ts +0 -46
  164. package/dist/static/tastyStatic.js +0 -31
  165. package/dist/static/tastyStatic.js.map +0 -1
  166. package/dist/static/types.d.ts +0 -49
  167. package/dist/static/types.js +0 -24
  168. package/dist/static/types.js.map +0 -1
  169. package/dist/styles/align.d.ts +0 -15
  170. package/dist/styles/align.js +0 -14
  171. package/dist/styles/align.js.map +0 -1
  172. package/dist/styles/border.d.ts +0 -25
  173. package/dist/styles/border.js +0 -114
  174. package/dist/styles/border.js.map +0 -1
  175. package/dist/styles/color.d.ts +0 -14
  176. package/dist/styles/color.js +0 -23
  177. package/dist/styles/color.js.map +0 -1
  178. package/dist/styles/createStyle.js +0 -77
  179. package/dist/styles/createStyle.js.map +0 -1
  180. package/dist/styles/dimension.js +0 -97
  181. package/dist/styles/dimension.js.map +0 -1
  182. package/dist/styles/display.d.ts +0 -37
  183. package/dist/styles/display.js +0 -67
  184. package/dist/styles/display.js.map +0 -1
  185. package/dist/styles/fade.d.ts +0 -15
  186. package/dist/styles/fade.js +0 -58
  187. package/dist/styles/fade.js.map +0 -1
  188. package/dist/styles/fill.d.ts +0 -42
  189. package/dist/styles/fill.js +0 -51
  190. package/dist/styles/fill.js.map +0 -1
  191. package/dist/styles/flow.d.ts +0 -16
  192. package/dist/styles/flow.js +0 -12
  193. package/dist/styles/flow.js.map +0 -1
  194. package/dist/styles/gap.d.ts +0 -31
  195. package/dist/styles/gap.js +0 -37
  196. package/dist/styles/gap.js.map +0 -1
  197. package/dist/styles/height.d.ts +0 -17
  198. package/dist/styles/height.js +0 -20
  199. package/dist/styles/height.js.map +0 -1
  200. package/dist/styles/index.d.ts +0 -2
  201. package/dist/styles/index.js +0 -9
  202. package/dist/styles/index.js.map +0 -1
  203. package/dist/styles/inset.d.ts +0 -52
  204. package/dist/styles/inset.js +0 -150
  205. package/dist/styles/inset.js.map +0 -1
  206. package/dist/styles/justify.d.ts +0 -15
  207. package/dist/styles/justify.js +0 -14
  208. package/dist/styles/justify.js.map +0 -1
  209. package/dist/styles/list.d.ts +0 -16
  210. package/dist/styles/list.js +0 -98
  211. package/dist/styles/list.js.map +0 -1
  212. package/dist/styles/margin.d.ts +0 -24
  213. package/dist/styles/margin.js +0 -104
  214. package/dist/styles/margin.js.map +0 -1
  215. package/dist/styles/outline.d.ts +0 -29
  216. package/dist/styles/outline.js +0 -65
  217. package/dist/styles/outline.js.map +0 -1
  218. package/dist/styles/padding.d.ts +0 -24
  219. package/dist/styles/padding.js +0 -104
  220. package/dist/styles/padding.js.map +0 -1
  221. package/dist/styles/predefined.d.ts +0 -73
  222. package/dist/styles/predefined.js +0 -241
  223. package/dist/styles/predefined.js.map +0 -1
  224. package/dist/styles/preset.d.ts +0 -47
  225. package/dist/styles/preset.js +0 -126
  226. package/dist/styles/preset.js.map +0 -1
  227. package/dist/styles/radius.d.ts +0 -14
  228. package/dist/styles/radius.js +0 -51
  229. package/dist/styles/radius.js.map +0 -1
  230. package/dist/styles/scrollbar.d.ts +0 -21
  231. package/dist/styles/scrollbar.js +0 -112
  232. package/dist/styles/scrollbar.js.map +0 -1
  233. package/dist/styles/shadow.d.ts +0 -14
  234. package/dist/styles/shadow.js +0 -24
  235. package/dist/styles/shadow.js.map +0 -1
  236. package/dist/styles/styledScrollbar.d.ts +0 -47
  237. package/dist/styles/styledScrollbar.js +0 -38
  238. package/dist/styles/styledScrollbar.js.map +0 -1
  239. package/dist/styles/transition.d.ts +0 -14
  240. package/dist/styles/transition.js +0 -158
  241. package/dist/styles/transition.js.map +0 -1
  242. package/dist/styles/types.d.ts +0 -498
  243. package/dist/styles/width.d.ts +0 -17
  244. package/dist/styles/width.js +0 -20
  245. package/dist/styles/width.js.map +0 -1
  246. package/dist/tasty.d.ts +0 -982
  247. package/dist/tasty.js +0 -206
  248. package/dist/tasty.js.map +0 -1
  249. package/dist/tokens/typography.d.ts +0 -19
  250. package/dist/tokens/typography.js +0 -237
  251. package/dist/tokens/typography.js.map +0 -1
  252. package/dist/types.d.ts +0 -184
  253. package/dist/utils/cache-wrapper.js +0 -26
  254. package/dist/utils/cache-wrapper.js.map +0 -1
  255. package/dist/utils/case-converter.js +0 -8
  256. package/dist/utils/case-converter.js.map +0 -1
  257. package/dist/utils/colors.d.ts +0 -5
  258. package/dist/utils/colors.js +0 -9
  259. package/dist/utils/colors.js.map +0 -1
  260. package/dist/utils/css-types.d.ts +0 -7
  261. package/dist/utils/dotize.d.ts +0 -26
  262. package/dist/utils/dotize.js +0 -122
  263. package/dist/utils/dotize.js.map +0 -1
  264. package/dist/utils/filter-base-props.d.ts +0 -15
  265. package/dist/utils/filter-base-props.js +0 -45
  266. package/dist/utils/filter-base-props.js.map +0 -1
  267. package/dist/utils/get-display-name.d.ts +0 -7
  268. package/dist/utils/get-display-name.js +0 -10
  269. package/dist/utils/get-display-name.js.map +0 -1
  270. package/dist/utils/hsl-to-rgb.js +0 -38
  271. package/dist/utils/hsl-to-rgb.js.map +0 -1
  272. package/dist/utils/is-dev-env.js +0 -19
  273. package/dist/utils/is-dev-env.js.map +0 -1
  274. package/dist/utils/is-valid-element-type.js +0 -15
  275. package/dist/utils/is-valid-element-type.js.map +0 -1
  276. package/dist/utils/merge-styles.js.map +0 -1
  277. package/dist/utils/mod-attrs.d.ts +0 -8
  278. package/dist/utils/mod-attrs.js +0 -21
  279. package/dist/utils/mod-attrs.js.map +0 -1
  280. package/dist/utils/okhsl-to-rgb.js +0 -296
  281. package/dist/utils/okhsl-to-rgb.js.map +0 -1
  282. package/dist/utils/process-tokens.d.ts +0 -31
  283. package/dist/utils/process-tokens.js +0 -171
  284. package/dist/utils/process-tokens.js.map +0 -1
  285. package/dist/utils/resolve-recipes.d.ts +0 -17
  286. package/dist/utils/resolve-recipes.js.map +0 -1
  287. package/dist/utils/string.js +0 -8
  288. package/dist/utils/string.js.map +0 -1
  289. package/dist/utils/styles.d.ts +0 -178
  290. package/dist/utils/styles.js +0 -590
  291. package/dist/utils/styles.js.map +0 -1
  292. package/dist/utils/typography.d.ts +0 -36
  293. package/dist/utils/typography.js +0 -53
  294. package/dist/utils/typography.js.map +0 -1
  295. package/dist/utils/warnings.d.ts +0 -16
  296. package/dist/utils/warnings.js +0 -16
  297. package/dist/utils/warnings.js.map +0 -1
  298. package/dist/zero/css-writer.d.ts +0 -45
  299. package/dist/zero/css-writer.js +0 -74
  300. package/dist/zero/css-writer.js.map +0 -1
  301. package/dist/zero/extractor.d.ts +0 -24
  302. package/dist/zero/extractor.js +0 -150
  303. package/dist/zero/extractor.js.map +0 -1
@@ -0,0 +1,438 @@
1
+ # Configuration
2
+
3
+ Configure the Tasty style system before your app renders using the `configure()` function. Configuration must be done **before any styles are generated** (before first render). For a higher-level docs map, see the [Docs Hub](README.md).
4
+
5
+ ```jsx
6
+ import { configure } from '@tenphi/tasty';
7
+
8
+ configure({
9
+ // CSP nonce for style elements
10
+ nonce: 'abc123',
11
+
12
+ // Global state aliases
13
+ states: {
14
+ '@mobile': '@media(w < 768px)',
15
+ '@tablet': '@media(768px <= w < 1024px)',
16
+ '@dark': '@root(schema=dark)',
17
+ },
18
+
19
+ // Parser configuration
20
+ parserCacheSize: 2000, // LRU cache size (default: 1000)
21
+
22
+ // Custom units (merged with built-in units)
23
+ units: {
24
+ vh: 'vh',
25
+ vw: 'vw',
26
+ custom: (n) => `${n * 10}px`, // Function-based unit
27
+ },
28
+
29
+ // Custom functions for the parser
30
+ funcs: {
31
+ double: (groups) => {
32
+ const value = parseFloat(groups[0]?.output || '0');
33
+ return `${value * 2}px`;
34
+ },
35
+ },
36
+ });
37
+ ```
38
+
39
+ These docs use `data-schema="dark"` in examples. If your app already standardizes on a different attribute such as `data-theme`, keep the same pattern and swap the attribute name consistently everywhere you define root-state aliases.
40
+
41
+ ---
42
+
43
+ ## Options
44
+
45
+ | Option | Type | Default | Description |
46
+ |--------|------|---------|-------------|
47
+ | `nonce` | `string` | - | CSP nonce for style elements |
48
+ | `states` | `Record<string, string>` | - | Global state aliases for advanced state mapping |
49
+ | `parserCacheSize` | `number` | `1000` | Parser LRU cache size |
50
+ | `units` | `Record<string, string \| Function>` | Built-in | Custom units (merged with built-in). See [built-in units](dsl.md#built-in-units) |
51
+ | `funcs` | `Record<string, Function>` | - | Custom parser functions (merged with existing) |
52
+ | `handlers` | `Record<string, StyleHandlerDefinition>` | Built-in | Custom style handlers (replace built-in) |
53
+ | `tokens` | `Record<string, value \| stateMap>` | - | Design tokens injected as `:root` CSS custom properties |
54
+ | `replaceTokens` | `Record<string, string \| number>` | - | Parse-time token substitution (inline replacement) |
55
+ | `keyframes` | `Record<string, KeyframesSteps>` | - | Global keyframes for animations |
56
+ | `properties` | `Record<string, PropertyDefinition>` | - | Global CSS @property definitions |
57
+ | `fontFace` | `Record<string, FontFaceInput>` | - | Global @font-face definitions |
58
+ | `counterStyle` | `Record<string, CounterStyleDescriptors>` | - | Global @counter-style definitions |
59
+ | `autoPropertyTypes` | `boolean` | `true` | Auto-infer and register `@property` types from values |
60
+ | `recipes` | `Record<string, RecipeStyles>` | - | Predefined style recipes (named style bundles) |
61
+ | `presets` | `Record<string, TypographyPreset>` | - | Typography presets — shorthand for `generateTypographyTokens()` |
62
+ | `globalStyles` | `Record<string, Styles>` | - | Global Tasty styles keyed by CSS selector |
63
+ | `colorSpace` | `'rgb' \| 'hsl' \| 'oklch'` | `'oklch'` | Color space for decomposed color token companion variables |
64
+ | `namePrefix` | `string` | `'t'` (runtime) / `'ts'` (zero-runtime) | Prefix prepended to every generated identifier (class, keyframe, counter-style names). See [Name prefix](#name-prefix). |
65
+
66
+ ---
67
+
68
+ ## Color Space
69
+
70
+ Controls the CSS color space used for decomposed color token companion variables. When you define `#name` color tokens, tasty generates both `--name-color` (full color) and `--name-color-{suffix}` (decomposed components for alpha composition).
71
+
72
+ ```jsx
73
+ configure({
74
+ colorSpace: 'oklch', // default
75
+ });
76
+ ```
77
+
78
+ | Color Space | Suffix | Components Format | Alpha Syntax |
79
+ |---|---|---|---|
80
+ | `rgb` | `-rgb` | `255 128 0` | `rgb(var(--name-color-rgb) / .5)` |
81
+ | `hsl` | `-hsl` | `300 100% 25%` | `hsl(var(--name-color-hsl) / .5)` |
82
+ | `oklch` | `-oklch` | `0.42 0.16 328` | `oklch(var(--name-color-oklch) / .5)` |
83
+
84
+ The `oklch` color space is the default because it provides perceptually uniform color manipulation — alpha fading and color mixing produce more natural-looking results.
85
+
86
+ ---
87
+
88
+ ## Name Prefix
89
+
90
+ Every identifier Tasty generates — class names, keyframe names, counter-style names — starts with a configurable prefix. The runtime, SSR, and RSC paths default to `'t'`; the zero-runtime build path (`tastyStatic` via the Babel plugin) defaults to `'ts'` so static-extracted classes can never collide with runtime classes when both are loaded on the same page.
91
+
92
+ ```jsx
93
+ configure({
94
+ namePrefix: 'mb',
95
+ });
96
+ ```
97
+
98
+ The prefix is prepended verbatim to the hash, so include any separator inside the prefix string itself:
99
+
100
+ | Setting | Class | Keyframe | Counter-style |
101
+ |---|---|---|---|
102
+ | `'t'` (runtime default) | `t1a2b3` | `tk1a2b3` | `tc1a2b3` |
103
+ | `'ts'` (zero-runtime default) | `ts1a2b3` | `tsk1a2b3` | `tsc1a2b3` |
104
+ | `'mb'` | `mb1a2b3` | `mbk1a2b3` | `mbc1a2b3` |
105
+ | `'myapp-'` | `myapp-1a2b3` | `myapp-k1a2b3` | `myapp-c1a2b3` |
106
+
107
+ The single-letter discriminators (`k` for keyframes, `c` for counter-styles) keep the three kinds visually distinct in devtools — they are not required for correctness because CSS keeps these in separate namespaces.
108
+
109
+ ### Rules
110
+
111
+ - Must match `^[a-zA-Z_][a-zA-Z0-9_-]{0,31}$`. Examples that pass: `'t'`, `'ts'`, `'app'`, `'myapp-'`, `'_foo'`. Examples that fail: `''`, `'1foo'`, `'my app'`.
112
+ - Validated at `configure()` time; an invalid prefix throws synchronously rather than silently producing broken hydration.
113
+ - Locked once styles have been generated, like all other config.
114
+
115
+ ### Coexistence with the zero-runtime build
116
+
117
+ The runtime and zero-runtime builds **must use different prefixes** when both are loaded on the same page. Defaults already guarantee this; if you customize one, customize the other accordingly:
118
+
119
+ ```jsx
120
+ // app config (runtime / SSR / RSC)
121
+ configure({ namePrefix: 'mb' });
122
+
123
+ // tasty-zero.config.ts (Babel plugin)
124
+ export default { namePrefix: 'mbs' };
125
+ ```
126
+
127
+ If you only use one of the two builds, you only need to set `namePrefix` on that path.
128
+
129
+ ---
130
+
131
+ ## Design Tokens
132
+
133
+ Design tokens define CSS custom properties on `:root`. They are injected automatically when the first style is rendered. Values are parsed through the Tasty DSL, so you can use units, color syntax, and other DSL features.
134
+
135
+ Tokens support state maps for responsive or theme-aware values:
136
+
137
+ ```jsx
138
+ configure({
139
+ tokens: {
140
+ '$gap': '4px',
141
+ '$radius': '6px',
142
+ '#primary': {
143
+ '': '#purple',
144
+ '@dark': '#light-purple',
145
+ },
146
+ '$font-size': {
147
+ '': '14px',
148
+ '@mobile': '12px',
149
+ },
150
+ },
151
+ });
152
+ ```
153
+
154
+ - `$name` keys become `--name` CSS custom properties
155
+ - `#name` keys become `--name-color` and `--name-color-{colorSpace}` properties (suffix depends on `colorSpace`, default `oklch`)
156
+
157
+ Tokens are automatically emitted in all rendering modes: runtime (client), SSR, and zero-runtime (Babel plugin).
158
+
159
+ ---
160
+
161
+ ## Replace Tokens (Parse-Time Substitution)
162
+
163
+ Replace tokens are **substituted inline at parse time** — they are baked into the generated CSS, not resolved via CSS custom properties at runtime. This makes them ideal for value aliases and shorthand references.
164
+
165
+ Use `$name` for value tokens and `#name` for color token aliases:
166
+
167
+ ```jsx
168
+ configure({
169
+ replaceTokens: {
170
+ $spacing: '2x',
171
+ '$card-padding': '4x',
172
+ '#accent': '#purple',
173
+ '#surface-hover': '#gray.05',
174
+ },
175
+ });
176
+ ```
177
+
178
+ When a component uses `padding: '$card-padding'`, the parser replaces it with `'4x'` before generating CSS. When a component uses `fill: '#accent'`, it is replaced with `'#purple'`, which in turn resolves to `var(--purple-color)`.
179
+
180
+ See [Replace Tokens](dsl.md#replace-tokens) in the Style DSL reference.
181
+
182
+ ---
183
+
184
+ ## Font Face
185
+
186
+ Register custom fonts globally so every component can reference them by family name. Values are descriptor objects or arrays (for multiple weights/styles). Rules are injected eagerly when styles are first generated.
187
+
188
+ ```ts
189
+ configure({
190
+ fontFace: {
191
+ 'Brand Sans': [
192
+ {
193
+ src: 'url("/fonts/brand-regular.woff2") format("woff2")',
194
+ fontWeight: 400,
195
+ fontDisplay: 'swap',
196
+ },
197
+ {
198
+ src: 'url("/fonts/brand-bold.woff2") format("woff2")',
199
+ fontWeight: 700,
200
+ fontDisplay: 'swap',
201
+ },
202
+ ],
203
+ Icons: {
204
+ src: 'url("/fonts/icons.woff2") format("woff2")',
205
+ fontDisplay: 'block',
206
+ },
207
+ },
208
+ });
209
+ ```
210
+
211
+ Now any component can use `fontFamily: '"Brand Sans", sans-serif'` and the browser will already have the `@font-face` rules in the stylesheet.
212
+
213
+ See [Font Face (`@fontFace`)](dsl.md#font-face-fontface) for inline usage inside component styles and the full list of supported descriptors.
214
+
215
+ ---
216
+
217
+ ## Counter Style
218
+
219
+ Define custom list-marker algorithms globally. Rules are injected eagerly when styles are first generated.
220
+
221
+ ```ts
222
+ configure({
223
+ counterStyle: {
224
+ thumbs: {
225
+ system: 'cyclic',
226
+ symbols: '"👍"',
227
+ suffix: '" "',
228
+ },
229
+ 'lower-roman-parens': {
230
+ system: 'extends lower-roman',
231
+ suffix: '") "',
232
+ },
233
+ },
234
+ });
235
+ ```
236
+
237
+ Components can then reference `listStyleType: 'thumbs'` directly.
238
+
239
+ See [Counter Style (`@counterStyle`)](dsl.md#counter-style-counterstyle) for inline usage inside component styles and the full list of supported descriptors.
240
+
241
+ ---
242
+
243
+ ## Recipes
244
+
245
+ Recipes are predefined, named style bundles. Define them globally via `configure()`:
246
+
247
+ ```jsx
248
+ configure({
249
+ recipes: {
250
+ card: {
251
+ padding: '4x',
252
+ fill: '#surface',
253
+ radius: '1r',
254
+ border: true,
255
+ },
256
+ elevated: {
257
+ shadow: '2x 2x 4x #shadow',
258
+ },
259
+ },
260
+ });
261
+ ```
262
+
263
+ Recipe values are flat tasty styles (no sub-element keys). They may contain base styles, tokens, local states, `@keyframes`, and `@properties`. Recipes cannot reference other recipes.
264
+
265
+ For how to apply, compose, and override recipes in components, see [Recipes](dsl.md#recipes) in the Style DSL reference.
266
+
267
+ ---
268
+
269
+ ## Typography Presets
270
+
271
+ Typography presets are a shorthand for `generateTypographyTokens()`. Instead of calling the function manually and spreading the result into `tokens`, pass the presets directly:
272
+
273
+ ```jsx
274
+ configure({
275
+ presets: {
276
+ h1: { fontSize: '32px', lineHeight: '1.2', fontWeight: '700' },
277
+ t2: { fontSize: '16px', lineHeight: '1.5', fontWeight: '400' },
278
+ tag: {
279
+ fontSize: '10px',
280
+ lineHeight: '1.4',
281
+ letterSpacing: '0.04em',
282
+ fontWeight: '600',
283
+ },
284
+ },
285
+ });
286
+ ```
287
+
288
+ Each preset generates `$name-font-size`, `$name-line-height`, `$name-letter-spacing`, `$name-font-weight`, and optional `$name-bold-font-weight`, `$name-icon-size`, `$name-text-transform`, `$name-font-family`, `$name-font-style` tokens.
289
+
290
+ Preset values support state maps for responsive or theme-aware typography:
291
+
292
+ ```jsx
293
+ configure({
294
+ presets: {
295
+ t2: {
296
+ fontSize: '16px',
297
+ lineHeight: '1.5',
298
+ fontWeight: { '': '400', '@dark': '300' },
299
+ },
300
+ },
301
+ });
302
+ ```
303
+
304
+ The generated tokens are merged **under** explicit `tokens` — if both `presets` and `tokens` define `$t2-font-weight`, the `tokens` value wins. Plugins can also provide `presets`; plugin presets are merged first, then config presets, then explicit tokens on top.
305
+
306
+ ---
307
+
308
+ ## Global Styles
309
+
310
+ Apply Tasty styles to any selector via configuration, without needing `useGlobalStyles(selector, ...)` at runtime:
311
+
312
+ ```jsx
313
+ configure({
314
+ globalStyles: {
315
+ body: {
316
+ fill: '#surface',
317
+ color: '#text',
318
+ preset: 't2',
319
+ margin: 0,
320
+ fontFamily: 'system-ui, sans-serif',
321
+ },
322
+ html: {
323
+ overflow: 'hidden',
324
+ },
325
+ },
326
+ });
327
+ ```
328
+
329
+ Each key is a CSS selector, and each value is a Tasty `Styles` object supporting the full style syntax including style properties, tokens, state maps, and selector-based sub-styling (e.g. `$: '> .app'` for elements outside React scope). Global styles are injected alongside `:root` tokens when the first style is rendered.
330
+
331
+ Global styles are automatically emitted in all rendering modes: runtime (client), SSR, and zero-runtime (Babel plugin). Plugins can also provide `globalStyles`; they are merged per selector with config global styles (config wins on conflict).
332
+
333
+ ---
334
+
335
+ ## Auto Property Types
336
+
337
+ CSS cannot transition or animate custom properties unless their type is declared via [`@property`](https://developer.mozilla.org/en-US/docs/Web/CSS/@property). Tasty handles this automatically — when a custom property is assigned a concrete value (e.g. `'$scale': 1`, `'$gap': '10px'`, `'#accent': 'purple'`), the type is inferred and a `@property` rule is registered.
338
+
339
+ This works across all declaration contexts: component styles, `@keyframes`, global config, and the zero-runtime Babel plugin. It also resolves `var()` chains — if `$a` references `var(--b)`, the type propagates once `--b` is resolved.
340
+
341
+ Supported types:
342
+
343
+ | Detection | Inferred syntax |
344
+ |-----------|-----------------|
345
+ | `1`, `0.5`, `-3` (bare numbers) | `<number>` |
346
+ | `10px`, `2rem`, `100vw` (length units) | `<length>` |
347
+ | `50%` | `<percentage>` |
348
+ | `45deg`, `0.5turn` (angle units) | `<angle>` |
349
+ | `300ms`, `1s` (time units) | `<time>` |
350
+ | `#name` tokens (by naming convention) | `<color>` |
351
+
352
+ Auto-inferred properties use `inherits: true` (the CSS default). Use explicit `@properties` when you need different settings:
353
+
354
+ ```jsx
355
+ // In component styles
356
+ styles: {
357
+ '@properties': {
358
+ '$scale': { syntax: '<number>', inherits: false, initialValue: 1 },
359
+ },
360
+ }
361
+
362
+ // Or globally
363
+ configure({
364
+ properties: {
365
+ '$scale': { syntax: '<number>', inherits: false, initialValue: 1 },
366
+ },
367
+ });
368
+ ```
369
+
370
+ To disable auto-inference entirely (only explicit `@properties` will be used):
371
+
372
+ ```jsx
373
+ configure({ autoPropertyTypes: false });
374
+ ```
375
+
376
+ ---
377
+
378
+ ## Custom Style Handlers
379
+
380
+ Override or extend the built-in style property handlers. A handler definition can take three forms:
381
+
382
+ | Form | Syntax | Description |
383
+ |------|--------|-------------|
384
+ | Function only | `handler` | Triggered by its key name; receives only that property |
385
+ | Single dep | `['styleName', handler]` | Triggered by the specified style property |
386
+ | Multi dep | `[['dep1', 'dep2', ...], handler]` | Triggered by any of the listed properties; receives all of them |
387
+
388
+ The multi-dep form is useful when output depends on several style properties together (e.g., `gap` needs to know `display` and `flow` to decide the CSS strategy).
389
+
390
+ ```jsx
391
+ import { configure, styleHandlers } from '@tenphi/tasty';
392
+
393
+ configure({
394
+ handlers: {
395
+ // Function only — overrides built-in fill handler
396
+ fill: ({ fill }) => {
397
+ if (fill?.startsWith('gradient:')) {
398
+ return { background: fill.slice(9) };
399
+ }
400
+ return styleHandlers.fill({ fill });
401
+ },
402
+
403
+ // Function only — new single-prop handler
404
+ elevation: ({ elevation }) => {
405
+ const level = parseInt(elevation) || 1;
406
+ return {
407
+ 'box-shadow': `0 ${level * 2}px ${level * 4}px rgba(0,0,0,0.1)`,
408
+ 'z-index': String(level * 100),
409
+ };
410
+ },
411
+
412
+ // Multi dep — handler reads multiple style properties
413
+ gap: [['display', 'flow', 'gap'], ({ display, flow, gap }) => {
414
+ if (!gap) return;
415
+ const isGrid = display?.includes('grid');
416
+ return { gap: isGrid ? gap : `/* custom logic for ${flow} */` };
417
+ }],
418
+ },
419
+ });
420
+ ```
421
+
422
+ ---
423
+
424
+ ## Extending Style Types (TypeScript)
425
+
426
+ Use module augmentation to extend the `StylesInterface`:
427
+
428
+ ```tsx
429
+ // tasty.d.ts
430
+ declare module '@tenphi/tasty' {
431
+ interface StylesInterface {
432
+ elevation?: string;
433
+ gradient?: string;
434
+ }
435
+ }
436
+ ```
437
+
438
+ See [Style DSL](dsl.md) for state maps, tokens, units, and extending semantics, and [React API](react-api.md) for `tasty()`, style functions, and component props.