github github
terminal-integration plugin
star 1386
alert-circle 24
open issues
users 14
git-branch 56





  use 'voldikss/vim-floaterm'


require "paq" { 

Use (neo)vim terminal in the floating/popup window.

CI GitHub license Maintenance


  • Support neovim floatwin and vim8 popupwin
  • Manage multiple terminal instances
  • Customizable terminal window style
  • Switch/preview floating terminal buffers using fuzzy-finder plugins such as denite.nvim or fzf, etc.
  • Use with other external command-line tools(ranger, fzf, ripgrep etc.)
  • Use as a custom task runner for asynctasks.vim or asyncrun.vim


  • Vim or neovim with terminal feature


  • vim-plug
Plug 'voldikss/vim-floaterm'
  • dein.nvim
call dein#add('voldikss/vim-floaterm')

Get Started

Use :FloatermNew to open a terminal window, use :FloatermToggle to hide/reopen that. The filetype of the terminal buffer is floaterm.

If you've opened multiple floaterm instances, they will be attached to a double-circular-linkedlist. Then you can use :FloatermNext or : FloatermPrev to switch between them.

❗️Note: Long-running jobs (e.g. yarn watch) inside the builtin terminal would probably slowdown your operation. It's recommended to put them into the external terminals.


:FloatermNew[!] [options] [cmd] Open a floaterm window.

  • If ! is given, execute cmd in $SHELL. Try :FloatermNew python and : FloatermNew! python to learn about the difference.
  • If execute without cmd, open $SHELL.
  • The options is formed as --key[=value], it is used to specify local attributes of a specific floaterm instance. Note that in order to input space, you have to form it as \ followed by space, and \ must be typed as \\
    • cwd working directory that floaterm will be opened at. Accepts a path, the literal <root> which represents the project root directory, and the literal <buffer> which specifies the directory of the active buffer
    • name name of the floaterm
    • silent If --silent is given, spawn a floaterm but not open the window, you may toggle it afterwards
    • disposable If --disposable is given, the floaterm will be destroyed once it is hidden.
    • title see g:floaterm_title
    • width see g:floaterm_width
    • height see g:floaterm_height
    • opener see g:floaterm_opener
    • wintype see g:floaterm_wintype
    • position see g:floaterm_position
    • autoclose see g:floaterm_autoclose
    • borderchars see g:floaterm_borderchars
  • This command basically shares the consistent behaviors with the builtin :terminal:
    • The special characters(:help cmdline-special) such as % and <cfile> will be auto-expanded, to get standalone characters, use \ followed by the corresponding character(e.g., \%).
    • Note that <bar>(i.e., |) will be seen as an argument of the command, therefore it can not be followed by another Vim command.
  • If execute this command with a range, i.e., '<,'>:FloatermNew ..., the selected lines will be sent to the created floaterm. For example, see python repl use case below.
  • Use <TAB> to get completion.

For example, the command

:FloatermNew --height=0.6 --width=0.4 --wintype=float --name=floaterm1 --position=topleft --autoclose=2 ranger --cmd="cd ~"

will open a new floating/popup floaterm instance named floaterm1 running ranger --cmd="cd ~" in the topleft corner of the main window.

The following command allows you to compile and run your C code in the floaterm window:

:FloatermNew --autoclose=0 gcc % -o %< && ./%<

:FloatermPrev Switch to the previous floaterm instance

:FloatermNext Switch to the next floaterm instance

:FloatermFirst Switch to the first floaterm instance

:FloatermLast Switch to the last floaterm instance

:FloatermUpdate [options] Update floaterm window attributes(height, width, etc.).

  • The options is the same as in :FloatermNew (except --silent).
  • Use <TAB> to get completion.

:[N]FloatermToggle[!] [floaterm_name] Open or hide the floaterm window.

  • If N is given, toggle the floaterm whose buffer number is N
  • If floaterm_name is given, toggle the floaterm instance whose name attribute is floaterm_name. Otherwise create a new floaterm named floaterm_name.
  • Use <TAB> to get completion.
  • If ! is given, toggle all floaterms (:FloatermHide! or : FloatermShow!)

:[N]FloatermShow[!] [floaterm_name] Show the current floaterm window.

  • If N is given, show the floaterm whose buffer number is N
  • If floaterm_name is given, show the floaterm named floaterm_name.
  • If ! is given, show all floaterms (If multiple floaterms have the same position attribute, only one of them will be show)

:[N]FloatermHide[!] [floaterm_name] Hide the current floaterms window.

  • If N is given, hide the floaterm whose buffer number is N
  • If floaterm_name is given, show the floaterm named floaterm_name.
  • If ! is given, hide all floaterms

:[N]FloatermKill[!] [floaterm_name] Kill the current floaterm instance

  • If N is given, kill the floaterm whose buffer number is N
  • If floaterm_name is given, kill the floaterm instance named floaterm_name.
  • If ! is given, kill all floaterms

:FloatermSend[!] [--name=floaterm_name] [cmd] Send command to a job in floaterm.

  • If --name=floaterm_name is given, send lines to the floaterm instance whose name is floaterm_name. Otherwise use the current floaterm.
  • If cmd is given, it will be sent to floaterm and selected lines will be ignored.
  • This command can also be used with a range, i.e., '<,'>:FloatermSend [--name=floaterm_name] to send selected lines to a floaterm.
    • If cmd is given, the selected lines will be ignored.
    • If use this command with a !, i.e., '<,'>:FloatermSend! [--name=floaterm_name] the common white spaces in the beginning of lines will be trimmed while the relative indent between lines will still be kept.
  • Use <TAB> to get completion.
  • Examples
    :FloatermSend                        " Send current line to the current floaterm (execute the line in the terminal)
    :FloatermSend --name=ft1             " Send current line to the floaterm named ft1
    :FloatermSend ls -la                 " Send `ls -la` to the current floaterm
    :FloatermSend --name=ft1 ls -la      " Send `ls -la` to the floaterm named ft1
    :23FloatermSend ...                  " Send the line 23 to floaterm
    :1,23FloatermSend ...                " Send lines between line 1 and line 23 to floaterm
    :'<,'>FloatermSend ...               " Send lines selected to floaterm(visual block selection are supported)
    :%FloatermSend ...                   " Send the whole buffer to floaterm



Type String. Default: &shell


Type String. Show floaterm info(e.g., 'floaterm: 1/3' implies there are 3 floaterms in total and the current is the first one) at the top left corner of floaterm window.

Default: 'floaterm: $1/$2'($1 and $2 will be substituted by 'the index of the current floaterm' and 'the count of all floaterms' respectively)

Example: 'floaterm($1|$2)'


Type String. 'float'(nvim's floating or vim's popup) by default. Set it to 'split' or 'vsplit' if you don't want to use floating or popup window.


Type Number (number of columns) or Float (between 0 and 1). If Float, the width is relative to &columns.

Default: 0.6


Type Number (number of lines) or Float (between 0 and 1). If Float, the height is relative to &lines.

Default: 0.6


Type String. The position of the floating window. Available values:

  • If wintype is split/vsplit: 'leftabove', 'aboveleft', 'rightbelow', 'belowright', 'topleft', 'botright'. Default: 'botright'.

    It's recommended to have a look at those options meanings, e.g. :help :leftabove.

  • If wintype is float: 'top', 'bottom', 'left', 'right', 'topleft', 'topright', 'bottomleft', 'bottomright', 'center', 'auto'(at the cursor place). Default: 'center'

In addition, there is another option 'random' which allows to pick a random position from above when (re)opening a floaterm window.


Type String. 8 characters of the floating window border (top, right, bottom, left, topleft, topright, botright, botleft).

Default: ─│─│┌┐┘└


Type List of String. Markers used to detect the project root directory for --cwd=<root>

Default: ['.project', '.git', '.hg', '.svn', '.root']


Type String. Command used for opening a file in the outside nvim from within :terminal.

Available: 'edit', 'split', 'vsplit', 'tabe', 'drop' or user-defined commands

Default: 'split'


Type Number. Whether to close floaterm window once the job gets finished.

  • 0: Always do NOT close floaterm window
  • 1: Close window if the job exits normally, otherwise stay it with messages like [Process exited 101]
  • 2: Always close floaterm window

Default: 0.


Type Number. Whether to hide previous floaterms before switching to or opening a another one.

  • 0: Always do NOT hide previous floaterm windows
  • 1: Only hide those whose position (b:floaterm_position) is identical to that of the floaterm which will be opened
  • 2: Always hide them

Default: 1.


Type Boolean. Whether to enter Terminal-mode after opening a floaterm.

Default: v:true


This plugin doesn't supply any default mappings. Here are the configuration examples.

" Configuration example
let g:floaterm_keymap_new    = '<F7>'
let g:floaterm_keymap_prev   = '<F8>'
let g:floaterm_keymap_next   = '<F9>'
let g:floaterm_keymap_toggle = '<F12>'

You can also use other keys as shown below:

let g:floaterm_keymap_new = '<Leader>ft'

All options for the mappings are listed below:

  • g:floaterm_keymap_new
  • g:floaterm_keymap_prev
  • g:floaterm_keymap_next
  • g:floaterm_keymap_first
  • g:floaterm_keymap_last
  • g:floaterm_keymap_hide
  • g:floaterm_keymap_show
  • g:floaterm_keymap_kill
  • g:floaterm_keymap_toggle

Note that the key mappings are set from the plugin/floaterm.vim, so if you are using on-demand loading feature provided by some plugin-managers, the keymap above won't take effect(:help load-plugins). Then you have to define the key bindings by yourself. For example,

nnoremap   <silent>   <F7>    :FloatermNew<CR>
tnoremap   <silent>   <F7>    <C-\><C-n>:FloatermNew<CR>
nnoremap   <silent>   <F8>    :FloatermPrev<CR>
tnoremap   <silent>   <F8>    <C-\><C-n>:FloatermPrev<CR>
nnoremap   <silent>   <F9>    :FloatermNext<CR>
tnoremap   <silent>   <F9>    <C-\><C-n>:FloatermNext<CR>
nnoremap   <silent>   <F12>   :FloatermToggle<CR>
tnoremap   <silent>   <F12>   <C-\><C-n>:FloatermToggle<CR>


There are two highlight-groups to specify the color of floaterm (also the border color if g: floaterm_wintype is 'float') window.

To customize, use hi command together with the colors you prefer.

" Configuration example

" Set floaterm window's background to black
hi Floaterm guibg=black
" Set floating window border line color to cyan, and background to orange
hi FloatermBorder guibg=orange guifg=cyan

Besides, there is a neovim only highlight group which can be used to configure no-current-focused window(:help NormalNC).

" Configuration example

" Set floaterm window background to gray once the cursor moves out from it
hi FloatermNC guibg=gray


autocmd User FloatermOpen        " triggered after opening a new/existed floaterm

Advanced Topics

Use with command line tools

The following cases should work both in Vim and NeoVim unless otherwise specifically noted.


Normally if you run vim/nvim somefile.txt within the builtin terminal, you would get another nvim/vim instance running in the subprocess.

Floaterm, which is a builtin script in this plugin, allows you to open files from within : terminal without starting a nested nvim. To archive that, just literally replace vim/nvim with floaterm, e.g. floaterm somefile.txt


  • #208 describes how to use gf in the floating terminal window.
  • floaterm is too long to type? set alias in your bashrc, e.g. alias f=floaterm
  • For configurable open action, refer to g:floaterm_opener


Execute git commit in the terminal window without starting a nested vim/nvim.

Refer to g:floaterm_opener for configurable open action


This plugin has implemented a wrapper for fzf command. So it can be used as a tiny fzf plugin.

Try :FloatermNew fzf or even wrap this to a new command like this:

command! FZF FloatermNew fzf


This plugin has implemented a wrapper for rg command.

Try :FloatermNew rg or create yourself a new command like this:

command! Rg FloatermNew --width=0.8 --height=0.8 rg


This plugin has implemented a wrapper for broot.

Try :FloatermNew broot or create yourself a new command like this:

command! Broot FloatermNew --width=0.8 --height=0.8 broot


There is also an fff wrapper

Try :FloatermNew fff or define a new command:

command! FFF FloatermNew fff


There is also an nnn wrapper

Try :FloatermNew nnn or define a new command:

command! NNN FloatermNew nnn


There is also an xplr wrapper

Try :FloatermNew xplr or define a new command:

command! XPLR FloatermNew xplr


There is also an lf wrapper. It is recommened to use lf.vim which is an lf wrapper with more features (Overriding netrw, Lfcd, etc.).

Try :FloatermNew lf or define a new command:

command! LF FloatermNew lf


This plugin can also be a handy ranger plugin since it also has a ranger wrapper

Try :FloatermNew ranger or define a new command:

command! Ranger FloatermNew ranger


There is also a vifm wrapper

Try :FloatermNew vifm or define a new command:

command! Vifm FloatermNew vifm


Furthermore, you can also use other command-line programs, such as lazygit, htop, ncdu, etc.

Use lazygit for instance:


Use :FloatermNew python to open a python shell. After that you can use : FloatermSend to send lines to the Python interactive shell.

Or you can just select lines and execute :'<,'>FloatermNew --wintype=split python, then the selected lines will be sent and executed once a python repl floaterm window is opened.

This can also work for other languages which have interactive shells, such as lua, node, etc.

Use with other plugins


Use vim-clap to switch/preview floating terminal buffers.

Install clap-floaterm and try :Clap floaterm


Use denite to switch/preview/open floating terminal buffers.

Install denite-floaterm and try :Denial floaterm


Use CocList to switch/preview/open floating terminal buffers.

Install coc-floaterm and try :CocList floaterm


Install fzf-floaterm and try :Floaterms


Install LeaderF-floaterm and try :Leaderf floaterm

asynctasks.vim | asyncrun.vim

This plugin can be a runner for asynctasks.vim or asyncrun.vim. See asyncrun.extra for the installation and usage.

How to define more wrappers

The wrapper script must be located in autoload/floaterm/wrapper/ directory, e.g., autoload/floaterm/wrapper/fzf.vim.

There are two ways for a command to be spawned:

  • To be executed after spawning $SHELL. Here is the old implementation of fzf wrapper

    function! floaterm#wrapper#fzf#(cmd, jobopts, config) abort
      return [v:true, 'floaterm $(fzf)']

    The code above returns a list. floaterm $(fzf) is the command to be executed. v:true means the command will be executed after the &shell startup.

  • To be executed through termopen()/term_start() function, in that case, a callback option can be provided. See fzf wrapper

    function! floaterm#wrapper#fzf#(cmd, jobopts, config) abort
      let s:fzf_tmpfile = tempname()
      let cmd = a:cmd . ' > ' . s:fzf_tmpfile
      let a:jobopts.on_exit = funcref('s:fzf_callback')
      return [v:false, cmd]
    function! s:fzf_callback(...) abort
      if filereadable(s:fzf_tmpfile)
        let filenames = readfile(s:fzf_tmpfile)
        if !empty(filenames)
          if has('nvim')
            call floaterm#window#hide(bufnr('%'))
          let locations = []
          for filename in filenames
            let dict = {'filename': fnamemodify(filename, ':p')}
            call add(locations, dict)
          call floaterm#util#open(locations)

    In the example above, after executing :FloatermNew fzf, function floaterm#wrapper#fzf# will return

    [v:false, 'fzf > /tmp/atmpfilename'].

    Here v:false means cmd

    fzf > /tmp/atmpfilename

    will be passed through termopen()(neovim) or term_start()(vim). As the result, an fzf interactive will be opened in a floaterm window.

    When user picks a file using ENTER, fzf exits and the filepath will be written in /tmp/atmpfilename and s:fzf_callback() will be invoked to open the file. Note that the function s: fzf_callback() is registered by

    let a:jobopts.on_exit = funcref('s:fzf_callback')

    The variable a:jobopts in the above code will be eventually passed to termopen()(neovim) or term_start()(vim). For more info, see :help jobstart-options(neovim) or :help job-options(vim)

How to write sources for fuzzy finder plugins

Function floaterm#buflist#gather() returns a list contains all the floaterm buffers.

Function floaterm#terminal#open_existing({bufnr}) opens the floaterm whose buffer number is {bufnr}.

For reference, see floaterm source for LeaderF.


  • Improve the documentation
  • Help resolve issues labeled as help wanted



Breaking Changes