Getting started
Five minutes to a running TUI.
This page assumes you want a terminal-native app written in Swift.
For other targets — embedding in macOS/iOS, hosting in the browser,
cross-compiling for Android — see
platforms after you have a hello world
running.
1 — Prerequisites
- Swift 6.3.1 via
swiftly.
The repo pins this exact version.
- macOS 15+ for local Apple-platform development.
- A terminal that supports raw mode and ANSI escapes.
Any modern macOS Terminal, iTerm2, Alacritty, kitty, WezTerm, or Ghostty.
For the full toolchain story (wasm SDK, Bun, Xcode, Android NDK), see
toolchains.
Anatomy
The four pieces above each play a specific role:
-
@main App — the root. TerminalUICLI
provides the default App.main() implementation, which
owns terminal raw-mode acquisition, the alternate-screen buffer, and
the run loop. You don't write a main.swift.
-
Scene — the unit of presentation. The shipped runtime
renders one active scene per host. Multi-scene apps are supported,
but only one is on screen at a time.
-
WindowGroup — the full-canvas container. It sizes itself
to the current terminal proposal and clips drawing to terminal bounds.
-
View — body-only, identity-keyed. Modifier order matters.
@State persists across rerenders by identity-path plus
source location.
That's the model. The same authored App can flow into
three execution modes: terminal-native (above), WASI, or
host-managed embedding inside macOS / iOS / web shells.
5 — Five next things