Compatibility
FrontAlign is designed for modern browsers and modern web standards. The framework relies on CSS Custom Properties, OKLCH color spaces, logical properties, modern layout APIs, and contemporary browser JavaScript features.
Rather than shipping large compatibility layers, FrontAlign embraces the capabilities already available in current browser engines, resulting in a smaller runtime, cleaner code, and better long-term maintainability.
Supported Browsers
| Browser | Minimum Version |
|---|---|
| Chrome | 111+ |
| Edge | 111+ |
| Firefox | 113+ |
| Safari | 15.4+ |
| iOS Safari | 15.4+ |
| Opera | 97+ |
| Samsung Internet | 22+ |
These versions provide reliable support for the platform features required by FrontAlign.
These are the minimums for FrontAlign's core feature set (plain OKLCH, logical properties, CSS custom properties). A handful of tokens that derive their color from another custom property —
--selection,--link-hover, and similar — use relative color syntax, which requires slightly newer versions (Chrome/Edge 122+, Safari 18.0+, Firefox 128+). See OKLCH Color System below for the distinction.
Why Modern Browsers
FrontAlign intentionally targets modern browser engines.
This allows the framework to use:
- OKLCH color spaces
- CSS Custom Properties
- color-mix()
- Logical Properties
- CSS Grid
- Flexbox
- Modern viewport units
- Web Animations API
- IntersectionObserver
- MutationObserver
without introducing unnecessary compatibility overhead.
OKLCH Color System
FrontAlign uses OKLCH as its primary color format.
:root {
--accent: oklch(
from var(--primary) min(calc(l + 0.08), 0.88) calc(c * 0.9) h
);
}
OKLCH provides more predictable color manipulation, perceptual consistency, and cleaner theme generation compared to legacy color models.
As of early 2026, plain oklch() color values are supported by 90.55% of tracked global browser usage, per caniuse.com. Support shipped in:
- Safari 15.4 — March 14, 2022
- Chrome 111 — March 7, 2023
- Edge 111 — March 2023
- Firefox 113 — May 9, 2023
This lines up closely with FrontAlign's own minimum browser versions above, so most static color tokens already render natively for the large majority of visitors without any extra step.
Wide-gamut rendering depends on the display hardware and the selected color values.
Two categories of OKLCH usage
FrontAlign's stylesheet uses OKLCH in two structurally different ways, and they need different compatibility strategies. Knowing which one you're looking at determines whether tooling can help you or not.
Static OKLCH values — color defined directly as literal numbers, with no reference to another color:
:root {
--white: oklch(1 0 0);
--light: oklch(0.961 0 0);
--dark: oklch(0.2 0.01 260);
--body-text: oklch(0.145 0 0);
}
These make up the majority of FrontAlign's color definitions. Because the values are fixed at author-time, a build tool can resolve them to an equivalent sRGB color ahead of time — see Build-time fallbacks below.
Relative OKLCH derived from a custom property — color computed from another token using the from keyword:
:root {
--link-hover: oklch(from var(--primary) calc(l - 0.06) calc(c + 0.04) h);
--selection: oklch(from var(--primary) 0.88 calc(c * 0.85) h / 0.24);
}
.button:hover {
background-color: oklch(from var(--primary) calc(l - 0.08) c h);
}
These tokens derive their value from var(--primary), var(--accent), currentColor, and similar dynamic sources, which means the actual color is only known by the browser at render time — it can change with a theme switch, a dark: override, or a user-supplied brand color.
Relative color syntax (the from keyword) shipped slightly later than plain oklch(). Per caniuse.com, it currently sits at 89.52% full support, or 92.04% counting partial support, across tracked global browser usage. Full support shipped in:
- Safari 18.0 — September 2024
- Chrome 122 / Edge 122 — February 2024
- Firefox 128 — July 2024
This is still comfortably above 90% combined, but it's a different (slightly more recent) threshold than plain oklch() — worth knowing if you're deciding where to draw a fallback line. Build tools cannot precompute these tokens. See Manual fallbacks below.
Runtime Compatibility
The JavaScript runtime is built around standard browser APIs.
- Event delegation
- IntersectionObserver
- MutationObserver
- Custom Events
- Web Animations API
- ResizeObserver (where applicable)
These APIs are available across all officially supported browsers.
Theme Updates
FrontAlign relies heavily on CSS Custom Properties.
.button:hover {
background-color: oklch(from var(--primary) calc(l - 0.08) c h);
border-color: oklch(from var(--primary) calc(l - 0.12) c h);
}
When theme values change, the browser updates dependent styles automatically without requiring a DOM re-render.
Build-time fallbacks
If your project needs to support browsers below FrontAlign's minimum versions, static OKLCH values and color-mix() calls with literal arguments can be converted to an equivalent sRGB color automatically, at build time, with no changes to FrontAlign's source CSS.
Using the FrontAlign build tool
The simplest path is FrontAlign's own build command, which wraps this conversion for you — no PostCSS config required:
npx frontalign build
This produces a built output file with static OKLCH tokens automatically written as fallback-ordered pairs:
:root {
--white: rgb(255, 255, 255);
--white: oklch(1 0 0);
}
Older browsers read the first declaration; browsers with OKLCH support read the second, since the cascade lets the later matching declaration win. Ship the file that npx frontalign build outputs in place of the raw source stylesheet — nothing in FrontAlign's source needs to change, and this is purely a build step you opt into. For details on what the build step does internally, see Compiler Engine.
Using PostCSS directly
If you'd rather integrate the conversion into an existing PostCSS pipeline instead of using npx frontalign build, the same class of tools apply directly:
@csstools/postcss-oklab-function— convertsoklab()/oklch()torgb()(and optionallycolor(display-p3 ...)for wide-gamut displays), with the original notation kept as a fallback-ordered pair of declarations.- Lightning CSS — a faster, Rust-based alternative that performs the same class of color downleveling alongside other modern-syntax transforms (nesting, logical properties), if your build already uses it.
Example install and usage with PostCSS:
npm install --save-dev postcss @csstools/postcss-oklab-function
// postcss.config.js
module.exports = {
plugins: [
require("@csstools/postcss-oklab-function")({
preserve: true, // keep the original oklch() as a fallback pair
}),
],
};
This approach works for any static OKLCH value in FrontAlign's stylesheet, and for color-mix() calls where every argument is a literal color (no var()).
Manual fallbacks
Neither npx frontalign build nor the PostCSS plugins above can resolve a relative color's origin when that origin is a CSS custom property. This is a documented limitation of the relative color syntax tooling, not a bug: the actual value of var(--primary) isn't known until the browser renders the page, and it can change after a theme switch — so no build step can precompute it ahead of time.
This affects two patterns used throughout FrontAlign's stylesheet:
Relative OKLCH from a custom property or currentColor:
--link-hover: oklch(from var(--primary) calc(l - 0.06) calc(c + 0.04) h);
--selection: oklch(from var(--primary) 0.88 calc(c * 0.85) h / 0.24);
background-color: oklch(from currentColor l c h / 0.1);
color-mix() where one argument is a custom property:
background-color: color-mix(in srgb, var(--accent) 12%, transparent);
outline: 2.5px solid color-mix(in srgb, var(--primary) 60%, transparent);
If your project needs to support browsers below FrontAlign's minimum versions for these specific declarations, provide the fallback yourself with @supports, ordering the plain value first so the cascade falls back correctly:
:root {
/* Plain fallback — read by browsers without relative-color support */
--selection: rgba(37, 99, 235, 0.24);
}
@supports (color: oklch(from red l c h)) {
:root {
/* Original token — read by browsers that understand relative OKLCH */
--selection: oklch(from var(--primary) 0.88 calc(c * 0.85) h / 0.24);
}
}
The same pattern applies to color-mix(), testing the feature directly:
.badge {
background-color: rgba(37, 99, 235, 0.12); /* fallback */
}
@supports (background-color: color-mix(in srgb, red, blue)) {
.badge {
background-color: color-mix(in srgb, var(--accent) 12%, transparent);
}
}
Pick the fallback color deliberately — it won't track --primary automatically, since the entire reason for the fallback is that the browser can't compute that relationship. A neutral, low-contrast value (as shown above) degrades gracefully without needing to match your brand color exactly. FrontAlign does not ship these fallbacks by default, in the same way it does not ship physical-property margin or padding utilities by default — see Margin for the reasoning. Add them only where your project's supported-browser list actually requires it.
Progressive Enhancement
FrontAlign follows a progressive enhancement approach.
Core content remains accessible even when advanced visual features are unavailable. Modern browsers receive the complete design system, runtime behavior, animations, and theme capabilities.
See also
- Compiler Engine — how
npx frontalign buildresolves tokens, orders fallback declarations, and generates the final output CSS.