Oxide Terminal / docs
Docs / Reference / Configuration

Configuration

One TOML file at ~/.config/oxide/config.toml. Every key has a default, so a three-line config is a perfectly good config.

The file

A fully commented default is written on first run. Open it from inside Oxide with cmd-, (Oxide → Settings…), which opens it with your $EDITOR in the focused pane — without echoing a command line at the prompt.

Set the OXIDE_CONFIG environment variable to point somewhere else — useful for keeping the file in a dotfiles repo:

OXIDE_CONFIG=~/dotfiles/oxide.toml open -a Oxide

Reloading

Oxide watches the file's directory (editors write-and-rename, so watching the file alone misses saves) and reloads on change.

  • Live: [font], [colors], [window], [cursor], [tree], [status_bar], [keymap], [notifications], [ssh], [workspaces], shell.scrollback, bell, copy_on_select. Save the file and the window repaints.
  • New sessions only: the rest of [shell], [prompt], and commands.emit_cmdline — they're baked into a shell's environment and init script when it starts. Open a new tab to pick them up.

When it doesn't parse

A malformed file never takes the app down. Oxide keeps running with the configuration it already had and shows the first line of the parse error as a red toast in the bottom-right corner. Fix the file, save, and the toast clears. Click it to hide it early; it comes back on the next reload if the file is still broken.

Unknown keys are an error rather than a shrug — a typo'd show_hiden tells you so instead of silently doing nothing. An unrecognised color preset is reported the same way, with the list of valid names. Bad [keymap] entries are listed in the toast too, one per line, while the rest of the map still binds.

Top level

KeyTypeDefaultDescription
bell string "none" "none", "sound" (the system beep), or "visual" (a brief flash of the pane).
copy_on_select bool false Copy to the system clipboard as soon as a mouse selection ends.

[font]

KeyTypeDefaultDescription
family string or array "JetBrainsMono Nerd Font Mono" Any installed monospace family. The default is bundled into the binary, so it works with nothing installed. A list names fallbacks: the first entry is the terminal font, the rest are tried in order for glyphs it lacks — ["JetBrainsMono Nerd Font Mono", "Apple Color Emoji", "PingFang SC"] avoids tofu for emoji and CJK.
size float 14.0 Points. cmd-+/cmd-- adjust at runtime without writing back here.
line_height float 1.25 Multiple of the font size.
weight string "normal" "normal", "medium", or "bold".
ligatures bool false Enable programming ligatures, if the family has them.

[window]

KeyTypeDefaultDescription
padding table { x = 12, y = 8 } Pixels between the terminal grid and the window edge.
opacity float 1.0 0.0–1.0; below 1.0 makes the background translucent.
blur bool false Blur what's behind a translucent window.
titlebar string "hidden" "hidden" gives the tab bar the whole top edge; "native" keeps the standard macOS title bar.
new_tab_directory string "pwd" Where cmd-t starts — "pwd" inherits the current pane's directory, "home" always opens at ~/.
inactive_pane_opacity float 1.0 Fade every pane except the active one to this (0.05–1.0; 0.7 or so is typical). Only applies when the tab has more than one pane, and never while zoomed. See dimming.
inactive_window_opacity float 1.0 Fade the whole window while another app is frontmost.

[cursor]

The shape the shell starts with. Programs that set their own with DECSCUSR (\e[<n> q — vim per mode, for one) win until they reset it. Blinking pauses while you type.

KeyTypeDefaultDescription
style string "block" "block", "bar", or "underline".
blink bool true Blink in the focused pane.
blink_interval integer 530 Milliseconds per half-cycle (100–5000).
unfocused string "hollow" The cursor in a pane that isn't focused: "hollow" (an outline), "solid" (the same shape, not blinking), or "hidden".
thickness float 0.15 Width of a bar and height of an underline, as a fraction of a cell.

[shell]

KeyTypeDefaultDescription
program string unset The shell to launch. Unset means $SHELL, falling back to /bin/zsh.
args array ["-l"] Arguments for the shell. Under bash with integration on, -l is replaced by --init-file, which emulates the login chain itself.
scrollback integer 10000 Lines of history kept per pane. Applies live, to every pane.
option_as_meta string "none" Send Option as Meta (ESC-prefixed). "none", "left", "right", or "both" — macOS can't distinguish the two Option keys, so "left" and "right" currently behave like "both".
integration bool true Install the OSC 133 hooks and the silent-cd widget. Independent of prompt styling.

[tree]

KeyTypeDefaultDescription
width float 280 Drawer width in pixels.
show_hidden bool false Show dotfiles. I toggles this for the running session.
respect_gitignore bool true Hide anything the repo's ignore rules cover.
indent float 16 Pixels of indent per nesting level.
icons bool true Nerd Font file-type icons in the drawer.
follow_cwd bool true Re-root the tree when the focused shell changes directory.
git_status bool true Colour rows by git state, rolled up onto collapsed directories.

[editor]

How cmd-click on a path:line opens your editor. Oxide maps the line-number flag for vim/nvim, VS Code and friends, emacs, Sublime, and Helix on its own; set this for anything else.

KeyTypeDefaultDescription
open_at_line string A shell command with {path}, {line}, and {col} substituted (the path arrives quoted; a missing column is 1), e.g. "myeditor --line {line} {path}". Overrides the built-in mapping.

[status_bar]

KeyTypeDefaultDescription
enabled bool true The native bar with workspace, directory, and git state. View → Toggle Status Bar overrides it for the current window.
position string "bottom" "top" or "bottom".

[colors]

A preset supplies all twenty colors; any individual key you set overrides the preset. Values are #rgb or #rrggbb hex.

[colors]
preset       = "oxide"
background   = "#0d0b0a"   # override just this one

# ...or let macOS pick between two:
follow_system = true
preset_dark   = "catppuccin-mocha"
preset_light  = "catppuccin-latte"
KeyDescription
preset One of the eight built-in themes. Unset means catppuccin-mocha.
follow_system Switch with the macOS appearance: dark uses preset_dark, light uses preset_light, each falling back to preset (and with nothing else set, light falls back to catppuccin-latte). Overrides below apply on top of whichever is active. Off by default.
preset_dark, preset_light The two variants follow_system chooses between.
background, foreground, cursor, selection_bg The four UI colors.
selection_fg Text inside a selection. Unset keeps each cell's own colour over selection_bg.
black, red, green, yellow, blue, magenta, cyan, white ANSI 0–7.
bright_black … bright_white ANSI 8–15.

Picking a theme with cmd-alt-t rewrites the whole [colors] block to just preset = "…", dropping individual overrides — they'd defeat the theme you just chose. Keep hand-tuned colors out of the picker's way, or re-add them after switching. With follow_system on, the picker only sets the variant for the current appearance and keeps the rest.

[ssh]

Accents for panes whose foreground process is ssh: the pane's border and the status bar's ssh: host chip take the colour while the connection lasts. An array of tables; the first pattern that matches wins. See SSH awareness.

[[ssh.hosts]]
match  = "*.prod.example.com"
accent = "#f38ba8"
KeyTypeDefaultDescription
hosts[].match string required A glob over the host as typed on the command line, after any user@: * matches any run, ? one character; case-insensitive.
hosts[].accent string required A hex colour.

[prompt]

Covered in full on Prompt & shell integration. In short:

KeyTypeDefaultDescription
enabled bool true Build and set the prompt. False keeps your own.
separator string "\ue0b0" Drawn between segments (the powerline right arrow).
end string "\ue0b0" Drawn after the last segment; empty falls back to separator.
newline_before_input bool false Put the cursor on its own line below the segments.
segments array of tables cwd, git, exit_status The segments, in render order.

[[prompt.segments]]

KeyTypeDefaultDescription
kind string "text" cwd, git, exit_status, time, user, host, duration, text, or env.
fg / bg string unset Hex colors for this segment.
bold bool false Bold the segment's text.
options table {} Per-kind settings: style, max_len, show_dirty, dirty_bg, ahead_behind, hide_on_success, format, text, var. See segment kinds.

[notifications]

Desktop notifications when a command finishes in a pane you aren't watching. From the installed app these are real macOS notifications (you'll be asked to allow them once), and clicking one focuses the pane; a cargo run build has no bundle to attach them to and falls back to osascript, which can't route a click.

KeyTypeDefaultDescription
enabledbooltrueMaster switch.
min_duration string "30s" Commands shorter than this never notify. "2m", "1.5s", "250ms", or a bare number of seconds.
only_when_unfocused bool true Stay quiet when the pane is focused and the window is active — you saw it finish.
on_failure_always bool false A non-zero exit notifies however short the command was.
passthrough_osc9 bool true Let programs post notifications themselves with OSC 9 / OSC 777, rate-limited per pane.

[commands]

The per-pane command log built from the shell integration's OSC 133 markers — what feeds the status bar, tab dots, history search, and the gutter. Needs shell.integration = true and zsh or bash.

KeyTypeDefaultDescription
trackbooltrueKeep the log at all. Off means no history, no indicators, no gutter.
emit_cmdline bool true The shell sends each command line to Oxide alongside the start marker, so history and notifications can name the command. Kept in memory only, never written to disk. Applies to new sessions.
max_entriesint500Commands remembered per pane.

[workspaces]

How pinned workspaces restore their startup commands.

KeyTypeDefaultDescription
run_startup_commands bool true Re-run each pane's saved startup command when a pinned workspace is restored, and when a closed tab is reopened. Off restores the layout only. For a single launch, --no-startup-commands or shift held at launch does the same.
startup_timeout string "5s" How long to wait for a pane's shell to show its first prompt before giving up on that pane's command. Same duration syntax as notifications.min_duration.

[keymap]

Keystroke on the left, action id on the right. Pairs directly under [keymap] bind everywhere; the subtables scope a binding to one context. An empty string unbinds a default. The full list of action ids and the rules for what's allowed where are on the keybindings page.

[keymap]
"cmd-shift-p"  = "app::palette"
"cmd-d"        = ""            # unbind

[keymap.file_tree]
"y"            = "tree::refresh"
KeyTypeDefaultDescription
replace_defaults bool false Start from an empty map instead of merging over the built-in one. Rarely what you want: every action that has no entry becomes unreachable.
root / terminal / terminal_vi / file_tree / workspaces / overlay table {} Context-scoped bindings. [keymap.root] is the same as writing the pairs directly under [keymap]. A bare key (no cmd, ctrl, or alt) is rejected in root and terminal — it would be stolen from your shell. terminal_vi is copy mode, where bare keys are fine.

The generated default

This is what lands in config.toml on first run.

# Oxide configuration.
# This file was generated on first run; every value shown is the default.
# Font and color changes apply live; [shell] and [prompt] changes apply to
# newly started sessions.

[font]
family      = "JetBrainsMono Nerd Font Mono"
                              # or a list: the rest are fallbacks for CJK/emoji,
                              # e.g. ["JetBrainsMono Nerd Font Mono", "Apple Color Emoji"]
size        = 14.0
line_height = 1.25
weight      = "normal"        # normal | medium | bold
ligatures   = false

[window]
padding  = { x = 12, y = 8 }
opacity  = 1.0                # 0.0 - 1.0; < 1.0 makes the background translucent
blur     = false              # blur what's behind a translucent window
titlebar = "hidden"           # native | hidden
new_tab_directory = "pwd"     # pwd | home — where cmd-t starts
inactive_pane_opacity   = 1.0 # dim the panes you aren't in (0.5–0.9 typical)
inactive_window_opacity = 1.0 # dim the whole window when another app is active

[cursor]
style          = "block"      # block | bar | underline (programs can override via DECSCUSR)
blink          = true
blink_interval = 530          # ms per half-cycle
unfocused      = "hollow"     # hollow | solid | hidden — the cursor in an unfocused pane
thickness      = 0.15         # bar width / underline height, as a fraction of a cell

[shell]
# program = "/bin/zsh"        # default: $SHELL
args           = ["-l"]
scrollback     = 10000
option_as_meta = "none"       # none | left | right | both
                              # (left/right currently behave like "both")
integration    = true         # OSC 133 markers + silent cd from the file tree.
                              # Independent of [prompt]: keep your own prompt
                              # (starship, p10k) and still get integration.

[tree]
width             = 280
show_hidden       = false
respect_gitignore = true
indent            = 16
icons             = true      # nerd-font icons in the drawer
follow_cwd        = true      # re-root the tree when the shell cd's
git_status        = true      # colour rows by git state (modified, added, untracked…)

# [editor]
# open_at_line = "myeditor --line {line} {path}"   # for editors Oxide doesn't know

# bell = "none"               # none | sound | visual
# copy_on_select = false      # mouse selection copies to clipboard on release

[status_bar]
enabled  = true               # native bar showing cwd + git branch/dirty
position = "bottom"           # top | bottom

[notifications]
enabled             = true    # notify when a command finishes in a pane you aren't watching
min_duration        = "30s"   # ...if it ran at least this long ("2m", "1.5s", or seconds)
only_when_unfocused = true    # stay quiet when the pane is focused and the window active
on_failure_always   = false   # a non-zero exit notifies regardless of duration
passthrough_osc9    = true    # let programs post notifications (OSC 9 / OSC 777)

[commands]
track        = true           # the command log: status bar, tab dots, cmd-r history, gutter
emit_cmdline = true           # the shell sends each command line to Oxide (memory only)
max_entries  = 500

[workspaces]
run_startup_commands = true   # re-run each pane's saved startup command when a pinned
                              # workspace is restored (skip once: --no-startup-commands,
                              # or hold shift while Oxide launches)
startup_timeout      = "5s"   # give up on a pane's command if its shell isn't ready by then

# [keymap]                    # keystroke = "action id"; see the keybindings page
# "cmd-shift-p" = "app::palette"
# "cmd-d"       = ""          # unbind a default

# [[ssh.hosts]]                # colour a pane's border while ssh'd into a matching host
# match  = "*.prod.example.com"
# accent = "#f38ba8"

[colors]
# Presets: catppuccin-mocha | catppuccin-latte | gruvbox-dark | tokyonight
#          | dracula | nord | solarized-dark | oxide
#          | ethereal | everforest | flexoki-light | hackerman | kanagawa
#          | last-horizon | lumon | lupine | matte-black | miasma | osaka-jade
#          | retro-82 | ristretto | rose-pine-dawn | solitude | vantablack | white
preset = "catppuccin-mocha"
# Follow the macOS appearance instead, switching between two presets:
# follow_system = true
# preset_dark   = "catppuccin-mocha"
# preset_light  = "catppuccin-latte"
# Any color can override the preset individually:
# background   = "#11111b"
# foreground   = "#cdd6f4"
# cursor       = "#f5e0dc"
# selection_bg = "#414458"
# selection_fg = "#cdd6f4"    # text inside a selection; unset keeps each cell's colour
# black / red / green / yellow / blue / magenta / cyan / white
# bright_black / bright_red / ... / bright_white

# The prompt is compiled into a zsh init script and injected via ZDOTDIR.
# Your own ~/.zshrc is sourced first; only PROMPT is overridden.
# Requires zsh (the macOS default shell); other shells keep their own prompt.
[prompt]
enabled              = true
separator            = "\ue0b0"   # powerline right arrow
end                  = "\ue0b0"
newline_before_input = false

# Segment kinds: cwd | git | exit_status | time | user | host | duration
#                | text (options.text) | env (options.var)
[[prompt.segments]]
kind = "cwd"
fg   = "#11111b"
bg   = "#89b4fa"
bold = true
options = { style = "truncate_to_repo", max_len = 40 }   # full | truncate_to_repo | basename

[[prompt.segments]]
kind = "git"
fg   = "#11111b"
bg   = "#a6e3a1"
options = { show_dirty = true, dirty_bg = "#f9e2af", ahead_behind = true }

[[prompt.segments]]
kind = "exit_status"
fg   = "#11111b"
bg   = "#f38ba8"
options = { hide_on_success = true }

# [[prompt.segments]]
# kind = "time"
# options = { format = "%H:%M" }

# [[prompt.segments]]
# kind = "duration"

The separator and end values in the real file are literal powerline glyphs (U+E0B0), written here as the equivalent TOML escape so they stay readable without a Nerd Font installed.