GPU-accelerated macOS terminal. Electron shell, xterm.js rendering, node-pty backend.
- GPU rendering via xterm.js's WebGL renderer (Metal through Chromium/ANGLE)
- Tabs with drag-to-reorder, inline double-click rename, close-confirmation dialog
- Shell integration for zsh and bash — prompt marks,
⌘↑/⌘↓prompt navigation, tab status dots (running spinner, attention dot) - Live tab titles — reflect the running command via OSC 0
- Unified ⌘⇧P palette — fuzzy search across both app actions and shell history in one overlay
- Find in terminal (
⌘F) with match highlights and counter - Inline images — drag a PNG / JPG / GIF onto a terminal and it renders via iTerm2's imgcat protocol; thumbnail size configurable
- Font picker with previews using Chromium's Local Font Access API
- Window snapping — resizing snaps the window to whole-cell boundaries so the grid never has a partial row or column
- Themes — gruvbox-dark (default), nord, solarized-dark, light
- Flat, minimalist UI — single chrome band, subtle tab separators, no background tints; an accent underline marks the active tab
| Key | Action |
|---|---|
| ⌘T | New tab |
| ⌘W | Close tab (with confirmation, toggleable) |
| ⌘K | Clear scrollback + viewport |
| ⌘F | Find in terminal |
| ⌘⇧] / ⌘⇧[ | Next / prev tab |
| ⌘1 – ⌘9 | Jump to tab N |
| ⌘⇧P | Open palette (actions + history) |
| ⌘↑ / ⌘↓ | Jump to prev / next prompt |
| ⌘, | Settings |
All bindings are rebindable in Settings → Keyboard shortcuts (except ⌘1–9).
- macOS 11+ (tested on 25.x / Apple Silicon)
- Node.js 20+ and npm
git clone git@github.com:dbrentley/bterm.git
cd bterm
npm install
npm run devnpm run dev hot-reloads renderer changes and restarts on main/preload changes.
npm run pack # unsigned .app for local smoke-testing
npm run dist:fast # signed, not notarized (~2 min) — runs on your Mac only
npm run dist # signed + notarized arm64 .dmg (~10 min)
npm run dist:universal # signed + notarized arm64 + x64 (~15 min)Code signing + notarization require an Apple Developer ID cert in your login Keychain and App Store Connect API credentials in a gitignored .env file:
APPLE_API_KEY=/path/to/AuthKey_XXXXXXXXXX.p8
APPLE_API_KEY_ID=XXXXXXXXXX
APPLE_API_ISSUER=<uuid>
electron-builder auto-discovers your Developer ID cert; scripts/release.sh loads .env and wraps the build in caffeinate -i.
Settings live at ~/Library/Application Support/bterm/settings.json. Edit via ⌘, inside the app — includes font, theme, cursor style, scrollback, shell override, shell-integration toggle, share-history toggle, image thumbnail size, close-confirmation toggle, and all key rebinds.
Three processes:
- main (
src/main/) — Node. Owns theBrowserWindow, all PTYs, config + history read/write, shell-integration script injection. - preload (
src/preload/) — narrowwindow.btermIPC surface exposed viacontextBridge. - renderer (
src/renderer/) — DOM + xterm.js, split into small modules (tabs,pane,palette,find,settings-ui,font-picker,window-snap,drop, etc.).
MIT