Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to use vim variables in an external filter command in visual mode?

Tags:

vim

I'm trying to make a code pretty printer filter (e.g. perltidy) accept arbitrary options depending on vim variables. My goal is to pass project specific options to an external command used as a filter (:!) in visual mode.

The following expresses my intention (the last line is problematic):

" set b:perltidy_options based on dirname of the currently edited file
function! SetProjectVars()
  if match(expand("%:p:h"), "/project-foo/") >= 0
    let b:perltidy_options = "--profile=$HOME/.perltidyrc-foo --quiet"
  elseif match(expand("%:p:h"), "/project-bar/") >= 0
    let b:perltidy_options = "--profile=$HOME/.perltidyrc-bar --quiet"
  else
    let b:perltidy_options = "--quiet"
  endif
endfunction

" first set the project specific stuff
autocmd BufRead,BufNewFile * call SetProjectVars()

" then use it
vnoremap ,t :execute "!perltidy " . b:perltidy_options<Enter>

However, the last line (vnoremap) is an error in vim, because it expands to:

:'<,'>execute "!perltidy " . b:perltidy_options

and the execute command cannot accept a range. But I'd like to have this:

:execute "'<,'>!perltidy " . b:perltidy_options

How can I do this?

p.s. My perltidy is configured to act like a unix filter and I use vim 7.3.

like image 364
rubasov Avatar asked Oct 09 '22 18:10

rubasov


1 Answers

You can use <C-\>e and getcmdline() to preserve command-line contents:

vnoremap ,t :<C-\>e'execute '.string(getcmdline()).'."!perltidy " . b:perltidy_options'<CR><CR>

, but in this case I would suggest simpler <C-r>= which purges out the need for :execute:

vnoremap ,t :!perltidy <C-r>=b:perltidy_options<CR><CR>
like image 83
ZyX Avatar answered Oct 12 '22 11:10

ZyX