25 CSS Spinners 16 / 25
Spiral Galaxy CSS Spinner
Three overlapping conic-gradient arms spiral outward from a bright central core, blurred and rotated 120° apart to simulate a three-armed barred spiral galaxy.
This is a full-page demo — interact inside the frame above, or open it in the playground for the full-screen experience.
The code
<div class="sp-16">
<div class="sp-16__galaxy">
<div class="sp-16__arm"></div>
<div class="sp-16__arm"></div>
<div class="sp-16__arm"></div>
<div class="sp-16__core"></div>
</div>
</div> <div class="sp-16">
<div class="sp-16__galaxy">
<div class="sp-16__arm"></div>
<div class="sp-16__arm"></div>
<div class="sp-16__arm"></div>
<div class="sp-16__core"></div>
</div>
</div>.sp-16,.sp-16 *,.sp-16 *::before,.sp-16 *::after{box-sizing:border-box;margin:0;padding:0}
.sp-16{
--bg:#03010a;
display:flex;
align-items:center;
justify-content:center;
min-height:100vh;
background:var(--bg);
}
.sp-16__galaxy{
position:relative;
width:100px;
height:100px;
animation:sp-16-spin 3s linear infinite;
}
.sp-16__arm{
position:absolute;
inset:0;
border-radius:50%;
}
.sp-16__arm:nth-child(1){
background:conic-gradient(
transparent 0deg, transparent 40deg,
rgba(99,102,241,0.8) 80deg, transparent 160deg,
transparent 200deg, transparent 240deg,
rgba(99,102,241,0.4) 280deg, transparent 360deg
);
filter:blur(2px);
}
.sp-16__arm:nth-child(2){
background:conic-gradient(
transparent 0deg, transparent 120deg,
rgba(168,85,247,0.7) 160deg, transparent 240deg,
transparent 280deg, transparent 300deg,
rgba(168,85,247,0.3) 340deg, transparent 360deg
);
filter:blur(1.5px);
transform:rotate(120deg);
}
.sp-16__arm:nth-child(3){
background:conic-gradient(
transparent 0deg, transparent 240deg,
rgba(236,72,153,0.6) 280deg, transparent 360deg
);
filter:blur(1px);
transform:rotate(240deg);
}
.sp-16__core{
position:absolute;
inset:38px;
border-radius:50%;
background:radial-gradient(circle,#fff 0%,rgba(168,85,247,0.8) 40%,transparent 80%);
filter:blur(2px);
}
@keyframes sp-16-spin{
to{transform:rotate(360deg)}
}
@media (prefers-reduced-motion: reduce){
.sp-16__galaxy{animation:none}
} .sp-16,.sp-16 *,.sp-16 *::before,.sp-16 *::after{box-sizing:border-box;margin:0;padding:0}
.sp-16{
--bg:#03010a;
display:flex;
align-items:center;
justify-content:center;
min-height:100vh;
background:var(--bg);
}
.sp-16__galaxy{
position:relative;
width:100px;
height:100px;
animation:sp-16-spin 3s linear infinite;
}
.sp-16__arm{
position:absolute;
inset:0;
border-radius:50%;
}
.sp-16__arm:nth-child(1){
background:conic-gradient(
transparent 0deg, transparent 40deg,
rgba(99,102,241,0.8) 80deg, transparent 160deg,
transparent 200deg, transparent 240deg,
rgba(99,102,241,0.4) 280deg, transparent 360deg
);
filter:blur(2px);
}
.sp-16__arm:nth-child(2){
background:conic-gradient(
transparent 0deg, transparent 120deg,
rgba(168,85,247,0.7) 160deg, transparent 240deg,
transparent 280deg, transparent 300deg,
rgba(168,85,247,0.3) 340deg, transparent 360deg
);
filter:blur(1.5px);
transform:rotate(120deg);
}
.sp-16__arm:nth-child(3){
background:conic-gradient(
transparent 0deg, transparent 240deg,
rgba(236,72,153,0.6) 280deg, transparent 360deg
);
filter:blur(1px);
transform:rotate(240deg);
}
.sp-16__core{
position:absolute;
inset:38px;
border-radius:50%;
background:radial-gradient(circle,#fff 0%,rgba(168,85,247,0.8) 40%,transparent 80%);
filter:blur(2px);
}
@keyframes sp-16-spin{
to{transform:rotate(360deg)}
}
@media (prefers-reduced-motion: reduce){
.sp-16__galaxy{animation:none}
}How this works
Three divs with identical inset:0 sizing each carry a different conic-gradient: each has one primary arm (a colour stop from transparent to opaque) and one ghost arm at lower opacity, placed at roughly the same angular position but with transparent zones between them. Each arm layer is pre-rotated by 0°, 120°, and 240° respectively so the three arms distribute evenly around the 360° space.
Each layer has a different filter:blur() value (2px, 1.5px, 1px) to soften arm edges, and the entire parent element rotates with a slow 3s sp-16-spin. A central radial-gradient core with extra blur provides the bright galactic nucleus. The rotation carries all three arm layers together as a unified shape.
Customize
- Change arm colours by editing the conic-gradient colour stops in each
:nth-childlayer — a blue-white-gold palette creates a realistic Milky Way appearance. - Add more arms by inserting a fourth layer with its own
conic-gradientrotated 90° from the others (for 4-arm spiral) or 72° apart (for 5-arm). - Increase blur values for a softer, more diffuse galaxy or reduce to near-zero for crisp mathematical-plot style arms.
- Change the rotation speed from
3sto10sfor an astronomical timescale; combine with a slower core pulse for a meditative effect. - Reduce the overall wrapper to
60pxfor a small planetary loading state, or expand to200pxfor a full hero section animation.
Watch out for
- Multiple
filter:blur()elements on overlapping layers can be expensive to composite on mobile — test on mid-range devices and fall back to a single-layer conic spinner if needed. conic-gradientrequires Chrome 69+, Safari 12.1+, Firefox 83+ — the galaxy disappears entirely in older browsers without a fallback.- The
mix-blend-mode:screenon the second layer requires the parent background to be non-white for the blend to add luminance; on white backgrounds change blend mode tomultiplyfor dark-on-light version.
Browser support
| Chrome | Safari | Firefox | Edge |
|---|---|---|---|
| 69+ | 12.1+ | 83+ | 69+ |
conic-gradient and mix-blend-mode required; filter blur GPU-accelerated on modern browsers.