Open-Source Wikis

/

fzf

/

Features

/

Key bindings and actions

junegunn/fzf

Key bindings and actions

--bind is the binding between an event (key, mouse, named) and a chained list of actions. The action set is large enough to make fzf programmable as a small TUI toolkit.

Anatomy of a bind

--bind '<event>:<action>[+<action>]*[,<event>:...]*'

Examples:

--bind 'ctrl-r:reload(rg --files)'
--bind 'enter:become(vim {})'
--bind 'change:first'
--bind 'ctrl-p:change-preview-window(right|down|hidden)'
--bind 'tab:toggle+down'
--bind 'start:reload(fd .)+unbind(ctrl-c)'

Multiple binds are separated by commas; multiple actions for one event are joined with +.

Events

Class Examples Notes
Key chord ctrl-a, alt-up, f5, enter, esc, tab, space Modifiers: ctrl, alt, shift.
Mouse click-header, right-click, double-click, scroll-up, scroll-down, preview-mouse-* --no-mouse disables.
Named start, load, change, result, focus, one, zero, multi, jump, jump-cancel, backward-eof, bracketed-paste-begin/end Fired by fzf's lifecycle, not the user.

start fires before any input has been read; load after the first read finishes; change when the query changes; result when the match list is updated; focus when the cursor moves to a new item; one/zero when the match count drops to 1 or 0.

Actions

Action types are enumerated in src/options.go and stringified by the generated src/actiontype_string.go (200+ entries). They fall into a few families:

up, down, page-up, page-down, half-page-up, half-page-down, first, last, top, pos(N), track, track-current, untrack-current.

Editing

backward-char, forward-char, kill-line, kill-word, backward-kill-line, clear-query, clear-screen, delete-char, delete-char/eof, beginning-of-line, end-of-line, unix-line-discipline, yank, put.

Selection

accept, accept-non-empty, accept-or-print-query, abort, cancel, close, select, select-all, deselect, deselect-all, toggle, toggle-all, toggle-down, toggle-up, clear-selection.

Layout

change-preview-window(...), change-prompt(...), change-pointer(...), change-header(...), change-header-lines(N), change-footer(...), change-input-label(...), change-list-label(...), change-border-label(...), change-preview-label(...), change-ghost(...), toggle-preview, toggle-preview-wrap, toggle-header, hide-header, hide-input, show-input, toggle-input, toggle-multi-line.

Search & input

change-query(...), change-multi, change-nth(...), change-with-nth(...), enable-search, disable-search, toggle-search, toggle-sort, toggle-track, toggle-track-current.

Run external commands

execute(...), execute-silent(...), become(...), reload(...), reload-sync(...), print(...), put(...).

Transform-* actions

transform-prompt(...), transform-query(...), transform-header(...), transform-footer(...), transform-search(...), transform-preview-window(...), transform-border-label(...), transform-list-label(...), transform-input-label(...), transform-preview-label(...), transform-ghost(...), transform-pointer(...), transform(...) (universal — body emits any number of fzf actions).

Bind manipulation

bind(...), unbind(...), rebind(...), toggle-bind(...).

Process exit

accept (exit code 0), abort (exit code ExitInterrupt), become(...) (exit code ExitBecome, then re-exec target).

The full list lives in src/actiontype_string.go; the man page (man/man1/fzf.1, "AVAILABLE ACTIONS") is the canonical user-facing reference.

Action chaining

Actions in a chain run in order. If one of them is accept, abort, or become, fzf finishes the rest of the chain that doesn't require a still-running UI, then exits.

--bind 'enter:print(picked: {})+accept'

prints the line, then accepts.

Argument syntax

Most argument-taking actions accept either of:

action(arg)
action:arg

Inside the parentheses, ( and ) must balance (escape with \(, \)). Inside :arg, the argument continues until the next bind separator (comma) or the end of the bind string.

transform-* family

transform-X runs a shell command, captures stdout, and uses it as the new value of X. The command can use the same placeholder language as --preview:

--bind 'change:transform-prompt(echo "{q}> ")'

Every keystroke the prompt becomes the current query plus > .

The universal transform(...) is more powerful: its stdout is interpreted as a list of fzf actions and executed. This is how scripts can dynamically react to the current state.

become(...) and ExitBecome

become(<cmd>) writes <cmd> + env to a .become temp file, exits with ExitBecome (a special exit code defined in src/constants.go), and lets the wrapper layer (or main.go) re-exec the target. The result: fzf --bind 'enter:become(vim {})' leaves the user inside vim after fzf has cleaned up the screen.

The implementation lives in src/proxy.go (ExitBecome branch in runProxy) and src/util/util.go (Executor.Become, which calls syscall.Exec on POSIX).

Where it lives

Concern File
Bind / action / placeholder grammar src/options.go
Action enum src/options.go + generated src/actiontype_string.go
Action dispatch src/terminal.go
Placeholder substitution src/terminal.go
Become / Exit codes src/constants.go, src/proxy.go, src/util/util.go
HTTP-driven action injection src/server.go
Tests src/options_test.go, test/test_core.rb, test/test_exec.rb, test/test_server.rb

See systems/options and systems/terminal-ui for implementation details.

Built by Factory AutoWiki from public repository content. It is a generated preview for codebase exploration, not source-maintained documentation.

Key bindings and actions – fzf wiki | Factory