Why does "locate filename | xargs vim" cause strange terminal behaviour?
While 'reset' fixes the problem, you can also explicitely re-activate the echo behaviour with:
stty echo
An other alternative is to execute xargs
with the -o
option. From the man page:
-o Reopen stdin as /dev/tty in the child process before executing
the command. This is useful if you want xargs to run an interac-
tive application.
Note, -o
is a BSD extension to xargs.
A more portable means to achieve the same effect is:
xargs sh -c 'vim "$@" < /dev/tty' vim
Vim expects to be connected to a real terminal and sends codes appropriate to that.
Reset the terminal with
reset
The easiest workaround:
locate 50local.policy | xargs gvim
Rationale gui vim doesn't require a terminal
Otherwise:
vim $(locate 50local.policy)
Rationale vim is started directly connected to the terminal (instead of as a child process under
xargs
which in turn runs in a subshell with stdin/stdout connected to pipes instead of a terminal). It is like sayingvim /usr/some/dir/50local.policy /usr/local/some/dir/50local.policy
Alternatively
You can dodge the issue by not starting vim with the arguments, but adding the arguments from vim! Vim is in fact a lot better at running shells than shells are at running vim.
Whilst in vim:
:args `locate 50local.policy`
:rewind
This sets the argument list to the files returned from the shell command between the ticks; :rewind then goes to the first file from that list. If you were editing multiple matches, try this:
:w|next
This sequence of commands (separated by |) writes the current buffer to file, then goes to the next file in the args list.