Hover Scroll Text
Truncated single-line text that scrolls horizontally on hover to reveal the full string.
Examples
Basic
Row trigger
Custom speed
Overview
HoverScrollText renders a single line of text that truncates with an ellipsis at rest. When the
text overflows its container, hovering it slowly scrolls the line to its end, holds, and sweeps
back, with fading edges masking whichever side is clipped. Leaving mid-scroll smoothly returns
the text to the start and restores the ellipsis. Text that fits does nothing.
import { HoverScrollText } from "@rogo-technologies/ui/hover-scroll-text";
<HoverScrollText>{project.name}</HoverScrollText>;Use it for user-generated names in constrained layouts (sidebar items, table cells, panel headers) where a tooltip alone is a poor way to read the full string.
Usage
Row trigger
By default the text scrolls when the pointer is over the text itself. For list rows, spread
hoverScrollTextTriggerProps on the row so hovering anywhere in the row drives the scroll:
import {
HoverScrollText,
hoverScrollTextTriggerProps,
} from "@rogo-technologies/ui/hover-scroll-text";
<div {...hoverScrollTextTriggerProps} className="flex items-center gap-1.5">
<IconFolder1 className="size-4 shrink-0" />
<HoverScrollText>{project.name}</HoverScrollText>
</div>;The component finds the nearest ancestor carrying the trigger attribute; without one it falls back to its own hover.
In flex layouts
The root is a block span with min-w-0 baked in, so it shrinks correctly as a flex item. Put
text styling on the component itself:
<HoverScrollText className="text-secondary type-small-strong">{project.name}</HoverScrollText>Custom speed
speed is the scroll speed in pixels per second (default 40). Duration scales with how far
the text overflows, clamped between 0.6s and 6s per sweep.
Accessibility
- Honors
prefers-reduced-motion: the text stays truncated with an ellipsis and never scrolls. - The full string is always present in the DOM, so screen readers announce it regardless of truncation or scroll state.
API
HoverScrollText
| Prop | Type | Default | Description |
|---|---|---|---|
children | ReactNode | — | Single-line content to truncate and scroll. |
speed | number | 40 | Scroll speed in pixels per second. |
className | string | — | Additional classes: text styles, flex sizing, etc. |
Any other <span> attributes pass through to the root element.
hoverScrollTextTriggerProps
Spreadable props object (data-hover-scroll-text-trigger) marking an ancestor as the hover
target that drives the scroll.
Guidelines
Do
- Use for user-generated, unbounded strings in constrained UI (project names, file names)
- Keep it to one scrolling title per row: the row trigger scrolls every instance inside it
Don't
- Don't use for multi-line or wrapping text; it's strictly single-line
- Don't use it as a marquee for decorative or attention-seeking motion; it's a reveal interaction, not an animation effect
- Don't nest interactive elements inside; children should be plain text or inline content. A block-level child defeats the resting ellipsis (MDX wraps multi-line JSX text in a paragraph, so pass titles from a client component, not inline MDX)