CSSApril 2026 · 6 min read

How to Create a CSS Loading Spinner (No JavaScript)

Loading indicators tell users something is happening. A well-designed spinner reduces perceived wait time and prevents users from clicking away. Pure CSS loaders require no JavaScript, load instantly, and work even if scripts fail — making them ideal for initial page loads and lazy-loaded content.

Try the CSS Loader Generator
Free, no signup
DG
Derek Giordano
Designer & Developer
In this guide
01The Classic Spinner02Bouncing Dot Loaders03Skeleton Screens04Accessibility Considerations
⚡ Key Takeaways
  • Build pure CSS loading spinners, dots, bars, and skeleton screens.
  • The Classic Spinner.
  • Covers bouncing dot loaders.
  • Covers skeleton screens.
  • Covers accessibility considerations.

The Classic Spinner

The simplest CSS spinner is a circle with a partial border that rotates:

.spinner {

width: 40px;

height: 40px;

border: 4px solid rgba(255,255,255,0.1);

border-top-color: #00FFD1;

border-radius: 50%;

animation: spin 0.8s linear infinite;

}

@keyframes spin { to { transform: rotate(360deg); } }

This pattern is lightweight, accessible, and works in every browser. Customize the size, border width, and colors to match your design system.

Bouncing Dot Loaders

Three dots with staggered animations create a typing or loading indicator:

💡 Tip
Stick to animating transform and opacity for smooth 60fps performance. These properties are handled by the GPU compositor and skip expensive layout recalculations.

.dots span {

display: inline-block;

width: 10px;

height: 10px;

border-radius: 50%;

background: #00FFD1;

animation: bounce 1.4s ease-in-out infinite;

}

.dots span:nth-child(2) { animation-delay: 0.16s; }

.dots span:nth-child(3) { animation-delay: 0.32s; }

@keyframes bounce {

0%, 80%, 100% { transform: scale(0); }

40% { transform: scale(1); }

}

Dot loaders feel more conversational — they're commonly used in chat interfaces and messaging apps.

Skeleton Screens

Skeleton screens show a placeholder layout that mimics the content's shape before it loads. They reduce perceived load time more than spinners because users can see the content structure forming:

⚠ Warning
Avoid animating width, height, top, or left. These trigger layout recalculations on every frame and can drop performance below 60fps.

.skeleton {

background: linear-gradient(90deg, rgba(255,255,255,0.03) 25%, rgba(255,255,255,0.06) 50%, rgba(255,255,255,0.03) 75%);

background-size: 200% 100%;

animation: shimmer 1.5s infinite;

border-radius: 8px;

}

@keyframes shimmer { to { background-position: -200% 0; } }

Apply this to placeholder divs that match the dimensions of your actual content elements.

Accessibility Considerations

Add role='status' and an aria-label to your loader container so screen readers announce the loading state. Use prefers-reduced-motion to provide a static alternative for users who've disabled animations:

@media (prefers-reduced-motion: reduce) {

.spinner { animation: none; border-top-color: #00FFD1; opacity: 0.7; }

}

Never rely solely on animation to indicate loading — include a visually hidden text label like 'Loading...' for screen readers. Use the CSS Loader Generator to create and customize loaders with all accessibility attributes built in.

Frequently Asked Questions

How do I create a CSS-only loading spinner?+
Use a div with a circular border where one side is colored and the rest is transparent, then apply a rotate animation. The classic pattern needs just 6 lines of CSS and no JavaScript.
Are CSS loaders better than GIF loaders?+
Yes. CSS loaders are smaller (no file download), infinitely scalable (no pixelation), customizable with CSS variables, and respect prefers-reduced-motion for accessibility. GIF loaders are a legacy approach.
How do I make a skeleton loading screen?+
Create placeholder divs that match your content layout, apply a shimmer gradient animation using background-size and background-position, and replace them with real content when it loads.
Try it yourself

Use the CSS Loader Generator — free, no signup required.

⚡ Open CSS Loader Generator
DG
Derek Giordano
Written by the creator of Ultimate Design Tools. BA in Business Marketing.
⚡ Try the free Loading Skeleton Generator →