# ScrollArea

A scrolling region with a thin themed native scrollbar, for panels, menus, side lists and code blocks of fixed height. Native scrolling and the native scrollbar stay; only its color and width are styled (scrollbar-width thin, scrollbar-color). No custom drawn thumb. The page itself keeps the browser scrollbar.

## Cách dùng

### Khi nào dùng

- Keep a long list, panel or code block inside a fixed or maximum height while the page stays still.
- Give a scrollable region a thin native scrollbar that follows the current theme.

### Khi nào không dùng

- The whole page should scroll with its content.
- A list is too long to scan and needs search. Use Combobox.

## Biến thể

### orientation

Which axes scroll.

Giá trị: `vertical`, `horizontal`, `both`. Mặc định: `vertical`.

### type

auto shows the native scrollbar when content overflows; always reserves its space (scrollbar-gutter stable) so content does not shift.

Giá trị: `auto`, `always`. Mặc định: `auto`.

## Ví dụ

### Recent activity

```tsx
<ScrollArea className="h-48 w-64 max-w-full rounded-container border border-border" label="Recent activity">
  <div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 01</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 02</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 03</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 04</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 05</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 06</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 07</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 08</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
  </div>
</ScrollArea>
```

### Horizontal projects

```tsx
<ScrollArea orientation="horizontal" className="h-40 w-64 max-w-full rounded-container border border-border" label="Projects">
  <div className="flex gap-md p-md">
    <Card className="w-40 shrink-0">
      <CardContent>Website</CardContent>
    </Card>
    <Card className="w-40 shrink-0">
      <CardContent>Mobile app</CardContent>
    </Card>
    <Card className="w-40 shrink-0">
      <CardContent>Documentation</CardContent>
    </Card>
  </div>
</ScrollArea>
```

### Both axes

```tsx
<ScrollArea orientation="both" className="h-48 w-64 max-w-full rounded-container border border-border" label="Project updates">
  <div className="w-160">
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 01</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 02</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 03</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 04</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 05</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 06</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 07</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 08</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
  </div>
</ScrollArea>
```

### Reserved scrollbar space

```tsx
<ScrollArea type="always" className="max-h-48 w-64 max-w-full rounded-container border border-border" label="All projects">
  <div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 01</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 02</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 03</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 04</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 05</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 06</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 07</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
    <div className="border-b border-border px-md py-md">
      <p className="text-sm font-medium">Project 08</p>
      <p className="text-xs text-text-secondary">Updated workspace notes</p>
    </div>
  </div>
</ScrollArea>
```

## Nên và không nên

### Nên

- Give the root a height or max height.
- Use in DropdownMenu or Combobox lists only if they need a themed bar; they already scroll natively.
- Provide enough content to overflow the chosen axis. Horizontal content needs a width greater than the viewport and must not shrink.

### Không nên

- Do not wrap the whole page.
- Do not hide the scrollbar on content that the user must know scrolls without another cue.

## Props

| Tên | Kiểu | Giá trị | Mặc định | Mô tả |
| --- | --- | --- | --- | --- |
| `orientation` | `enum` | `vertical`, `horizontal`, `both` | `vertical` | Which axes scroll. |
| `type` | `enum` | `auto`, `always` | `auto` | auto shows the native scrollbar when content overflows; always reserves its space (scrollbar-gutter stable) so content does not shift. |
| `label` | `string` |  |  | Accessible name for the region when the viewport is focusable. |
| `tabIndex` | `number` |  |  | On the viewport: override automatic tab order. By default it takes focus only when it has no visible, enabled focusable children. |
| `onScroll` | `React.UIEventHandler<HTMLDivElement>` |  |  | On the viewport: native scroll event handler. |
| `style` | `React.CSSProperties` |  |  | On the viewport: inline styles for the native scrolling element. Set the outer dimensions with className. |
| `className` | `string` |  |  | On the outer box: supply height, max height, width, borders and corners. The viewport fills this box. |

### Slot

| Tên | Bắt buộc | Mô tả |
| --- | --- | --- |
| `children` | có | The content that scrolls. |

## Cấu tạo

| Phần | Mô tả |
| --- | --- |
| `root` | Outer box with a fixed or max height. |
| `viewport` | The scrolling element with overflow auto and the styled native scrollbar. |

## Khả năng truy cập

Role: `region`

| Phím | Hành động |
| --- | --- |
| `Tab` | Focuses the viewport when it has no focusable children, so keyboard users can scroll. |
| `Arrow keys / PageUp / PageDown / Home / End` | Native scrolling on the enabled axes of the focused viewport. |

- Native scrolling stays: wheel, touch, momentum and find-in-page work.
- Pass aria-label when the viewport is focusable so the region has a name.
- Under reduced motion no smooth scrolling is added.
- The scrollbar is the browser's own, so it keeps its platform behavior (overlay scrollbars on touch, dragging, clicking the track).

## Cài đặt

```bash
npx werewolf-ui add scroll-area
```

Chạy `npx werewolf-ui init` một lần trong app trước khi thêm component. Init cài token, thêm CSS import và luật cho agent. Add cài component này cùng các dependency và giữ nguyên theme của bạn. Xem [Cài đặt](https://werewolf-ui.vercel.app/vi/docs/installation.md) để biết yêu cầu và cách cài qua registry.
