tl.create
The core API. Compiles a literal style-object map into atomic class names.
Signature
function create<T extends StyleMap>(map: T): ResolvedStyleMap<T>;
type StyleMap = Record<string, StyleDef>;
type StyleDef = {
[K in CSSPropertyName]?: string | number;
} & {
[K in BuiltInVariantKey | CustomVariantKey]?: StyleDef;
} & {
[K in `:${string}` | `&${string}` | `[${string}` | `.${string}` | `@${string}` | `>${string}`]?: StyleDef;
} & {
_autoDark?: false;
_autoRtl?: false;
_skipContrast?: true;
_layer?: string;
_bundle?: string;
};
type ResolvedStyleMap<T> = { [K in keyof T]: string };
Examples
Single rule
const $ = tl.create({
card: { padding: "1rem", background: "white" },
});
// → { card: "tla1b2c3d4 tle5f6g7h8" }
Multiple groups
const $ = tl.create({
card: { padding: "1rem" },
title: { fontSize: "1.25rem", fontWeight: 600 },
});
Variants
const $ = tl.create({
link: {
color: "blue",
_hover: { textDecoration: "underline" },
_focus: { outline: "2px solid currentColor" },
_disabled: { color: "gray", pointerEvents: "none" },
},
});
Breakpoints
tl.create({
layout: {
display: "grid",
gridTemplateColumns: "1fr",
md: { gridTemplateColumns: "1fr 1fr" },
lg: { gridTemplateColumns: "1fr 1fr 1fr" },
},
});
Dark mode (manual override)
tl.create({
surface: {
background: "white",
_dark: { background: "#0a0a0a" },
},
});
(For most colors, the auto-dark compiler pass derives this for you. See Dark mode.)
Raw selectors
tl.create({
list: {
listStyle: "none",
"& > li:not(:first-child)": { marginTop: "0.5rem" },
"@supports (display: grid)": { display: "grid" },
},
});
Allowed values
| Type | Example |
|---|---|
| String literal | "red", "1rem", "linear-gradient(...)" |
| Number literal | 8 (px-coerced for length-typed properties; raw for unitless properties) |
| Token reference | tokens.brand.primary, tl.cssVar("brand-primary") |
| Nested object | { _hover: { ... } }, { "@supports (...)": { ... } } |
Not allowed (compile-time error):
- Variables:
{ color: myVar } - Function calls:
{ color: getColor() } - Template literals:
{ color: `${a}-${b}` } - Spreads:
{ ...other } - Computed keys:
{ [k]: v }
Compile output
For tl.create({ btn: { color: "white", padding: "8px" } }):
- The CSS file gains:
.tla1b2c3d4 { color: white; } .tle5f6g7h8 { padding: 8px; } - The call site is rewritten to:
const $ = { btn: "tla1b2c3d4 tle5f6g7h8" };
Runtime fallback
If the compiler transform didn't run (Server Components without bundler hook, Vitest without setup, raw Node), tl.create runs at runtime and produces the same class names via the duplicated FNV-1a hash. The CSS rules themselves still come from the static stylesheet — no rules are emitted at runtime.
This means: server-rendered HTML, client-rendered HTML, and statically-extracted HTML all reference the same atomic classes for the same input, regardless of which path runs.
See also
tl.create is the entry point for almost everything in traceless-style.
Last-wins conflict-aware class joining. Reads compile-time-injected metadata to deterministically pick the latest input that sets each prope
clsx-style conditional class joining. No conflict resolution — preserves input order, drops falsy values.