Guides · · Maxwell Prehoda
14 Text Animation Examples for Websites (That Stay Readable)
The text animations worth copying do one job: they make one phrase land, then get out of the way. A headline rises line by line, a key sentence gets a marker swipe, one word sparkles because it is new. The ones that fail animate every letter of every heading and leave screen reader users hearing a spelling bee.
Below are 14 examples from libraries, tutorials and makers you can check yourself, plus two of ours. Each one says what it is best for, what it runs on, and the catch. Most come with a live, pure-CSS demo from our Text Animations directory that you can copy.
We picked examples that cover the jobs text motion actually does on a website: reveal, emphasis, decoding, ambient loops and rotating words. Effects with their own guides, like text reveals, kinetic typography, gradient text and glitch text, get one entry or a link here so this page stays a map of the whole field.
1. GSAP SplitText: Best for staggered headline reveals on marketing sites
Platform: GSAP plugin, JavaScript, free
SplitText is a common choice when a headline needs to arrive line by line or word by word. It splits an element's text into characters, words and lines, each in its own element, so GSAP can stagger them. The v3.13.0 release was a major rewrite: the docs say it is half the size with 14 new features, including a mask option that wraps each piece in a clipping element for slide-up reveals, and autoSplit, which re-splits after web fonts load or the width changes, with an onSplit callback to rebuild the animation.
It also costs nothing now. GSAP's pricing page says the entire library, SplitText and ScrambleText included, is free, supported by Webflow. Our Line Mask Reveal below is a pure-CSS version of the masked line reveal: each line is a clipping wrapper around a moving span, written by hand instead of split by script.
Watch out for: In February 2026 Adrian Roselli tested GSAP's own SplitText demo and only NVDA with Firefox and TalkBack with Chrome read it correctly; JAWS, Narrator and VoiceOver failed. Split by lines or words rather than letters, and consider reverting the split once the animation ends.
2. Splitting.js by Stephen Shaw: Best for CSS-driven letter staggers with a tiny helper
Platform: JavaScript, MIT, about 1.5kb gzipped
Splitting.js does the splitting and leaves the animation to CSS. Each word span gets a --word-index custom property and each character span gets --char-index, while the target gets --word-total and --char-total. From there a stagger is one line of CSS, something like an animation-delay of the index times 40ms, and you can count backwards from the total to stagger from the end.
That split of duties is why it stays popular with people who would rather not hand a whole timeline to JavaScript. Our Letters Rise below shows the same idea with the spans written by hand: each letter carries its index in --i, so the delay is a single calc() and adding letters needs no new CSS. If you want that without any script at all, it is already in our directory.
Watch out for: Character splitting carries the screen reader risk in the entry above. Splitting.js gives you the spans; making them read as one word is your job, so test the output in VoiceOver and NVDA or split by words.
3. Splinter.js by Andy Clarke: Best for letter animations that try to stay accessible
Platform: JavaScript, 1.3kb minified
Andy Clarke published Splinter.js in December 2025 for his cartoon-style Toon Text animations. It wraps each character in a span with the class toon-char and aria-hidden set to true, so screen readers skip the pieces, then copies the original text onto the element as an aria-label. Lines separated by line breaks get their own toon-line wrappers, which makes per-line staggers easy.
It is a good pick when you want bouncy, letter-level motion on a playful brand and you care about the accessible name. Our Bouncing Letters Text Animation below uses a similar pattern in pure CSS: an aria-label on the wrapper, one span per letter, and each keyframe with its own easing so the fall speeds up like gravity.
Watch out for: Roselli's point applies here too: aria-label is not allowed on a plain div, so put the split on a heading or another element that can be named. The post does not state a license, so check before using it in client work.
4. Anime.js splitText(): Best for pages already built on Anime.js timelines
Platform: Anime.js v4, JavaScript
Anime.js added a splitText() utility in version 4.1.0, described in its docs as a lightweight, responsive and accessible text utility for splitting, cloning and wrapping text. You choose lines, words or chars, and settings like accessible and includeSpaces are built in. The docs example wraps words with a clip, which gives you masked word reveals without extra markup. Since 4.2.0 you can import it alone from animejs/text.
If your page already uses Anime.js for other motion, this keeps text on the same timeline instead of adding a second library. Our Word by Word Text Animation below is the CSS-only version of a clipped word reveal: each word slides up out of its own overflow-hidden slot, tilted slightly.
Watch out for: Version 4 changed the API, and most older tutorials and CodePens use version 3 syntax. Copy examples from the v4 docs, not a 2019 blog post.
5. Motion Primitives Text Effect: Best for React apps already using Motion and Tailwind
Platform: React + Motion + Tailwind, MIT
Motion Primitives, by ibelick, is a set of copy-in React components built with Motion and Tailwind CSS. Its Text Effect component takes a preset (fade, slide, scale, blur-sm or fade-in-blur) and a per setting of word, char or line. The default is a fade per word, which is the right default: it reads as one gentle arrival, not a typewriter.
This is the low-effort route for a dashboard empty state or a landing page heading in a React codebase. Our Letter by Letter Blur In Text below is a pure-CSS take on the blur preset, with long overlaps between letters so a soft wave of focus travels across the word.
Watch out for: Blur is one of the more expensive things to animate, and per-character blur on a long paragraph multiplies it. Keep blur presets to short headings and test on a mid-range phone.
6. React Bits by David Haz: Best for React side projects that want bold text fast
Platform: React (JS or TS, CSS or Tailwind), MIT + Commons Clause
React Bits is a large animated component collection with around 51,000 GitHub stars at the time of writing. Its Text Animations category holds 33 components, covering split text, typewriters, rotating words and scroll reveals, plus showier pieces like Circular Text, Glitch Text and Shuffle. Every component comes in four variants, JavaScript or TypeScript with plain CSS or Tailwind, and installs through the shadcn CLI.
It suits portfolios, hackathon projects and launch pages where personality matters more than restraint. Our Rotating Circular Text below is a pure-CSS version of the circular badge idea: SVG textPath with textLength, so the phrase always closes the circle.
Watch out for: The license is MIT plus Commons Clause, which bars selling the software itself, so read it before bundling components into a paid template or kit. Dependencies differ per component; check each one before you install.
7. GSAP ScrambleTextPlugin: Best for decode effects for security and dev tool brands
Platform: GSAP plugin, JavaScript, free
ScrambleText swaps an element's text for random characters, then reveals the real string, like a terminal decoding a message. You pick the character set (upper case, lower case, both, or your own string), how often the noise refreshes with speed, how long the full scramble holds with revealDelay, and whether a length change tweens gradually with tweenLength.
It works best on a short label or a number that changes, such as a status word or a stat in a hero. Our Decrypt Text Effect below is a CSS-only version: each character's pseudo-element spins through symbols as an animated content value, then locks onto the real letter with a flash, left to right.
Watch out for: Scrambled characters are noise if a screen reader catches them mid-change, so keep the real text as the accessible name and run the effect once, briefly. On a paragraph it just reads as broken.
8. Rough Notation: Best for pointing at one phrase in long-form copy
Platform: JavaScript, MIT, 3.8kb gzipped
Rough Notation draws hand-drawn annotations onto a page: underline, box, circle, highlight, strike-through, crossed-off and brackets. It handles inline text that wraps across lines, and if you pass a list of annotations as a group they animate in order when you call show(). Animation is on by default with an 800ms duration, and you can change it or turn it off.
This is emphasis rather than decoration, which is why it ages well. It suits pricing pages, docs and essays where one claim matters most. Our Hand-Drawn Circle Around Text below is the pure-CSS version for a single word: one SVG path with pathLength set to 1, so the dash math is a single number, and it overshoots its start like a real pen.
Watch out for: Annotations draw when show() runs, so trigger them as the element scrolls into view; fire them on page load and readers below the fold miss the moment.
9. Chris Coyier's scroll highlight: Best for highlighting key lines as the reader scrolls
Platform: Pure CSS, scroll-driven animation
Chris Coyier wrote up a no-JavaScript version of a highlight he saw on Lene Saile's blog, where a line lights up as you scroll to it. The trick: a mark element gets a linear-gradient background instead of a background colour, so background-size can animate from 0 to 100% width. The keyframes run on animation-timeline: view(), and animation-range: contain 0% contain 25% controls when the sweep starts and ends.
It is a lovely fit for case studies and long articles, because it ties emphasis to reading position. Our Marker Highlight Text below plays on a timer, not on scroll, but it shows the ink-swipe look; move its keyframes onto a view() timeline to make it scroll-linked. For more scroll patterns see our scroll animation examples.
Watch out for: Scroll-driven animations shipped in Chrome and Edge 115, Safari 26 and Firefox 159 (October 2026), so readers on older browsers still lack them. Wrap the rule in @supports (animation-timeline: view()) and make sure the fallback shows the highlight already drawn.
10. Ryan Mulligan's CSS marquee: Best for logo strips and scrolling taglines
Platform: Pure CSS
Ryan Mulligan's 2022 write-up is still one of the clearest marquee recipes. A second copy of the content sits beside the first with aria-hidden set to true, so screen readers skip the duplicate. A keyframe moves the content to translateX of calc(-100% - var(--gap)), using the same --gap custom property that spaces the items, which keeps the loop seamless.
A marquee shows a lot of short text, client names or tags, in little space, which is why agency and SaaS sites use them for logo strips. Our Marquee That Pauses on Hover below uses the same duplicate-group structure and adds one line, animation-play-state: paused on hover, so any pill can be read or clicked.
Watch out for: WCAG 2.2.2 asks for a way to pause moving content that runs longer than five seconds next to other content. Hover pausing does not help keyboard or touch users, and Mulligan advises turning auto-scroll off entirely under reduced motion.
11. Mandy Michael's variable font animations: Best for type-led brands with a variable font
Platform: CSS + variable fonts (some demos add JavaScript)
Mandy Michael's 24 ways article is the best introduction to animating the font itself. Her Decovar demo animates the inline and skeleton worm axes with a keyframe that runs 4 seconds, alternating forever. Another demo shifts the Cheee font's temperature axis under prefers-color-scheme: dark, and a third maps viewport width to a weight between 200 and 900 through a custom property. As she puts it, the heavy lifting is done by the font.
The upside is real text, selectable and searchable, with no SVG or video. Our Font Weight Wave Text below rolls a wave of boldness through the letters. It animates font-weight, which is smooth with a variable system font and steps on older fonts.
Watch out for: Changing weight or width changes glyph widths, so the line reflows on every frame. Keep it to short display text, and remember her own warning that variable fonts still need a web font performance strategy.
12. Josh W. Comeau's animated sparkles: Best for flagging something new or loved
Platform: React tutorial
Josh Comeau's sparkles tutorial wraps a word in small four-pointed stars that appear at random, every 50 to 450ms in his final code, each living about 750ms while it scales and rotates. He uses it for something that is new and shiny, or something that has captured his affection. The detail worth stealing is the reduced-motion handling: when the user prefers reduced motion, the interval stops and three static sparkles remain.
Our Sparkle Text Effect below is a CSS-only cousin: six clip-path stars with fixed positions and negative delays over a gradient word. You lose the randomness and gain zero JavaScript.
Watch out for: It is a tutorial, not a package, so you maintain the code. Constant twinkling next to text pulls the eye, which is the point; use it on one word per page, not every badge.
13. Our Rotating Words with Animated Underline: Best for hero headlines that speak to several audiences
Platform: Motions directory, free Ours
The rotating-word headline ("Hire top designers, engineers, writers") is everywhere on SaaS and marketplace sites because it lets one hero speak to several buyers. In this one each word rises into place, an underline draws in beneath it, and before the swap the line retracts to the right. The underline is the word's own ::after, so it always fits the word.
It is plain HTML and CSS with a reduced-motion guard and two custom properties for colour and size. The directory holds dozens of variants if you want a different personality: Split Flap Rotating Text, Slot Machine Rotating Words and Blur Rotating Text among them.
Watch out for: All the words sit in the DOM, so a screen reader reads them as one run-on line. Add a visually hidden version of the full sentence and hide the rotating list from assistive tech.
14. Our Kinetic Typography Text: Best for a looping title card for a launch or reel
Platform: Motions directory, free Ours
Kinetic typography is text that performs: words arrive from different directions, the camera drifts, the block spins away. This snippet does that in a browser with four timed keyframe tracks and no video file, so it stays sharp at any size and you can change the words in the HTML.
Use it for a launch page title card, an event countdown or the first frame of a reel. If you need a full sequence rather than a three-word loop, our kinetic typography examples and the Kinetic Typography with AI post go further, and the Animation Studio choreographs whole scenes and exports to MP4 or GIF.
Watch out for: Like most split-text demos it names a div with aria-label, which some screen readers ignore. On a real page put it on a heading or add a visually hidden copy, and never loop it behind body text.
How to choose a text animation
Three questions settle almost every case.
Match it to the job
A reveal introduces a headline once (Line Mask Reveal, SplitText, Anime.js splitText). Emphasis points at one phrase in copy people are already reading (Rough Notation, Coyier's scroll highlight, a marker swipe). Ambient motion runs on its own (marquees, sparkles, rotating words) and should be the rarest of the three, because it competes with everything else on the page.
Match it to your stack
If the effect plays once on a heading you control, pure CSS is enough: copy a snippet from the Text Animations directory and edit the words. Reach for GSAP when the text must re-split responsively or sync with scroll and other motion. In React, Motion Primitives and React Bits save time, at the cost of a dependency and a license to read.
Match it to the reader
Split by words or lines before you split by letters, and test the result with a real screen reader, because aria-label on a div is not reliable. Honour prefers-reduced-motion by showing the final state, not a slower version. Anything that moves for more than five seconds needs a pause control. Every snippet in our directory ships with the reduced-motion guard already written.
Pick one phrase and animate it today
Pick the single sentence on your page that matters most and give it one of the effects above: a masked reveal for the headline, a marker swipe for the claim, nothing for the rest. Copy the snippet, change the words, check it with reduced motion turned on, and ship.
If none of these fits your brand, describe the effect you want or paste your own heading markup into our creator. It asks a few quick questions, builds the CSS keyframes in front of you, and lets you refine it in chat.
Animate my hero headline "Ship calmer software" with a line-by-line reveal. Each line slides up 0.6em out of a clipping mask over 600ms with cubic-bezier(0.2, 0.7, 0.2, 1), staggered 90ms. Split by lines only, keep the real text readable by screen readers, and play once on load. Under prefers-reduced-motion, show the final text immediately with no movement. Pure HTML and CSS, colour and size as custom properties.
Common questions
How do I make a text animation with only CSS?
Wrap each word or letter in a span, give each span its index as a custom property (for example --i: 3), and set animation-delay to calc(var(--i) * 40ms) on a single keyframe. For line reveals, wrap each line in an element with overflow: hidden and slide the inner span up. Our Letters Rise and Line Mask Reveal snippets show both patterns.
Are text animations bad for accessibility?
They can be. Splitting words into single letters can make screen readers spell them out or skip them, as Adrian Roselli's 2026 tests showed. Prefer word or line splits, keep the full text available, honour prefers-reduced-motion by showing the end state, and give looping text a way to pause under WCAG 2.2.2.
Is GSAP SplitText free?
Yes. GSAP's pricing page says the whole library is free, including SplitText, ScrambleText and ScrollTrigger, with Webflow supporting the project. SplitText was rewritten in v3.13.0 to be half the size, with masking and automatic re-splitting added.
How long should a text animation take?
For interface text, a reveal that finishes within about a second feels responsive; long staggers on a 12-word heading leave people waiting to read. Decorative loops can be slower but should be calm. Our animation duration guide covers timing in more depth.
What is the difference between a text reveal and kinetic typography?
A text reveal is how text arrives on a page, once, so people can read it. Kinetic typography is text as the performance: words move, scale and swap in a timed sequence, usually in video or a title card. See our text reveal examples and kinetic typography examples.
Sources
- GSAP SplitText docs
- GSAP pricing
- GSAP ScrambleTextPlugin docs
- Adrian Roselli, You Know What? Just Don't Split Words into Letters
- Splitting.js guide
- Andy Clarke, Splinter.js
- Anime.js splitText docs
- Motion Primitives Text Effect
- React Bits on GitHub
- Rough Notation on GitHub
- Chris Coyier, Highlight Text When a User Scrolls Down to That Piece of Text
- Ryan Mulligan, CSS marquee write-up
- Mandy Michael, Interactivity and Animation with Variable Fonts
- Josh W. Comeau, Animated Sparkles in React
- MDN: animation-timeline
- Firefox 159 release notes
- Can I use: animation-timeline