Skip to content

Table

Data table component with sorting, selection, and responsive stacking.

Demo

Default

Medarbejdere
RolleStatus
Alice JensenDesigneractive42000
Bob NielsenDeveloperactive48000
Carol SørensenManagerinactive55000
Dan ChristensenDeveloperactive46000

Borderless

Medarbejdere (borderless)
RolleStatus
Alice JensenDesigneractive42000
Bob NielsenDeveloperactive48000
Carol SørensenManagerinactive55000
Dan ChristensenDeveloperactive46000

Zebra

Medarbejdere (zebra)
RolleStatus
Alice JensenDesigneractive42000
Bob NielsenDeveloperactive48000
Carol SørensenManagerinactive55000
Dan ChristensenDeveloperactive46000

Compact

Medarbejdere (compact)
RolleStatus
Alice JensenDesigneractive42000
Bob NielsenDeveloperactive48000
Carol SørensenManagerinactive55000
Dan ChristensenDeveloperactive46000

Sortable (interactive)

Sortable table
RolleStatus
Alice JensenDesigneractive42000
Bob NielsenDeveloperactive48000
Carol SørensenManagerinactive55000
Dan ChristensenDeveloperactive46000

Selectable (interactive)

Selectable table
RolleStatus
Alice JensenDesigneractive42000
Bob NielsenDeveloperactive48000
Carol SørensenManagerinactive55000
Dan ChristensenDeveloperactive46000

Valgte: 0 rækker

Custom cell slot with Badge

Custom cell demo
RolleStatus
Alice JensenDesignerAktiv42.000 kr
Bob NielsenDeveloperAktiv48.000 kr
Carol SørensenManagerInaktiv55.000 kr
Dan ChristensenDeveloperAktiv46.000 kr

Props

PropTypeDefaultDescription
columnsTableColumn[]Column definitions (required)
rowsRecord<string, unknown>[]Row data (required)
variant'default' | 'borderless' | 'zebra''default'Visual variant
density'normal' | 'compact' | 'extra-compact''normal'Row density
responsivebooleanfalseStack rows on mobile
selectablebooleanfalseShow checkbox column
modelValuenumber[][]Selected row indices (v-model)
captionstringTable caption for accessibility
captionVisiblebooleanfalseShow caption visually
sortBystringControlled sort column (v-model:sortBy)
sortDirection'asc' | 'desc'Controlled sort direction (v-model:sortDirection)
stripedbooleanfalseShorthand for variant="zebra"

TableColumn

PropertyTypeDescription
keystringData property key
labelstringColumn header text
numericbooleanRight-align and use tabular-nums
sortablebooleanEnable sorting on this column
widthstringFixed CSS width

Events

EventPayloadDescription
update:modelValuenumber[]Selected row indices changed
update:sortBystringSort column changed
update:sortDirection'asc' | 'desc'Sort direction changed

Slots

SlotPropsDescription
#cell-{key}{ row, value }Custom cell content for a column

Example: Custom cell with Badge

vue
<GTTable :columns="columns" :rows="rows">
  <template #cell-status="{ value }">
    <GTBadge :variant="value === 'active' ? 'success' : 'neutral'" size="sm" dot>
      {{ value }}
    </GTBadge>
  </template>
</GTTable>

Usage

Basic

vue
<script setup>
import { GTTable } from '@grundtone/vue';

const columns = [
  { key: 'name', label: 'Name', sortable: true },
  { key: 'role', label: 'Role' },
  { key: 'salary', label: 'Salary', numeric: true, sortable: true },
];

const rows = [
  { name: 'Alice', role: 'Designer', salary: 42000 },
  { name: 'Bob', role: 'Developer', salary: 48000 },
];
</script>

<template>
  <GTTable :columns="columns" :rows="rows" caption="Team members" />
</template>

Selectable with v-model

vue
<script setup>
import { ref } from 'vue';
import { GTTable } from '@grundtone/vue';

const selected = ref<number[]>([]);
</script>

<template>
  <GTTable
    v-model="selected"
    :columns="columns"
    :rows="rows"
    selectable
  />
  <p>{{ selected.length }} selected</p>
</template>

CSS classes

See Design System Table reference for all available CSS classes and variants.