ScrollAreav1.0.6Documentation Under Review
A custom scrollbar component for product interfaces with customizable styling via className overrides. Supports vertical/horizontal scrolling, container queries, and brand theming.
The Product ScrollArea component provides a styled alternative to native scrollbars optimized for product/application experiences. Built on Radix UI with support for custom styling via className overrides, container queries, and brand-specific theming.
Installation
Install the ScrollArea component from the Catalyst component library:
npm install '@pmi/catalyst-scroll-area'Examples
Vertical Scrolling
Scroll vertically through content that exceeds container height.
Custom Brand Styling
Apply custom brand colors to scrollbar and viewport using className overrides.
Horizontal Scrolling
Scroll horizontally through wide content with horizontal scrollbar.
With Container Queries
Use CSS container queries within scroll area for responsive content.
API Reference
ScrollAreaRoot
The root container for the scroll area with overflow handling.
Prop
Type
Default Styles:
- Position:
relative overflow-hidden - Group:
group/scrollareafor hover states
ScrollAreaViewport
The scrollable viewport container for content.
Prop
Type
Default Styles:
- Size:
h-full w-full - Border:
border border-transparent rounded-lg - Focus:
focus-visible:ring-1 focus-visible:ring-pmi-off-black-800 - Padding:
p-0.5
Custom Styling Example:
<ScrollAreaViewport
className="focus-visible:ring-pmi-aqua-500 focus-visible:border-pmi-aqua-500"
>
{content}
</ScrollAreaViewport>ScrollAreaScrollbar
The scrollbar track that appears on hover or always.
Prop
Type
Default Styles:
- Layout:
flex shrink-0 touch-none select-none - Background:
group-hover/scrollarea:bg-pmi-neutral-100(on hover) - Vertical:
h-full w-2.5 p-0.5 - Horizontal:
h-2.5 flex-col p-0.5 - Transition:
transition-colors
Custom Styling Example:
<ScrollAreaScrollbar
className="group-hover/scrollarea:bg-neutral-200 dark:group-hover/scrollarea:bg-neutral-700"
>ScrollAreaThumb
The draggable thumb within the scrollbar.
Prop
Type
Default Styles:
- Shape:
relative flex-1 rounded-full - Background:
bg-pmi-neutral-500,dark:bg-pmi-neutral-300
Custom Styling Example:
<ScrollAreaThumb className="bg-neutral-500 dark:bg-neutral-400" />ScrollAreaCorner
The corner element where vertical and horizontal scrollbars meet.
Prop
Type
Design Tokens
The Product ScrollArea uses Tailwind design tokens with full customization support:
- Default Scrollbar Track:
- Hidden by default
bg-pmi-neutral-100(light) on hoverbg-pmi-neutral-800(dark) on hover- Width:
w-2.5(10px) vertical,h-2.5horizontal
- Default Thumb:
bg-pmi-neutral-500(light mode)bg-pmi-neutral-300(dark mode)- Shape:
rounded-full
- Default Viewport Focus:
- Ring:
focus-visible:ring-1 ring-pmi-off-black-800 - Border:
focus-visible:border-pmi-off-black-800
- Ring:
- Custom Colors: Any Tailwind color via className overrides
- Transitions:
transition-colorson scrollbar - Border Radius: Inherits from container (
rounded-[inherit])
Custom Styling Pattern
The Product variant supports extensive customization:
import { cn } from '@pmi/catalyst-utils'
// Custom scrollbar track
const customScrollbar = cn(
'group-hover/scrollarea:bg-neutral-200',
'dark:group-hover/scrollarea:bg-neutral-700'
)
// Custom viewport focus
const customViewport = cn(
'focus-visible:ring-pmi-aqua-500',
'focus-visible:border-pmi-aqua-500',
'dark:focus-visible:ring-pmi-aqua-500',
'dark:focus-visible:border-pmi-aqua-500'
)
// Custom thumb
const customThumb = cn(
'bg-neutral-500',
'dark:bg-neutral-400'
)
// Apply to scroll area
<ScrollAreaViewport className={customViewport}>
{content}
</ScrollAreaViewport>
<ScrollAreaScrollbar className={customScrollbar}>
<ScrollAreaThumb className={customThumb} />
</ScrollAreaScrollbar>Container Query Integration
Use CSS container queries for responsive content:
<ScrollAreaRoot className="h-[200px] w-full">
<ScrollAreaViewport>
<div className="@container/main">
<div className="@lg/main:bg-blue-100 p-4">
Content that changes at large container size
</div>
</div>
</ScrollAreaViewport>
<ScrollAreaScrollbar orientation="vertical">
<ScrollAreaThumb />
</ScrollAreaScrollbar>
</ScrollAreaRoot>Accessibility
The Product ScrollArea component follows WCAG 2.1 AA accessibility standards:
- Keyboard Navigation:
- Viewport is focusable with
tabIndex={0} - Arrow keys scroll content
- Page Up/Down for larger scrolls
- Home/End for start/end
- Viewport is focusable with
- Focus Indicators: Visible focus ring on viewport
- Touch Support:
touch-noneon scrollbar for proper touch handling- Native touch scrolling on viewport
- Screen Reader Support:
- Proper ARIA attributes from Radix UI
- Scrollable region announced
- Mouse Support:
- Click scrollbar track to jump
- Drag thumb to scroll
- Scroll wheel support
- RTL Support:
dirprop for right-to-left layouts - Color Contrast: Default colors meet 4.5:1 contrast ratio minimum
- Custom Theme Testing: Validate custom colors meet WCAG AA standards
Best Practices
- Always include ScrollAreaScrollbar with orientation
- Always include ScrollAreaThumb inside ScrollAreaScrollbar
- Include ScrollAreaCorner when using both orientations
- Set explicit height/width on ScrollAreaRoot
- Use
whitespace-nowrapfor horizontal scrolling text - Use
w-maxfor horizontal scrolling containers - Test keyboard navigation with Tab and arrow keys
- Ensure sufficient color contrast on custom themes
- Provide visual focus indicators
- Test with screen readers
- When using custom styles, verify color contrast meets WCAG AA (4.5:1)
- Test custom brand colors in both light and dark modes
- Use
@containerqueries for responsive scrollable content
Differences from Marketing ScrollArea
The Product ScrollArea variant differs from the Marketing ScrollArea in the following ways:
| Feature | Marketing | Product |
|---|---|---|
| Custom Styling | Standard theming | Full className override support |
| Use Case | Marketing pages, content areas | Product UIs, dashboards, data displays |
| Theming | Fixed PMI colors | Customizable brand colors |
| Examples | 3 standard | 4 including custom styling + container queries |
| Documentation | Basic implementation | Includes brand-specific patterns |
Related Components
- ScrollArea - Marketing-focused variant
- Sheet - Side panels that may use scroll areas
- Dialog - Modals that may contain scrollable content
- Popover - Popovers with scrollable content
- Table - Tables with scrollable content
See Also
- Radix UI ScrollArea - Underlying primitive
- WCAG Scrollable Regions - Accessibility guidelines
- Custom Scrollbar UX - Nielsen Norman Group
- Container Queries - Responsive content
- WCAG Color Contrast - Contrast requirements