Multi-sheet xlsx export

Live in demo 59-export-multi-sheet.

Open the live example: Export - Multiple sheets (Data Export & Import)

When

One workbook, multiple tabs - one per group / region / period.

How

Key API surface:

See the demo source for the full implementation; this recipe pins the pattern + the surface so you can copy-paste it confidently. The doc page that explains the underlying feature in depth is linked from the recipes index.

More examples

Workbook - multi-sheet + formulas

A real spreadsheet: A/B/C columns + many rows you can grow on demand, cross-sheet formulas (=SUM, =VLOOKUP, nested IF) recalculating live, cell + conditional formatting, validation dropdowns, an inline chart, a calendar/scheduler sheet, open .xlsx/.csv, and export every sheet to one multi-tab .xlsx.

Open the live example: Workbook - multi-sheet + formulas (Data Export & Import)

Exporting each group separately

A multi-sheet workbook is one export per slice of the data. Filtering the array and exporting each result is the portable version - it works with the CSV exporter in the free package, not just the XLSX one.

<script lang="ts">
  import { SvGrid, type GridColumns, type SvGridApi } from '@svgrid/grid'

  type Person = { id: number; name: string; department: string; salary: number }

  const people: Person[] = [
    { id: 1, name: 'Ada Lovelace',   department: 'Engineering', salary: 142000 },
    { id: 2, name: 'Grace Hopper',   department: 'Engineering', salary: 168000 },
    { id: 3, name: 'Linus Torvalds', department: 'Platform',    salary: 155000 },
    { id: 4, name: 'Barbara Liskov', department: 'Platform',    salary: 172000 },
  ]

  const columns: GridColumns<Person> = [
    { field: 'name',       header: 'Name',       width: 190 },
    { field: 'department', header: 'Department', width: 160 },
    { field: 'salary',     header: 'Salary',     width: 140,
      format: { type: 'currency', currency: 'USD' } },
  ]

  let api = $state<SvGridApi<{}, Person> | null>(null)
  let shown = $state<Person[]>(people)

  const departments = [...new Set(people.map((p) => p.department))]

  // One file per department: narrow the data, let the export follow the view.
  async function exportEach() {
    for (const dept of departments) {
      shown = people.filter((p) => p.department === dept)
      await Promise.resolve()
      await api?.exportCsv({ filename: dept.toLowerCase() })
    }
    shown = people
  }
</script>

<button type="button" onclick={exportEach}>Export one CSV per department</button>

<SvGrid data={shown} {columns} onApiReady={(next) => (api = next)} />

See also

Live examples

  • Export - Multiple sheets - One xlsx with 5 tabs - All orders + per-region splits - independent of the current grid filter.
  • Workbook - multi-sheet + formulas - A real spreadsheet: A/B/C columns + many rows you can grow on demand, cross-sheet formulas (=SUM, =VLOOKUP, nested IF) recalculating live, cell + conditional formatting, validation dropdowns, an inline chart, a calendar/scheduler sheet, open .xlsx/.csv, and export every sheet to one multi-tab .xlsx.

Related articles

  • CSV vs XLSX vs TSV - Which Export Format? - A practical breakdown of CSV, XLSX, and TSV for data grid exports - when each format earns its keep, what each one silently loses, and how to wire all three in SvGrid.
  • Multi-Level (Grouped) Column Headers in SvGrid - Band related columns under a shared parent header using SvGrid's nested column definition - how to nest, pin, combine with sorting and filtering, and when NOT to use grouping.
  • A Fill Handle (Drag to Fill) in SvGrid - Build a working spreadsheet-style fill handle on top of SvGrid's cell selection and editing - pointer tracking, range highlighting, series fill, and undo/redo integration all covered.