1. linear-gradient

The workhorse of CSS gradients. The first argument is the direction: either a keyword like to right or an angle in degrees. Everything after that is a list of colors (and optionally where each color starts). You can chain as many stops as you want.

to right

The default direction most people reach for first. Horizontal flows naturally for western reading patterns.

to bottom

Useful for hero sections where you want a colour to fade into the page below it.

135deg diagonal

135° is probably the sweet-spot for diagonal. Feels dynamic without looking tilted.

72deg custom angle
72°

Worth knowing: 0deg goes bottom-to-top, not left-to-right. Every 90° rotates the direction clockwise.

3 color stops
A → B → C

Just keep adding colours. CSS space them evenly by default, or you can give each one an explicit position.

Hard stop (no blend)
Hard

Put two colour stops at the same percentage and you get a hard edge instead of a blend. Useful for stripes and flags.

5-color spectrum
Rainbow

You can approximate a full rainbow by stepping through the hue wheel. Five stops gets you close enough.

Fade to transparent
Fade out

Fading to rgba(color, 0) instead of white or black lets the element dissolve into whatever's behind it.

/* Direction keywords */
background: linear-gradient(to right,   #6366f1, #a855f7);
background: linear-gradient(to bottom,  #6366f1, #ec4899);
background: linear-gradient(to bottom right, #6366f1, #06b6d4);

/* Angle in degrees (0deg = bottom→top, 90deg = left→right) */
background: linear-gradient(135deg, #6366f1, #06b6d4);

/* Multiple color stops */
background: linear-gradient(to right, #6366f1, #a855f7, #ec4899);

/* Explicit stop positions */
background: linear-gradient(to right, #6366f1 0%, #a855f7 50%, #ec4899 100%);

/* Hard stop - no blend between colors */
background: linear-gradient(to right, #6366f1 50%, #ec4899 50%);

/* Fade to transparent */
background: linear-gradient(to bottom, rgba(99, 102, 241, 0.9), rgba(99, 102, 241, 0));

2. radial-gradient

Where linear-gradient draws a line, radial-gradient expands outward from a point. You pick the shape (circle stays perfectly round; ellipse stretches to fill the box), where the centre sits, and how far the gradient reaches before it stops blending.

circle (default center)
Circle

Bright in the middle, dark at the edges. Works well for spot-lit product shots.

ellipse
Ellipse

The browser's default if you leave out the shape keyword. It auto-sizes to the element's aspect ratio, so it rarely looks perfectly circular.

circle at top
at top

Moving the origin to an edge or corner makes it look like light is coming from outside the frame. Very popular in dark-mode hero sections.

circle at bottom right
Corner

Corner origins give you that cinematic wide-angle lens flare feel.

closest-side size
closest-side

closest-side stops the gradient at whichever side of the box is nearest to the centre. Handy when you need tight control over the falloff radius.

Multi-stop target rings
Rings

Stack enough stops and you end up with a bullseye. Not always practical, but it shows how stop positions work radially.

Spotlight overlay
Spotlight

This is the pattern behind most "hero glow" designs: a wide, semi-transparent ellipse at the top that fades into the dark background below it.

Dot pattern
Dots

A 1px circle fading to transparent, tiled with background-size. Zero images, just CSS. You can change the dot colour or spacing with a couple of variables.

/* Circle from center */
background: radial-gradient(circle, #6366f1, #1e1b4b);

/* Ellipse (default shape) */
background: radial-gradient(ellipse, #06b6d4, #0c4a6e);

/* Position: at keyword or percentage */
background: radial-gradient(circle at top, #a855f7, #1e1b4b);
background: radial-gradient(circle at 30% 70%, #f59e0b, #451a03);

/* Size keywords: closest-side | farthest-side | closest-corner | farthest-corner */
background: radial-gradient(circle closest-side, #10b981, #022c22);

/* Explicit size */
background: radial-gradient(ellipse 80% 50% at 50% 0%, rgba(99,102,241,0.4), transparent);

/* Multi-stop rings */
background: radial-gradient(circle, #fff 0%, #c7d2fe 30%, #6366f1 70%, #1e1b4b 100%);

/* Dot pattern with background-size */
background-image: radial-gradient(circle, #94a3b8 1px, transparent 1px);
background-size: 1.5rem 1.5rem;

3. conic-gradient

conic-gradient is the newest of the three and genuinely fun to work with. Instead of radiating outward, it sweeps around a centre point like the hands of a clock. That makes it the only CSS-native way to draw a pie chart without JavaScript or SVG. It's also surprisingly good at checkerboards and sunburst patterns.

Color wheel

Six colours spread across 360° gives you a rough colour wheel. Round it off with border-radius: 50%.

Pie chart
40% 25% 15% 20%

Each slice is defined by a start and end percentage. The math is just addition, and unlike SVG you can update the percentages with a CSS variable.

from angle
from -90deg

By default the sweep starts at 3 o'clock (east). from -90deg rotates it to 12, which is what people expect for a clock or gauge.

Hard stop segments
Segments

Same idea as hard stops in linear-gradient. Pair the end of one colour with the start of the next and you get a clean solid edge with no blend.

Starburst

Two colours alternating every 30° gives you a starburst. Twelve stops total and the browser handles the rest.

Checkerboard
Checker

Four 90° hard stops + background-size tiling = checkerboard. If you've ever wondered how Figma does its transparency grid, this is exactly it.

/* Color wheel */
background: conic-gradient(#6366f1, #a855f7, #ec4899, #f59e0b, #10b981, #06b6d4, #6366f1);

/* Pie chart - hard stop segments */
background: conic-gradient(
  #6366f1  0%  40%,   /* 40% slice */
  #a855f7 40%  65%,   /* 25% slice */
  #ec4899 65%  80%,   /* 15% slice */
  #f59e0b 80% 100%    /* 20% slice */
);
border-radius: 50%;

/* Start from -90deg (12 o'clock) */
background: conic-gradient(from -90deg, #6366f1, #ec4899, #f59e0b, #6366f1);

/* Checkerboard with background-size */
background:
  conic-gradient(#e5e7eb 90deg, #fff 90deg 180deg, #e5e7eb 180deg 270deg, #fff 270deg);
background-size: 2rem 2rem;

4. Gradient Text

The trick is simple: apply a gradient as the background, then clip it to the text shape with background-clip: text and make the text itself transparent so the background shows through. Browser support is solid now, but keep the -webkit-background-clip prefix because Safari still needs it. Not great for body text (contrast audits will hate you), but brilliant for headlines.

Rainbow
Vivid

Four-stop diagonal, the classic starting point. Add more stops or tighten the angle to taste.

Gold metallic
Gold

Dark amber → bright yellow → near-white → back again. The symmetry of the stops is what gives it that metallic highlight look.

Animated shimmer
Neon

Make the gradient twice as wide as the element, then slide the position. The text stays put but the colours move underneath it.

Sunset
Dusk

Top-to-bottom direction means warm tones at the top of the letters and cool ones at the bottom. Works really well on tall letterforms.

Ice blue
Frost

Monochromatic gradients (different shades of one hue) feel more refined than multi-colour ones. Sky blues work well for tech brands.

Fire
Blaze

Real fire is hottest at the base and cooler at the tips. to top puts the reds at the bottom and the yellows up top, which maps to that naturally.

/* The gradient text recipe */
.gradient-text {
  background-image: linear-gradient(135deg, #6366f1, #a855f7, #ec4899);
  -webkit-background-clip: text; /* Safari */
  background-clip: text;
  -webkit-text-fill-color: transparent; /* Safari */
  color: transparent;
}

/* Animated shimmer - oversized background moves via animation */
.shimmer-text {
  background-image: linear-gradient(90deg, #22d3ee, #10b981, #22d3ee);
  background-size: 200%; /* twice as wide as the element */
  -webkit-background-clip: text;
  background-clip: text;
  -webkit-text-fill-color: transparent;
  color: transparent;
  animation: shimmer 3s linear infinite;
}

@keyframes shimmer {
  0%   { background-position: 200% center; }
  100% { background-position: 0%   center; }
}
Contrast heads-up: Automated accessibility checkers can't measure contrast on gradient text. They'll either skip it or flag it as a failure. The lightest colour in your gradient should still be readable against the background on its own. Keep gradient text to short headings; never use it for body copy or anything instructional.

5. Layered & Multi-background Gradients

CSS lets you stack as many gradients on top of each other as you want, separated with commas. The first one in the list sits on top. Combine a few semi-transparent radial gradients and you can replicate the "noise + gradient" aesthetic that's been everywhere in design tool exports lately, without a single exported image.

Mesh gradient
3 radial layers

Three semi-transparent radial blobs (top-left, bottom-right, centre) that mix where they overlap. This is how most "mesh gradient" generators work under the hood.

Dual spotlight
Spotlights

Two wide, off-screen ellipses bleeding inward. You see this in basically every dark-mode SaaS landing page right now.

Sunrise blend
Sunrise

Three linear gradients stacked: one from the bottom, one from the top, one as the base. Each is opaque only at its end and transparent in the middle, so they blend into each other.

Glass / frosted overlay
Glass

A 15% white diagonal sheen on top of a solid gradient. It's what gives glassmorphism cards that slightly lighter upper-left corner.

Diagonal stripe texture
Stripes

repeating-linear-gradient tiles automatically. Define a stripe once and it repeats forever. Layer it at 7% opacity and it reads as texture rather than pattern.

SVG noise + gradient
Noise

SVG turbulence filter base64'd into a url() and layered over the gradient at 8% opacity. Same grainy texture that design tools export, but no image files involved.

/* Multiple backgrounds - first listed is on top */
background:
  radial-gradient(ellipse at top left,    rgba(99,102,241,0.5)  0%, transparent 60%),
  radial-gradient(ellipse at bottom right,rgba(168,85,247,0.5)  0%, transparent 60%),
  radial-gradient(ellipse at center,      rgba(236,72,153,0.3)  0%, transparent 70%),
  #0f172a;

/* Glass sheen overlay */
background:
  linear-gradient(135deg, rgba(255,255,255,0.15) 0%, rgba(255,255,255,0.02) 100%),
  linear-gradient(135deg, #6366f1, #4f46e5);

/* Diagonal repeating stripes as texture */
background:
  repeating-linear-gradient(
    -45deg,
    rgba(255,255,255,0.07) 0px,
    rgba(255,255,255,0.07) 10px,
    transparent 10px,
    transparent 20px
  ),
  linear-gradient(135deg, #6366f1, #4f46e5);

6. Animated Gradients

Here's the awkward truth: CSS can't tween between two gradient definitions directly. You can't smoothly animate from one colour palette to another the way you'd animate a colour property. But there are a few clever workarounds: sliding an oversized gradient's position, rotating its hue with a filter, or using a pseudo-element as the moving part. Each has its place.

Shifting background-position
Shifting

The go-to technique. Make the gradient 3× wider than the element and animate background-position back and forth. The visible window stays the same; the colours scroll underneath it.

hue-rotate filter
Hue spin

One line of CSS, zero extra elements. The gradient itself never changes; hue-rotate just shifts all its colours through the wheel. Worth noting: it affects child elements too.

Fast shimmer
Shimmer

Same technique as above but faster and with fewer colours. 2s feels urgent rather than ambient, which works well for a CTA button you want people to click.

Sweep shimmer (::after)
Sweep

A thin white diagonal stripe in a ::after element slides from right to left continuously. This is the exact pattern used in skeleton loading screens.

Glow pulse
Pulse

Cheat: animate box-shadow spread instead. The gradient stays static, the glow around it breathes. Lighter on the browser than animating background properties.

/* Technique 1: animate background-position on oversized gradient */
.animated-gradient {
  background: linear-gradient(270deg, #6366f1, #a855f7, #ec4899, #f59e0b, #6366f1);
  background-size: 300% 300%; /* must be larger than element */
  animation: gradientShift 6s ease infinite;
}

@keyframes gradientShift {
  0%   { background-position: 0% 50%; }
  50%  { background-position: 100% 50%; }
  100% { background-position: 0% 50%; }
}

/* Technique 2: hue-rotate filter - simplest approach */
.hue-animated {
  background: linear-gradient(135deg, #6366f1, #06b6d4);
  animation: hueRotate 4s linear infinite;
}

@keyframes hueRotate {
  to { filter: hue-rotate(360deg); }
}

/* Technique 3: ::after sweep shimmer */
.shimmer-element {
  position: relative;
  overflow: hidden;
  background: #1e1b4b;
}
.shimmer-element::after {
  content: '';
  position: absolute;
  inset: 0;
  background: linear-gradient(105deg, transparent 40%, rgba(255,255,255,0.15) 50%, transparent 60%);
  background-size: 200% 100%;
  animation: sweep 2s linear infinite;
}

@keyframes sweep {
  0%   { background-position: 200% 0; }
  100% { background-position: -200% 0; }
}

7. Gradient Borders

There's no border-gradient property in CSS, so you have to be creative. Of the four approaches below, Method 2 (the ::before trick) is the one I'd reach for in most projects: it supports rounded corners, works in every browser, and the code is straightforward enough to understand at a glance.

border-image (no border-radius)
border-image

One property, done. Catch: border-image and border-radius can't be used together. The spec forbids it. Square corners only.

::before pseudo overlay (recommended)
::before trick

The background element sits 2px outside on all sides, fully behind the main element. border-radius: inherit means they curve together automatically.

background-clip: border-box
Padding trick

Two backgrounds in one declaration: a white one clipped to the padding area, and the gradient clipped all the way to the border edge. No extra elements needed, but the syntax takes a second read.

Animated rotating border
Spinning border

Requires the @property rule (well-supported, not IE). Without it the browser can't interpolate --angle and the animation jumps instead of spinning.

Glow border (box-shadow)
Glow

Not technically a gradient border, but on dark backgrounds the inset + outer box-shadow combo looks identical and requires zero tricks. Worth keeping in mind as a lightweight alternative.

Gradient underline
Underline link Another link

A background-image gradient constrained to 2px tall, pinned to the bottom edge. Works with multi-line text, animates smoothly on hover, and degrades gracefully.

/* Method 1: border-image - no border-radius support */
.border-gradient {
  border: 2px solid transparent;
  border-image: linear-gradient(135deg, #6366f1, #ec4899) 1;
}

/* Method 2: ::before pseudo - supports border-radius */
.border-gradient-rounded {
  position: relative;
  background: white;
  border-radius: 0.75rem;
}
.border-gradient-rounded::before {
  content: '';
  position: absolute;
  inset: -2px; /* border thickness */
  border-radius: inherit;
  background: linear-gradient(135deg, #6366f1, #ec4899);
  z-index: -1;
}

/* Method 3: background-clip - supports border-radius */
.border-gradient-clip {
  background:
    linear-gradient(white, white) padding-box,
    linear-gradient(135deg, #f59e0b, #ef4444, #a855f7) border-box;
  border: 2px solid transparent;
  border-radius: 0.75rem;
}

/* Method 4: Animated rotating border */
@property --angle {
  syntax: '';
  initial-value: 0deg;
  inherits: false;
}

.animated-border {
  background:
    linear-gradient(white, white) padding-box,
    linear-gradient(var(--angle), #6366f1, #ec4899, #f59e0b, #6366f1) border-box;
  border: 2px solid transparent;
  animation: rotate-border 3s linear infinite;
}

@keyframes rotate-border {
  to { --angle: 360deg; }
}

/* Gradient underline */
.grad-underline {
  background-image: linear-gradient(135deg, #6366f1, #ec4899);
  background-size: 100% 2px;
  background-position: 0 100%;
  background-repeat: no-repeat;
  padding-bottom: 0.25rem;
}