A CSS gradient generator that composites layers instead of drawing one ramp
Part of CSS LabKit, built by GrowQuest, leaders in web experiences.
Most gradient tools give you one linear or radial ramp, a handful of colour stops, and a copy button. That covers a button background. It doesn't cover the layered, textured backgrounds you see on product pages and hero sections — the ones with a soft radial glow sitting under a linear wash, tinted by a multiply layer, with grain breaking up the banding. Those aren't one gradient. They're several, stacked and blended, the same way you'd build them in a design tool.
GradientLab treats a gradient the way a design tool treats layers: add as many linear, radial or conic layers as you want, reorder them, hide one to compare, lock one while you tune another, duplicate a layer you like, or flatten the whole stack down to a single ramp when you're done. Each layer keeps its own colour stops, its own interpolation space and its own blend mode, and the CSS you export is exactly what's compositing on screen — including background-blend-mode, because that's a real, supported CSS property.
Layers composite for real
Blend modes are written out as background-blend-mode, so the preview and the copied CSS render identically.
Perceptual colour spaces
Interpolate in OKLCH or OKLab to keep mid-tones saturated, or stay in sRGB when you need legacy output.
Measured, not guessed
The legibility panel samples pixels the browser actually painted across the whole stack, rather than estimating from stop colours.
What you can do with GradientLab
background-blend-mode CSS, not simulated for the preview only.background-image gradient value and it comes apart into fully editable layers, parsed by the browser's own CSS engine.How browsers actually paint a gradient
Every choice in the sidebar maps to something the rendering engine does. Knowing what happens between your stops explains most of the surprises — the muddy middles, the visible steps, the grey fades.
Gradients are computed, not downloaded
A gradient isn't an image file — it's a value the <image> type accepts wherever a background image would go, and the browser computes it at paint time. That's why gradient CSS is a few hundred bytes instead of a few hundred kilobytes, and why it stays sharp at any DPI.
The gradient line, and three different geometries
A linear gradient runs along a line through the box centre at your angle, with stops projected perpendicular to it. A radial gradient grows outward from a centre point, with an ending shape and size keyword deciding where 100% falls. A conic gradient sweeps stops around a centre by angle — the only one of the three that can draw a pie chart or colour wheel natively.
Why sRGB interpolation looks muddy
Interpolating directly in sRGB averages channels arithmetically, but sRGB isn't perceptually uniform — a numeric midpoint between two saturated, distant hues lands on a desaturated, often grey colour. OKLCH and OKLab are built so equal numeric steps correspond to roughly equal perceived steps, keeping the midpoint vibrant instead.
transparent is transparent black, not “nothing”
transparent resolves to rgba(0,0,0,0) — fully transparent, but still nominally black. Fading a saturated colour straight to it in standard interpolation can drag the ramp toward grey; fading to the same colour at zero alpha instead avoids the smear.
Banding is an 8-bit problem
Displays store colour at 8 bits per channel — 256 discrete levels. A gradient spanning a small numeric range over a large area can need finer steps than that provides, and the eye reads the result as stripes. A small amount of noise dithers the quantization error away, which is exactly what a grain overlay does.
Stacking and blending
background-image accepts a comma-separated list, and the first layer paints on top. background-blend-mode takes a matching list, blending each layer with everything beneath it — the same mental model as layers in a design tool.
Anatomy of the CSS behind a stacked gradient
A two-layer gradient of the kind the tool produces — a soft radial glow screened over a linear base:
background-image:
radial-gradient(120% 90% at 12% 8% in oklch, #7A4DFF 0%, 46%, rgb(122 77 255 / 0) 72%),
linear-gradient(135deg in oklch shorter hue, #4D1DED 0%, #0E7490 100%);
background-blend-mode: screen, normal;
background-color: #351A9E;radial-gradient()The layer type. Swap for linear-gradient() or conic-gradient(), or prefix any of them with repeating-.120% 90%Ending shape size — the radii of the ellipse, relative to the box.at 12% 8%Where the gradient originates. Off-centre origins are what make a glow read as light rather than a bullseye.in oklchThe interpolation colour space used between stops.shorter hueWhich way round the hue wheel to travel. longer hue takes the scenic route through the other hues.135degDirection of the gradient line, clockwise from straight up.#4D1DED 0%A colour stop and its position along the line. Two stops at the same position create a hard edge.46%A bare percentage is a colour hint — the midpoint where the mix is half and half — without adding a stop.comma (,)Starts a new layer. The first one listed sits on top of the rest.background-blend-modeOne mode per layer, in the same order, blending it into what's beneath. background-color is the solid fallback below everything.Best practices & design principles
Match the interpolation space to the mood, not just the hue count
OKLCH and OKLab keep saturated transitions between complementary or far-apart hues vibrant. sRGB or HSL can be the better pick when you deliberately want a muted, desaturated middle, like fog or dusk — muddy isn't always wrong, it's a choice you should make on purpose.
Off-centre radial origins read as light; centred ones read as a target
A radial gradient centred with concentric rings reads as a bullseye. Push the centre toward a corner (circle at 20% 15%) and the same gradient reads as ambient light falling across a surface.
Check contrast at the worst point, not the average
Text over a gradient can be legible at one end and unreadable at the other. Sample the actual darkest and lightest points it crosses against WCAG's 4.5:1 minimum — a gradient that averages to good contrast can still fail badly at one edge.
Widen a shallow gradient's range or add grain before a large hero
Banding gets worse as a gradient spans more pixels with less colour change per pixel. Either increase the perceptual distance between stops or add a low-opacity noise layer; both fix it, and they're not mutually exclusive.
Use multiply or duotone layers for on-brand tinting
A neutral or photographic base with a brand-colour layer set to multiply keeps every section visually related without manually re-deriving a palette each time — change the tint layer once and every background using it updates in kind.
Keep gradient direction consistent with your UI's implied light source
If cards and buttons cast shadows implying light from the upper left, a background gradient brightening toward the lower right reads as physically inconsistent, even if nobody names why it feels off.
Why GradientLab exists
Most gradient generators optimise for the ten-second case: pick two colours, copy linear-gradient(...), done. That's real and common, and GradientLab still does it in ten seconds. But it doesn't stop there, because a two-stop ramp isn't what most shipped interfaces actually use — real hero sections and brand surfaces are usually two or three gradients composited together with a blend mode and a bit of grain, built by hand in a design tool and then approximated back into CSS by whoever implements it.
GradientLab is built so that approximation step doesn't have to happen, because the tool composites layers the same way the CSS property does. It's also built to be honest about the platform's actual limits: conic gradients don't have an SVG equivalent, so conic layers don't silently break your SVG export, they get flagged. transparent is transparent black, and the interpolation options exist specifically because sRGB midpoints go muddy — that's documented here, not hidden behind a “just trust the preview” black box.
If you're new to this
Start from a preset in the colour family you need, or run one of the smart generators and take the result apart layer by layer. The angle dial and position pad mean you never have to guess at degree values by hand.
If you do this daily
Everything is keyboard-and-drag reachable: on-canvas stop dragging, per-layer blend modes, hard stops via a second click at the same position, and CSS paste-in when iterating on something a designer handed you.
Honest output
No blend-mode effect that isn't actually in the exported CSS, no SVG conic gradient pretending to exist, no contrast number estimated from stop colours instead of the real composited pixels.
A better alternative to cssgradient.io, uiGradients and Colorffy
cssgradient.io and uiGradients are both solid, fast tools for the single-ramp case, and Colorffy's mesh gradient tool goes further with blend modes and OKLCH export. Here's where the structural differences sit.
background-blend-mode, not just the preview.background-image gradient into GradientLab and it becomes editable layers again; the other tools are one-directional, generator-to-clipboard only.Frequently asked questions about CSS gradients
How many gradients can one CSS element have?
As many as you list, comma-separated, in background-image — there's no hard spec limit, only practical rendering cost. Each needs its own entry in background-blend-mode (or it defaults to normal) if you want it composited with the ones beneath it.
What causes visible banding in a CSS gradient, and how do I fix it?
Banding happens when a gradient spans a colour range too subtle for 8-bit colour depth to represent smoothly over a large area — the eye picks out the resulting steps as bands. Widening the colour distance between stops helps, but the more reliable fix for a gradient that has to stay subtle is a low-opacity noise overlay.
Can I animate a CSS gradient?
Not the gradient's own stop colours or positions directly — background-image isn't natively animatable in most browsers. Common workarounds are animating background-position on an oversized gradient, animating a mask or clip-path over a static gradient, or animating filter: hue-rotate() on top of it.
How do I check if text is readable over a gradient background?
Check contrast at the worst point the text touches, not an average across the gradient — WCAG's 4.5:1 minimum (3:1 for large text) applies at every point text sits over. A gradient that looks fine where you placed a headline can fail badly a few pixels to the left.
Why does my gradient look grey or brown in the middle instead of blending cleanly?
That's sRGB linear interpolation: averaging red/green/blue channels between two saturated, far-apart hues produces a numeric midpoint that happens to be desaturated. Switching the interpolation space to OKLCH or OKLab keeps the transition perceptually vibrant instead.
What's the difference between linear, radial and conic gradients?
Linear transitions along a straight line at a set angle across the box. Radial transitions outward from a centre point in a circle or ellipse. Conic sweeps around a centre point by angle instead of moving outward — the only one of the three that can draw a natural pie-chart or colour-wheel effect.
Can I export a conic gradient to SVG?
No — SVG has no conic gradient primitive, only linearGradient and radialGradient. A tool claiming to export a conic layer to SVG is approximating it with a raster fill; it's more honest for a conic-containing stack to export as CSS or PNG instead.
Why is transparent sometimes causing a dark or muddy fade instead of a clean one?
transparent resolves to fully-transparent black, not “no colour.” Fading directly to it in standard interpolation briefly crosses through partially-transparent near-black values, producing a dark smear — fading to a transparent version of the actual foreground hue avoids it.