<script setup lang="ts">
import { AScrollAreaRoot, AScrollAreaScrollbar, AScrollAreaThumb, AScrollAreaViewport } from 'akar';
const tags = Array.from({ length: 50 }).map((_, i, a) => `v1.2.0-beta.${a.length - i}`);
</script>
<template>
<AScrollAreaRoot
class="border border-border rounded-lg bg-background h-[225px] w-[200px] shadow-sm relative overflow-hidden"
style="--scrollbar-size: 10px"
>
<div class="h-6 w-full top-0 absolute z-10 from-transparent to-white bg-gradient-to-t" />
<AScrollAreaViewport class="rounded h-full w-full">
<div class="px-5 py-[15px]">
<div class="text-sm color-primary leading-[18px] font-semibold">
Tags
</div>
<div
v-for="tag in tags"
:key="tag"
class="text-xs leading-[18px] mt-2.5 pt-2.5 border-t border-t-border"
>
{{ tag }}
</div>
</div>
</AScrollAreaViewport>
<AScrollAreaScrollbar
class="p-0.5 bg-background-elevated flex select-none transition-colors duration-[160ms] ease-out z-20 touch-none hover:bg-background-accented data-[orientation=horizontal]:flex-col data-[orientation=horizontal]:h-2.5 data-[orientation=vertical]:w-2.5"
orientation="vertical"
>
<AScrollAreaThumb
class="rounded-[10px] bg-primary flex-1 relative before:(h-full min-h-[44px] min-w-[44px] w-full content-empty left-1/2 top-1/2 absolute -translate-x-1/2 -translate-y-1/2)"
/>
</AScrollAreaScrollbar>
<AScrollAreaScrollbar
class="p-0.5 bg-background-elevated flex select-none transition-colors duration-[160ms] ease-out touch-none hover:bg-background-accented data-[orientation=horizontal]:flex-col data-[orientation=horizontal]:h-2.5 data-[orientation=vertical]:w-2.5"
orientation="horizontal"
>
<AScrollAreaThumb
class="rounded-[10px] bg-primary flex-1 relative before:(h-full min-h-[44px] min-w-[44px] w-full content-empty left-1/2 top-1/2 absolute -translate-x-1/2 -translate-y-1/2)"
/>
</AScrollAreaScrollbar>
<div class="h-6 w-full bottom-0 absolute z-10 from-transparent to-white bg-gradient-to-b" />
</AScrollAreaRoot>
</template>
Import all parts and piece them together.
<script setup>
import { AScrollAreaRoot, AScrollAreaScrollbar, AScrollAreaThumb, AScrollAreaViewport } from 'akar';
</script>
<template>
<AScrollAreaRoot>
<AScrollAreaViewport />
<AScrollAreaScrollbar orientation="horizontal">
<AScrollAreaThumb />
</AScrollAreaScrollbar>
<AScrollAreaScrollbar orientation="vertical">
<AScrollAreaThumb />
</AScrollAreaScrollbar>
<AScrollAreaCorner />
</AScrollAreaRoot>
</template>
Contains all the parts of a scroll area.
| Prop | Default | Type |
|---|---|---|
as | 'div' | APrimitiveAsTag | ComponentThe element or component this component should render as. Can be overwritten by |
asChild | booleanChange the default rendered element for the one passed as a child, merging their props and behavior. Read our Composition guide for more details. | |
dir | 'ltr' | 'rtl'The reading direction of the combobox when applicable. | |
scrollHideDelay | 600 | numberIf type is set to either |
type | 'hover' | 'always' | 'scroll' | 'hover' | 'auto'Describes the nature of scrollbar visibility, similar to how the scrollbar preferences in MacOS control visibility of native scrollbars.
|
The viewport area of the scroll area.
| Prop | Default | Type |
|---|---|---|
as | 'div' | APrimitiveAsTag | ComponentThe element or component this component should render as. Can be overwritten by |
asChild | booleanChange the default rendered element for the one passed as a child, merging their props and behavior. Read our Composition guide for more details. | |
nonce | stringWill add |
The vertical scrollbar. Add a second Scrollbar with an orientation prop to enable horizontal scrolling.
| Prop | Default | Type |
|---|---|---|
as | 'div' | APrimitiveAsTag | ComponentThe element or component this component should render as. Can be overwritten by |
asChild | booleanChange the default rendered element for the one passed as a child, merging their props and behavior. Read our Composition guide for more details. | |
forceMount | booleanUsed to force mounting when more control is needed. Useful when controlling animation with Vue animation libraries. | |
orientation | 'vertical' | 'horizontal' | 'vertical'The orientation of the scrollbar |
| Attribute | Value |
|---|---|
[data-orientation] | 'vertical' | 'horizontal' |
[data-state] | 'visible' | 'hidden' |
The thumb to be used in AScrollAreaScrollbar.
| Prop | Default | Type |
|---|---|---|
as | 'div' | APrimitiveAsTag | ComponentThe element or component this component should render as. Can be overwritten by |
asChild | booleanChange the default rendered element for the one passed as a child, merging their props and behavior. Read our Composition guide for more details. |
| Attribute | Value |
|---|---|
[data-state] | 'visible' | 'hidden' |
The corner where both vertical and horizontal scrollbars meet.
| Prop | Default | Type |
|---|---|---|
as | 'div' | APrimitiveAsTag | ComponentThe element or component this component should render as. Can be overwritten by |
asChild | booleanChange the default rendered element for the one passed as a child, merging their props and behavior. Read our Composition guide for more details. |
Use the exposed viewport to modify / or set the scroll position outside default methods
<script setup lang="ts">
import { AScrollAreaRoot, AScrollAreaScrollbar, AScrollAreaThumb, AScrollAreaViewport } from 'akar'
const scrollArea = useTemplateRef('scrollArea')
function scrollToBottom() {
const viewport = scrollArea.value?.viewport
if (viewport) {
const top = scrollArea.value?.$el.scrollHeight
container.scrollTo({
top,
behavior: 'smooth'
})
}
}
</script>
<template>
<AScrollAreaRoot ref="scrollArea">
<AScrollAreaViewport />
<AScrollAreaScrollbar orientation="horizontal">
<AScrollAreaThumb />
</AScrollAreaScrollbar>
<AScrollAreaScrollbar orientation="vertical">
<AScrollAreaThumb />
</AScrollAreaScrollbar>
<AScrollAreaCorner />
</AScrollAreaRoot>
</template>
In most cases, it's best to rely on native scrolling and work with the customization options available in CSS. When that isn't enough, AScrollArea provides additional customizability while maintaining the browser's native scroll behavior (as well as accessibility features, like keyboard scrolling).
Scrolling via keyboard is supported by default because the component relies on native scrolling. Specific keyboard interactions may differ between platforms, so we do not specify them here or add specific event listeners to handle scrolling via key events.