Documentation Index
Fetch the complete documentation index at: https://mintlify.com/pocket-stack/pocketjs/llms.txt
Use this file to discover all available pages before exploring further.
PocketJS styles come from a build-time Tailwind subset. There is no runtime Tailwind, no CSS, and no arbitrary-utility escape hatch: a fixed set of utilities is parsed at build time by compiler/tailwind.ts and baked into styles.bin, which the Rust core reads directly. This page is the exhaustive reference for exactly which utilities exist and what values they accept.
import { View, Text } from "@pocketjs/framework/components";
function Card() {
return (
<View class="flex flex-col gap-2 p-4 bg-slate-800 rounded-lg">
<Text class="text-lg font-bold text-slate-50">Hello PSP</Text>
</View>
);
}
For how styling fits into the build pipeline, see the Styling guide.
How a Class Literal Compiles
A candidate string is split on whitespace into tokens. Every token must parse as a supported utility for the string to become a style record.
- If all tokens parse, the literal compiles to a
styleId stored in styles.bin. The class attribute resolves to that id natively.
- If any token is not a supported utility, the whole literal is silently ignored — it is assumed to be ordinary text. One unknown token drops the entire literal.
- Token order does not matter. Records are canonicalized and deduped, so
"p-4 flex" and "flex p-4" share one styleId.
When any single token in a class literal is unrecognized, the entire literal is silently dropped — not just the bad token. One unknown token disqualifies the whole string. Double-check spelling and consult this reference if a style is not applying.
The Spacing Scale
Most sizing and offset utilities take a value on Tailwind’s spacing scale, where N maps to N * 4 pixels. Decimals are allowed.
| Token | Pixels |
|---|
0 | 0 |
1 | 4 |
2 | 8 |
3 | 12 |
4 | 16 |
6 | 24 |
8 | 32 |
12 | 48 |
2.5 | 10 |
Arbitrary pixel values are supported for every spacing-scale utility using bracket syntax — the value is taken as literal pixels (the px suffix is optional):
<View class="w-[123] h-[123px] p-[10] gap-[6px]" />
A second group of utilities (z, opacity, scale, scale-x, scale-y, rotate, duration, delay) take a plain number instead. Those do not accept bracket syntax — only bare digits.
Negative values are not supported. Any token beginning with - fails to parse.
Color Palette
Colors come from the Tailwind v3 default palette: {family}-{shade}, plus the keywords white, black, and transparent.
Families: slate, gray, zinc, red, orange, amber, yellow, green, emerald, teal, cyan, sky, blue, indigo, violet, purple, fuchsia, pink, rose.
Shades: 50, 100, 200, 300, 400, 500, 600, 700, 800, 900, 950.
| Prefix | Applies to | Example |
|---|
bg-{color} | Background fill | bg-slate-800 |
text-{color} | Text color | text-emerald-400 |
border-{color} | Border color (also sets a 1px border) | border-slate-600 |
from-{color} | Gradient start stop | from-sky-500 |
to-{color} | Gradient end stop | to-blue-700 |
An unrecognized family or shade (e.g. bg-slate-999, text-brand-500) causes the entire literal to be ignored.
Flex
| Utility | Effect |
|---|
flex | display: flex |
flex-row | Main axis = row |
flex-col | Main axis = column |
flex-wrap | Allow wrapping |
flex-1 | grow: 1, shrink: 1, basis: 0 |
grow | flex-grow: 1 |
grow-0 | flex-grow: 0 |
shrink-0 | flex-shrink: 0 |
basis-N | Flex basis (spacing scale) |
gap-N | Gap between children (spacing scale or arbitrary px) |
justify-start | justify-center | justify-end | justify-between | justify-around | Main-axis distribution |
items-start | items-center | items-end | items-stretch | Cross-axis alignment |
Only the five justify-* and four items-* values above exist. justify-evenly and items-baseline are not supported.
Box & Position
| Utility | Effect |
|---|
w-N | w-full | w-[px] | Width (spacing scale, full parent, or arbitrary px) |
h-N | h-full | h-[px] | Height |
min-w-N, min-h-N, max-w-N, max-h-N | Min/max size (spacing scale or arbitrary px) |
p-N, px-N, py-N, pt-N, pr-N, pb-N, pl-N | Padding (all sides, axes, or individual) |
m-N, mx-N, my-N, mt-N, mr-N, mb-N, ml-N | Margin |
absolute | position: absolute |
relative | position: relative |
inset-N, top-N, right-N, bottom-N, left-N | Position offsets (spacing scale or arbitrary px) |
hidden | display: none |
overflow-hidden | Clip children (native scissor) |
z-N | Z-index (plain integer) |
w-full / h-full are the only percentage-style sizes — they map to the SIZE_FULL sentinel in the spec. min-* / max-* do not accept -full.
Visual
| Utility | Effect |
|---|
bg-{color} | Background color |
bg-gradient-to-t | -b | -l | -r | Gradient direction (top / bottom / left / right) |
from-{color} | Gradient start color |
to-{color} | Gradient end color |
rounded | 4px corner radius |
rounded-sm | 2px |
rounded-md | 6px |
rounded-lg | 8px |
rounded-xl | 12px |
rounded-full | Pill/circle — build-time size required (see below) |
opacity-N | Opacity, N/100 (0–100) |
shadow | Small shadow |
shadow-md | Medium shadow |
shadow-lg | Large shadow |
border | 1px border (width only) |
border-{color} | Border color and a 1px border |
Gradients only run along the four cardinal directions — no diagonals. Set a direction with bg-gradient-to-* and stops with from-* / to-*:
<View class="bg-gradient-to-b from-sky-500 to-blue-700 w-full h-16" />
Border width is fixed at 1px. border-2, border-4, etc. do not exist — only bare border and border-{color}.
rounded-full Requires Build-Time Size
rounded-full bakes an exact radius at build time, so it needs the node’s width and height to be build-time known in the same literal via w-N/h-N (or arbitrary-px forms). The radius becomes min(w, h) / 2:
{/* ✅ OK — radius baked to 24px */}
<View class="w-12 h-12 rounded-full bg-rose-500" />
{/* ❌ Compile error — w-full is not a build-time pixel size */}
<View class="w-full h-12 rounded-full" />
Using rounded-full without a concrete w-N and h-N is a hard compile error, not a silent drop. This is used extensively in the settings demo for the toggle knobs:
{/* From demos/settings/app.tsx — knob with build-time known size */}
<View class="w-4 h-4 rounded-full bg-white border-indigo-200 shadow-md m-[2] translate-x-[0.5]" />
Text
| Utility | Effect |
|---|
text-{color} | Text color |
text-xs | 12px |
text-sm | 14px |
text-base | 16px (default) |
text-lg | 18px |
text-xl | 20px |
text-2xl | 24px |
text-4xl | 36px |
font-bold | Bold weight (baked bold atlas) |
text-left | text-center | text-right | Horizontal alignment |
leading-N | Line height (spacing scale or arbitrary px) |
tracking-wide | Letter spacing = 0.025 × font-size |
Font sizes are baked into atlases at build time — only the seven sizes above exist (12 / 14 / 16 / 18 / 20 / 24 / 36 px). There is no text-3xl, text-5xl, etc. Each size ships in two weights (regular and bold when font-bold is used). Text with no size or weight utility uses the 16px regular default.
Only font-bold exists for weight — no font-normal or font-semibold. Only tracking-wide exists for letter spacing.
Transforms are animatable and do not trigger relayout — always prefer them for motion.
| Utility | Effect |
|---|
translate-x-N | Translate X (spacing scale or arbitrary px) |
translate-y-N | Translate Y (spacing scale or arbitrary px) |
scale-N | Uniform scale, N/100 (e.g. scale-105 → 1.05) |
scale-x-N | X scale, N/100 |
scale-y-N | Y scale, N/100 |
rotate-N | Rotation in degrees (e.g. rotate-45) |
scale-* and rotate-* take plain numbers only (no bracket syntax, no negatives).
Motion / Transition
Adding any motion token to a literal attaches a transition block to that style record. Transitions fire when the style is swapped — for example on focus: / active: variant changes — and interpolate the animatable properties in the mask.
| Utility | Animates |
|---|
transition | Transforms + colors + opacity (the default property set) |
transition-all | Every animatable prop (including layout — can trigger relayout) |
transition-colors | bgColor, gradFrom, gradTo, borderColor, textColor |
transition-opacity | opacity |
transition-transform | translateX/Y, scale, scaleX/Y, rotate |
duration-N | Duration in milliseconds (0–65535) |
delay-N | Delay in milliseconds (0–65535) |
ease-linear | ease-in | ease-out | ease-in-out | ease-spring | ease-out-back | Easing curve |
Defaults. When a literal contains any motion token, unspecified fields fall back to: duration 150ms, delay 0ms, easing ease-in-out. A literal with duration/ease/delay but no transition-* utility behaves like transition-all.
spring and out-back are PocketJS additions beyond standard Tailwind easings. spring-bouncy is imperative-only — use spring() from @pocketjs/framework/animation instead.
{/* Background fades natively on focus — Rust ticks it, zero JS per frame */}
<View class="bg-slate-700 focus:bg-slate-500 transition-colors duration-200 ease-out" />
Variants
Two state variants are supported. They compile into separate blocks of the same style record and are switched natively — no JS runs on focus or press state change.
| Variant | Applies when |
|---|
focus: | The node is the focused node |
active: | The node is pressed/active |
<View
class="bg-slate-700 border-slate-600
focus:bg-slate-600 focus:border-blue-500
active:scale-95 transition"
focusable
/>
Any base utility can be prefixed with focus: or active:. Motion tokens (transition*, duration, delay, ease) apply to the whole record and are only recognized on the base variant — not behind focus: / active:.
Not Supported — Loud Errors
These are rejected at build/dev time rather than silently dropped:
| Construct | Why |
|---|
classList={{ … }} | Dynamic class objects are not supported; the renderer raises a dev error. |
Template-interpolated class fragments (class={`p-${n}`}) | Classes must be static literals to be collected and baked at build time. |
hover: | The PSP has no pointer — hover: in an otherwise valid literal is a hard compile error. Use focus: / active:. |
rounded-full without build-time w-N/h-N | The radius must be bakeable at build time. |
For dynamic styling, use one of:
- Ternaries of complete literals —
class={ok() ? "bg-green-600" : "bg-red-600"}.
style={{ … }} objects — per-key dynamic props applied at runtime.
animate() — imperative property animation (see Animation).
See Also
- Styling — the styling model overview, dynamic styling patterns, and pipeline details
- Animation —
transition-*, animate(), springs, and easing names
- Components —
View, Text, Image, and which accept class