---
title: "VersionCapsule"
description: "A split release pill: download on the left, history on the right."
category: Advanced
status: beta
since: 0.3.9
tags: [version, release, download, history]
syncStatus: reviewed
verified: true
---

## Usage

### Download and History
The `download` and `history` slots hold the two panels; their `close` slot prop closes the panel and returns focus.
:::TuffDemoWrapper{demo="VersionCapsuleVersionCapsuleDemo" code-lang="vue"}
---
code: |
  <script setup lang="ts">
  import { ref } from 'vue'

  const panel = ref<'download' | 'history' | null>('download')
  const notice = { tone: 'warning', title: 'Preview channel build', points: ['Features may change without notice'] }
  const builds = [
    { id: 'mac-arm', name: 'macOS · Apple silicon', meta: '.dmg · 126 MB', href: '#mac-arm', recommended: true },
    { id: 'win', name: 'Windows · x64', meta: '.exe · 118 MB', href: '#win' },
  ]
  const latest = { id: '1', tag: 'v2.4.13-beta.19', channel: 'BETA', tone: 'preview', date: 'Jul 21', note: 'Icon self-healing' }
  const entries = [{ id: '2', tag: 'v2.4.12', channel: 'RELEASE', tone: 'stable', date: 'Jul 12', href: '#v2412' }]
  </script>

  <template>
    <TxVersionCapsule v-model:panel="panel" version="v2.4.13-beta.19" channel="BETA" tone="preview">
      <template #download="{ close }">
        <TxVersionDownloadPanel :notice="notice" :builds="builds" @select="close" />
      </template>
      <template #history="{ close }">
        <TxVersionHistoryPanel :latest="latest" :entries="entries" count-label="6 releases" @select="close" />
      </template>
    </TxVersionCapsule>
  </template>
---
:::

### Channel Tones
`tone` sets the status dot and channel color.
:::TuffDemoWrapper{demo="VersionCapsuleChannelTonesDemo" code-lang="vue"}
---
code: |
  <script setup lang="ts">
  const capsules = [
    { tone: 'stable', version: 'v2.4.12', channel: 'STABLE' },
    { tone: 'preview', version: 'v2.4.13-beta.19', channel: 'BETA' },
    { tone: 'nightly', version: 'v2.4.14-nightly.5', channel: 'NIGHTLY' },
    { tone: 'neutral', version: 'v1.9.8', channel: 'ARCHIVED' },
  ]
  </script>

  <template>
    <TxVersionCapsule
      v-for="item in capsules"
      :key="item.tone"
      :version="item.version"
      :channel="item.channel"
      :tone="item.tone"
      history-label="History"
    >
      <template #history="{ close }">
        <TxVersionHistoryPanel :latest="{ id: item.tone, tag: item.version, channel: item.channel, tone: item.tone }" @select="close" />
      </template>
    </TxVersionCapsule>
  </template>
---
:::

### Best Practices

- Always name the channel (`BETA`, `STABLE`, `NIGHTLY`), never "LATEST"; pair the capsule with the page's stable download button instead of replacing it.
- Put pre-release caveats in the download panel's `notice` (`warning`); use `success` for certified builds.
- Give builds an `href` so they download directly as `<a download>`; omit it only when the URL is resolved on `select`.
- Mark only the visitor's platform build `recommended`.
- Match each history entry's `tone` to its channel, and use `note` only on `latest`.

## API Reference

### TxVersionCapsule

#### Props

| Prop | Type | Default | Description |
|------|------|---------|------|
| `version` | `string` | — (required) | Version tag shown as the headline, e.g. `v2.4.13-beta.19`. |
| `channel` | `string` | - | Channel label beside the status dot, e.g. `BETA`; hidden when unset. |
| `tone` | `TxVersionChannelTone` | `'preview'` | Color of the dot and channel label. |
| `historyLabel` | `string` | `'History'` | Text of the right segment. |
| `downloadLabel` | `string` | `'Download this build'` | Accessible name of the left segment. |
| `panel` | `TxVersionCapsulePanel` | - | Controlled open panel, for `v-model:panel`; omit for uncontrolled. |
| `disabled` | `boolean` | `false` | Disables both segments and closes any open panel. |
| `closeOnClickOutside` | `boolean` | `true` | Closes the panel on an outside `pointerdown`. |
| `closeOnEsc` | `boolean` | `true` | Closes the panel on Escape. |

#### Events

| Event | Params | Description |
|------|------|------|
| `update:panel` | `(value: TxVersionCapsulePanel)` | Fires when the open panel changes. |
| `download` | - | Fires when the left segment is activated. |
| `history` | - | Fires when the right segment is activated. |

#### Slots

| Slot | Props | Description |
|------|-------|-------------|
| `download` | `{ close: () => void }` | Download panel content, anchored under the left segment. |
| `history` | `{ close: () => void }` | History panel content, anchored under the right segment. |

#### Exposed Methods

| Member | Type | Description |
|------|------|------|
| `close` | `() => void` | Closes the panel and returns focus to its segment; also passed to both slots. |
| `downloadRef` | `Ref<HTMLButtonElement \| null>` | The left segment's button element. |
| `historyRef` | `Ref<HTMLButtonElement \| null>` | The right segment's button element. |

### TxVersionDownloadPanel

#### Props

| Prop | Type | Default | Description |
|------|------|---------|------|
| `notice` | `TxVersionNotice` | - | Trust block above the builds; omit to show builds only. |
| `builds` | `TxVersionBuild[]` | `[]` | Builds per platform. |
| `buildsLabel` | `string` | `'Choose a build'` | Overline above the build list. |
| `downloadLabel` | `string` | `'Download'` | Text on the recommended build's button. |
| `emptyText` | `string` | `'No builds published yet.'` | Shown when `builds` is empty. |

#### Events

| Event | Params | Description |
|------|------|------|
| `select` | `(id: string)` | Fires with the build's `id` when a build is chosen. |

#### Slots

| Slot | Props | Description |
|------|-------|-------------|
| `footer` | - | Footer below the build list. |

### TxVersionHistoryPanel

#### Props

| Prop | Type | Default | Description |
|------|------|---------|------|
| `title` | `string` | `'Version history'` | Panel heading. |
| `latest` | `TxVersionHistoryEntry` | - | Featured card above the list. |
| `entries` | `TxVersionHistoryEntry[]` | `[]` | Release rows below the featured card. |
| `latestLabel` | `string` | `'LATEST'` | Badge on the featured card. |
| `countLabel` | `string` | - | Right side of the header, e.g. `6 releases`. |
| `notesLabel` | `string` | `"What's new"` | Call to action on the featured card. |
| `emptyText` | `string` | `'No releases published yet.'` | Shown when there is neither `latest` nor any `entries`. |

#### Events

| Event | Params | Description |
|------|------|------|
| `select` | `(entry: TxVersionHistoryEntry)` | Fires when a release row or the featured card is chosen. |

#### Slots

| Slot | Props | Description |
|------|-------|-------------|
| `footer` | - | Footer below the release list. |

### Types

`TxVersionChannelTone` is `'stable' \| 'preview' \| 'nightly' \| 'neutral'`, mapped to `success` / `primary` (default) / `warning` / `secondary` colors.

#### TxVersionBuild

| Field | Type | Description |
|------|------|------|
| `id` | `string` | List key. |
| `name` | `string` | Headline, e.g. `macOS · Apple silicon`. |
| `meta` | `string?` | Secondary line, e.g. `.dmg · 126 MB`. |
| `href` | `string?` | Direct URL; renders the row as `<a download>`, otherwise a `<button>`. |
| `recommended` | `boolean?` | The visitor's platform build; only the first gets the highlight and labelled button. |
| `icon` | `string?` | Icon class before the name; the consumer supplies the icon set. |

#### TxVersionNotice

| Field | Type | Description |
|------|------|------|
| `tone` | `'warning' \| 'success'` | `warning` (default) for pre-release caveats, `success` for certified builds. |
| `title` | `string` | Notice headline. |
| `description` | `string?` | Supporting sentence. |
| `points` | `string[]?` | Bulleted caveats. |

#### TxVersionHistoryEntry

| Field | Type | Description |
|------|------|------|
| `id` | `string` | List key. |
| `tag` | `string` | Version tag. |
| `channel` | `string?` | Channel label, e.g. `BETA`. |
| `tone` | `TxVersionChannelTone?` | Tone of this row; defaults to `preview`. |
| `date` | `string?` | Release date text. |
| `note` | `string?` | One-line changelog, rendered only on `latest`. |
| `href` | `string?` | Renders the row or card as a link. |

## Overview

- The two segments are independent click targets: the left downloads the build, the right opens history. Don't wrap the whole capsule in one action.
- One panel is open at a time; clicking the other segment swaps panels, and clicking the active one closes it.
- Panels anchor under their own segment (download left-aligned, history right-aligned) and are not modal.
- `panel` left `undefined` means uncontrolled; `null` is the controlled "all closed" value.
- Without a slot, its segment only emits its event and opens nothing — useful when the host has its own dialog.

## Technologies

- Source: `packages/tuffex/packages/components/src/version-capsule/`.

<TuffDocSourceLink />
