@teacss/preset-standard 0.5.1 → 0.6.0
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.
- package/README.md +170 -29
- package/dist/index.d.ts +9 -25
- package/dist/index.js +16 -10
- package/package.json +5 -5
- package/dist/mappings-CGGqku6p.js +0 -1
- package/dist/merge.d.ts +0 -15
- package/dist/merge.js +0 -1
package/README.md
CHANGED
|
@@ -12,7 +12,7 @@ bun add @teacss/preset-standard
|
|
|
12
12
|
```
|
|
13
13
|
|
|
14
14
|
```css
|
|
15
|
-
@
|
|
15
|
+
@presets "standard";
|
|
16
16
|
@source "./src/**/*.{ts,tsx}";
|
|
17
17
|
@teacss;
|
|
18
18
|
```
|
|
@@ -50,11 +50,11 @@ Preflight emits low-specificity reset rules and theme variables. Set
|
|
|
50
50
|
reset while limiting variables to referenced keys (including the reset's sans
|
|
51
51
|
and monospace families).
|
|
52
52
|
|
|
53
|
-
Selecting `@
|
|
53
|
+
Selecting `@presets "standard"` also normalizes headings, links, lists, media,
|
|
54
54
|
tables, horizontal rules, code typography, and form-control typography. Headings
|
|
55
55
|
inherit size and weight; links inherit color and decoration; lists lose their
|
|
56
56
|
markers; images and videos fit their container without losing aspect ratio.
|
|
57
|
-
Use utilities or
|
|
57
|
+
Use utilities or Official's `prose` family to author their visible presentation.
|
|
58
58
|
|
|
59
59
|
Small text, sub/sup, titled abbreviations, and progress have consistent baselines.
|
|
60
60
|
Dialogs and popovers retain native auto-margin centering after the universal
|
|
@@ -64,43 +64,173 @@ appearance. Fieldsets use `min-inline-size: 0` so their boxes can shrink inside
|
|
|
64
64
|
narrow containers; oversized descendants still need responsive sizing.
|
|
65
65
|
Grouped options in `select[multiple]` and `select[size]` retain a 20px
|
|
66
66
|
inline-start indent, following text direction and allowing utility overrides.
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
67
|
+
The reset enforces native hiding with two global rules:
|
|
68
|
+
|
|
69
|
+
```css
|
|
70
|
+
:where([hidden]:not([hidden="until-found" i])) { display: none !important; }
|
|
71
|
+
:where([hidden="until-found" i]) { display: revert !important; }
|
|
72
|
+
```
|
|
73
|
+
|
|
74
|
+
Ordinary display utilities, component CSS and inline styles cannot reveal an
|
|
75
|
+
element with `hidden`; remove the attribute to show it. Explicit `!important`
|
|
76
|
+
declarations still follow the CSS cascade. `until-found` restores the tag's
|
|
77
|
+
native display, with discovery depending on the tag and browser. Prefer `div`
|
|
78
|
+
or `section` containers for discoverable content:
|
|
79
|
+
|
|
80
|
+
```html
|
|
81
|
+
<section hidden="until-found">Searchable content</section>
|
|
82
|
+
```
|
|
83
|
+
|
|
84
|
+
These rules run in both default and on-demand preflight. With preflight disabled,
|
|
85
|
+
the application supplies its own hiding rules.
|
|
70
86
|
|
|
71
87
|
Native control appearance, focus outlines, disabled state, and disclosure
|
|
72
88
|
behavior remain intact. Marker-free semantic lists should use `role="list"`
|
|
73
89
|
for Safari/VoiceOver. The reset adds no brand palette or global motion policy.
|
|
74
|
-
Element-local `reset-*` shortcuts
|
|
90
|
+
Element-local `reset-*` shortcuts belong to the optional Official preset;
|
|
75
91
|
Standard does not register those classes.
|
|
76
92
|
|
|
77
|
-
|
|
78
|
-
zero-specificity variable overrides and a dynamic `theme-<name>` class.
|
|
79
|
-
Preset-aware merging treats those classes as one opaque family.
|
|
93
|
+
### Role palettes and mode regions
|
|
80
94
|
|
|
81
|
-
|
|
95
|
+
Primary creates emphasis. Neutral builds the interface. Semantic colors communicate state.
|
|
82
96
|
|
|
83
|
-
|
|
84
|
-
|
|
97
|
+
Standard provides seven 12-step roles: primary → gray, neutral → sage,
|
|
98
|
+
focused → neutral, success → jade, warning → amber, failure → red, general → blue. Use
|
|
99
|
+
`bg-color:primary-200 text-color:primary-950` directly. Neither Standard nor
|
|
100
|
+
Official adds background/hover/foreground aliases; role steps already describe
|
|
101
|
+
those uses. Keep palette selection in central configuration.
|
|
85
102
|
|
|
86
|
-
|
|
87
|
-
|
|
103
|
+
The role order is primary, neutral, then the states: focused, success, warning,
|
|
104
|
+
failure, general. Focused follows the resolved neutral scale at each step when
|
|
105
|
+
no focused selection applies, including when `@focused` is omitted. Declaring
|
|
106
|
+
`@focused` only enables choices; it does not change this fallback. A configured
|
|
107
|
+
`data-css-focused` selection overrides it. Empty, unknown or undeclared selections
|
|
108
|
+
return to the region’s neutral palette; `theme.rolePalettes.focused: []` clears
|
|
109
|
+
independent choices. Application `@custom` overrides still take precedence in
|
|
110
|
+
the base mapping.
|
|
111
|
+
|
|
112
|
+
Declare selectable physical palettes in the CSS entry:
|
|
113
|
+
|
|
114
|
+
```css
|
|
115
|
+
@presets "standard,official";
|
|
116
|
+
@primary "gray,gold,red,blue";
|
|
117
|
+
@neutral "sage,slate";
|
|
118
|
+
@focused "gray,blue";
|
|
119
|
+
@success "jade,green";
|
|
120
|
+
@warning "amber,orange";
|
|
121
|
+
@failure "red,ruby";
|
|
122
|
+
@general "blue,cyan";
|
|
123
|
+
@teacss;
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
Lists add available selections, not defaults. Repeated declarations/imports union
|
|
127
|
+
and sort each role's names. Sources must be lowercase kebab-case physical palettes
|
|
128
|
+
with all 12 base steps and no direct or transitive role references in any mode.
|
|
129
|
+
Programmatic `theme.rolePalettes` has seven optional arrays; later arrays replace
|
|
130
|
+
earlier arrays per role, and `[]` clears that role. It is global configuration,
|
|
131
|
+
not a scale or a mode field. No DOM scanning is involved.
|
|
132
|
+
|
|
133
|
+
```html
|
|
134
|
+
<html data-css-primary="gray" data-css-neutral="sage" data-css-mode="dark">
|
|
135
|
+
<body>
|
|
136
|
+
<section data-css-primary="red" data-css-mode="light">
|
|
137
|
+
<p>Red / sage / light</p>
|
|
138
|
+
<article data-css-neutral="slate">Gray / slate / dark</article>
|
|
139
|
+
</section>
|
|
140
|
+
</body>
|
|
141
|
+
</html>
|
|
142
|
+
```
|
|
143
|
+
|
|
144
|
+
Any of the seven `data-css-<role>` attributes, `data-css-mode`, or configured mode
|
|
145
|
+
alias starts a region. Each of its eight dimensions uses the same selection order:
|
|
146
|
+
**own attribute → root HTML attribute → configured default**. Intermediate
|
|
147
|
+
regions are ignored. Plain descendants inherit until the next region. Empty,
|
|
148
|
+
unknown, or undeclared values explicitly select the configured default and block
|
|
149
|
+
root fallback. Removing the last marker rejoins the enclosing region. Runtime
|
|
150
|
+
attribute changes need no regeneration. `data-css-theme` has no TeaCSS meaning.
|
|
151
|
+
|
|
152
|
+
`@dark` / `@light` test the final styled target's region; pseudo-elements use their
|
|
153
|
+
host. No explicit mode activates neither condition. `defaultMode` names the base
|
|
154
|
+
palette; `@os-dark` / `@os-light` remain independent media queries.
|
|
155
|
+
`modeSelectors: { dark: ".night", light: ".day" }` adds aliases; explicit mode
|
|
156
|
+
attributes win, both aliases select neutral mode, and neither alias is implicit.
|
|
157
|
+
Programmatic mode names preserve case, spaces and punctuation; empty names, NUL
|
|
158
|
+
and unpaired surrogates are rejected.
|
|
159
|
+
|
|
160
|
+
Global `@custom` sets scales and colors; `@custom dark` changes colors only.
|
|
161
|
+
Whole-theme variants are unsupported. `@custom theme ...` and `theme.themes`
|
|
162
|
+
are errors. Palette selection never changes spacing, radii or shadow templates.
|
|
163
|
+
|
|
164
|
+
### Relationship markers
|
|
165
|
+
|
|
166
|
+
`data-css-group` enables anonymous ancestor conditions such as `@group-hover`;
|
|
167
|
+
`data-css-peer` enables preceding-sibling conditions such as `@peer-checked`.
|
|
168
|
+
Named values are ASCII-whitespace-separated lists: `data-css-group="card panel"`
|
|
169
|
+
also enables `@group-hover/card` and `@group-hover/panel`. Presence always
|
|
170
|
+
matches anonymous conditions; an empty value enables only anonymous ones.
|
|
171
|
+
Names are case-sensitive. Group remains descendant matching, peer uses `~`.
|
|
172
|
+
|
|
173
|
+
## Root language conditions
|
|
174
|
+
|
|
175
|
+
```html
|
|
176
|
+
<html lang="zh">
|
|
177
|
+
<body><p lang="en" class="p:4 p:10@lang-zh">...</p></body>
|
|
178
|
+
</html>
|
|
88
179
|
```
|
|
89
180
|
|
|
90
|
-
|
|
91
|
-
|
|
181
|
+
`@lang-<tag>` compares the complete root `html:root[lang]` value, ignoring ASCII
|
|
182
|
+
case without trimming. Here `@lang-zh` matches and `@lang-en` does not.
|
|
183
|
+
`zh`, `zh-CN`, and `zh-Hans` are independent: `@lang-zh` does not match a root
|
|
184
|
+
value of `zh-CN`. Local `lang`, theme, and mode regions do not override the root
|
|
185
|
+
language.
|
|
186
|
+
Root elements, descendants, targets, and pseudo-elements share this condition.
|
|
187
|
+
|
|
188
|
+
Use BCP 47 tags: `zh`, `zh-CN`, `zh-Hans`, `zh-Hans-CN`, `es-419`,
|
|
189
|
+
`de-1996`, and `en-u-ca-gregory`. Extlang, private-use (`x-project`), and
|
|
190
|
+
grandfathered (`i-klingon`) forms are also supported. Validation checks structure,
|
|
191
|
+
not registry membership; it does not canonicalize aliases or infer parent tags.
|
|
192
|
+
Tag case is unrestricted: `@lang-zh-CN` and `@lang-zh-cn` match identically.
|
|
193
|
+
Non-ASCII characters, malformed subtags, underscores, whitespace, wildcards,
|
|
194
|
+
and escapes are unmatched. The lowercase `lang-` prefix is reserved: rename custom
|
|
195
|
+
breakpoint keys using it, including invalid language forms. Existing `@max-<name>`
|
|
196
|
+
syntax is unchanged.
|
|
197
|
+
|
|
198
|
+
`@!lang-en` also matches missing/empty root language. Conditions compose with
|
|
199
|
+
states, relations, queries, modes, targets, shortcuts, and `@apply` using AND.
|
|
200
|
+
Conflicting languages never match; repetition follows ordinary suffix behavior.
|
|
201
|
+
The language guard contributes `0,1,0` specificity before existing wrappers;
|
|
202
|
+
`space-*` / `divide-*` keep their zero-specificity selectors.
|
|
203
|
+
|
|
204
|
+
Changing root `lang` updates generated CSS without runtime listeners or
|
|
205
|
+
regeneration, including with preflight disabled. Keep complete tokens in scanned
|
|
206
|
+
sources or safelists; do not escape `@` in HTML/JSX class strings. Each HTML iframe
|
|
207
|
+
uses its own root; propagation across Shadow DOM or independent XML documents
|
|
208
|
+
is unsupported. Applications own translation, `dir`, and SSR's initial language.
|
|
209
|
+
|
|
210
|
+
## Class merging
|
|
92
211
|
|
|
93
212
|
```ts
|
|
94
|
-
import {
|
|
95
|
-
import { pluginIcon } from "@teacss/preset-icons/merge";
|
|
96
|
-
import { pluginStandard } from "@teacss/preset-standard/merge";
|
|
213
|
+
import { cn } from "@teacss/classes";
|
|
97
214
|
|
|
98
|
-
|
|
215
|
+
cn("p:4 d:flex", "p:8"); // "d:flex p:8"
|
|
216
|
+
cn("p:4", "p:invalid"); // "p:invalid"
|
|
217
|
+
cn("p:2@lang-en", "p:4@lang-en"); // "p:4@lang-en"
|
|
218
|
+
cn("p:2@lang-ZH", "p:4@lang-zh"); // "p:4@lang-zh"
|
|
99
219
|
```
|
|
100
220
|
|
|
221
|
+
`cn` uses fixed Standard and Icons rules. Install and import `@teacss/classes`
|
|
222
|
+
directly for runtime class composition.
|
|
223
|
+
Merge uses prefix shape and ordered conditions, ignoring ASCII language-tag
|
|
224
|
+
case while preserving each winning token's spelling. It does not validate values
|
|
225
|
+
or condition support: malformed suffixes can merge but emit no CSS.
|
|
226
|
+
Unknown declarations merge
|
|
227
|
+
only by their own prefix; application shortcuts have no cross-prefix footprint.
|
|
228
|
+
|
|
101
229
|
Native shorthands are emitted before their component overrides. For example,
|
|
102
230
|
`cn("border:[1px_solid_red]", "border-t-width:4")` retains both classes and
|
|
103
231
|
produces a 4px top border. Reversing those arguments leaves only the shorthand.
|
|
232
|
+
The same ordering covers place/gap/columns, text families and corner shapes;
|
|
233
|
+
explicit display and overflow can override `line-clamp`'s corresponding declarations.
|
|
104
234
|
|
|
105
235
|
## Value and composition boundaries
|
|
106
236
|
|
|
@@ -108,23 +238,34 @@ produces a 4px top border. Reversing those arguments leaves only the shorthand.
|
|
|
108
238
|
`border-a-width:[1px_2px]`; physical x/y and single-edge forms accept one.
|
|
109
239
|
- `[…]` keeps structurally valid arbitrary CSS, including
|
|
110
240
|
`animation-name:[var(--name)]`. It does not guarantee browser support.
|
|
241
|
+
- Custom-variable values and `font-palette` use the shared structural checks;
|
|
242
|
+
failed bracket/variable decoding cannot fall back to unchecked raw CSS.
|
|
243
|
+
- A configured `DEFAULT` key references its unsuffixed variable: `p:DEFAULT`
|
|
244
|
+
reads `--spacing`, including through negative spacing. Applications supply
|
|
245
|
+
these scale variables when preflight is disabled.
|
|
246
|
+
- Named shadows use global templates and support local color overrides.
|
|
247
|
+
`shadow:$shadow-card` reads a complete raw variable without recoloring;
|
|
248
|
+
`box-shadow:[…]` replaces the whole composed surface.
|
|
249
|
+
- Named animations quote their decoded CSS names to avoid shorthand keyword
|
|
250
|
+
ambiguity. Numeric zero iteration counts remain zero.
|
|
111
251
|
- Bare background/mask sizes cannot be negative.
|
|
112
252
|
- Border-spacing axis variables do not inherit into nested tables.
|
|
113
253
|
- Gradient properties are registered on demand, retaining shared fallbacks
|
|
114
254
|
and neutral additive-mask layers without registering unrelated families.
|
|
115
255
|
|
|
116
|
-
##
|
|
256
|
+
## Explicit activators
|
|
117
257
|
|
|
118
|
-
|
|
258
|
+
Standard utilities all use `property:value`. The following activators accept
|
|
259
|
+
exactly `on`, with ordinary importance and suffix conditions:
|
|
119
260
|
|
|
120
261
|
```txt
|
|
121
|
-
mask-g-linear mask-g-radial mask-g-conic
|
|
122
|
-
|
|
123
|
-
space-x-reverse space-y-reverse space-a-reverse space-c-reverse
|
|
262
|
+
mask-g-linear:on mask-g-radial:on mask-g-conic:on
|
|
263
|
+
space-x-reverse:on space-y-reverse:on space-a-reverse:on space-c-reverse:on
|
|
124
264
|
```
|
|
125
265
|
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
266
|
+
Use `divide-x-width:1` / `divide-y-width:1` for 1px child dividers. The former
|
|
267
|
+
nine bare spellings emit nothing; bare names are reserved for registered
|
|
268
|
+
application or Official shortcuts. Removing an activator restores its default;
|
|
269
|
+
`off`, `true`, variable, arbitrary, and CSS-wide values are unsupported.
|
|
129
270
|
|
|
130
271
|
Pre-1.0. Keep tests and documentation aligned when changing vocabulary.
|
package/dist/index.d.ts
CHANGED
|
@@ -64,6 +64,7 @@ declare function transformerCompileClass(options?: CompileClassOptions): SourceC
|
|
|
64
64
|
type ColorPalette = Record<string, Record<string, string>>;
|
|
65
65
|
/** Semantic color roles emitted as `--color-<role>` variables. */
|
|
66
66
|
type SemanticColors = Record<string, string | number>;
|
|
67
|
+
type ColorRole = "primary" | "neutral" | "focused" | "success" | "warning" | "failure" | "general";
|
|
67
68
|
interface ThemeAnimation {
|
|
68
69
|
keyframes?: Record<string, string>;
|
|
69
70
|
durations?: Record<string, string>;
|
|
@@ -74,8 +75,10 @@ interface ThemeAnimation {
|
|
|
74
75
|
interface Theme {
|
|
75
76
|
/** Named color palette; each color is a 12-step `100...950` scale. */
|
|
76
77
|
colors?: ColorPalette;
|
|
77
|
-
/**
|
|
78
|
+
/** Application semantic colors. Presets supply an empty namespace. */
|
|
78
79
|
semanticColors?: SemanticColors;
|
|
80
|
+
/** Physical palettes available through each data-css-<role> attribute. Lists replace per role. */
|
|
81
|
+
rolePalettes?: Partial<Record<ColorRole, readonly string[]>>;
|
|
79
82
|
breakpoint?: Record<string, string>;
|
|
80
83
|
container?: Record<string, string>;
|
|
81
84
|
spacing?: Record<string, string>;
|
|
@@ -100,8 +103,8 @@ interface Theme {
|
|
|
100
103
|
/**
|
|
101
104
|
* Non-default mode color overrides. `theme.colors` and
|
|
102
105
|
* `theme.semanticColors` are the default mode; each entry here (e.g. `dark`)
|
|
103
|
-
*
|
|
104
|
-
* configured `dark`/`light`
|
|
106
|
+
* contributes to the complete mapping for its `data-css-mode` region (or a
|
|
107
|
+
* configured `dark`/`light` alias). Only declare values that differ. OS
|
|
105
108
|
* preference uses `@os-dark` / `@os-light`.
|
|
106
109
|
*/
|
|
107
110
|
modes?: Record<string, {
|
|
@@ -110,38 +113,19 @@ interface Theme {
|
|
|
110
113
|
}>;
|
|
111
114
|
/** The mode whose palette is `theme.colors` (need not appear in `modes`). @default "light" */
|
|
112
115
|
defaultMode?: string;
|
|
113
|
-
/**
|
|
114
|
-
* Named theme variants (`@custom theme <name>`): subtree-scoped variable
|
|
115
|
-
* overrides emitted under `:where(.theme-<name>)` after the base and mode
|
|
116
|
-
* blocks. The bare `theme-<name>` class activates one. A variant may only
|
|
117
|
-
* override values the base theme declares — `@teacss/config` enforces that
|
|
118
|
-
* contract for entry-declared variants.
|
|
119
|
-
*/
|
|
120
|
-
themes?: Record<string, ThemeVariant>;
|
|
121
|
-
/** Root selector(s) used when emitting preflight CSS custom properties */
|
|
116
|
+
/** Additional declaration points inside every mode/palette region; roots always receive the complete mapping. */
|
|
122
117
|
preflightRoot?: Arrayable<string>;
|
|
123
118
|
/** Additional CSS custom properties merged after the default theme-derived preflight variables */
|
|
124
119
|
preflightBase?: Record<string, string | number>;
|
|
125
120
|
}
|
|
126
|
-
/**
|
|
127
|
-
* One named theme variant: the scalar scales plus color-only mode overrides
|
|
128
|
-
* (entry-authored variants carry only `dark`). Structural records, mode
|
|
129
|
-
* bookkeeping, and preflight options stay top-level-theme-only.
|
|
130
|
-
*/
|
|
131
|
-
interface ThemeVariant extends Omit<Theme, "animation" | "modes" | "defaultMode" | "themes" | "preflightRoot" | "preflightBase"> {
|
|
132
|
-
modes?: Record<string, {
|
|
133
|
-
colors?: ColorPalette;
|
|
134
|
-
semanticColors?: SemanticColors;
|
|
135
|
-
}>;
|
|
136
|
-
}
|
|
137
121
|
type CustomRule = Rule<Theme>;
|
|
138
|
-
/**
|
|
122
|
+
/** Optional region-marker aliases for `dark` / `light`; canonical `data-css-mode` takes precedence. */
|
|
139
123
|
interface ModeSelectors {
|
|
140
124
|
dark?: string;
|
|
141
125
|
light?: string;
|
|
142
126
|
}
|
|
143
127
|
interface PresetStandardOptions extends PresetOptions {
|
|
144
|
-
/**
|
|
128
|
+
/** Add `dark` / `light` region aliases, e.g. `{ dark: ".night" }`; no aliases are enabled by default. */
|
|
145
129
|
modeSelectors?: ModeSelectors;
|
|
146
130
|
/**
|
|
147
131
|
* Container sizes for the `@container-*` conditions, merged over the default
|