如何使用vimscript包装文本块?

如何使用vimscript包装文本块?,vim,Vim,我正在编写一个vimscript函数,将当前选择的行(视觉模式)包装到Ruby begin rescue块中。我有一些奇怪的行为。以下是我的功能: function! BeginRescueWrap() execute "normal! gvd" let head = "begin\<CR>" let body = @" let tail = "rescue StandardError =>e\<CR>binding.pry\<CR>en

我正在编写一个vimscript函数,将当前选择的行(视觉模式)包装到Ruby begin rescue块中。我有一些奇怪的行为。以下是我的功能:

function! BeginRescueWrap()
  execute "normal! gvd"
  let head = "begin\<CR>"
  let body = @"
  let tail = "rescue StandardError =>e\<CR>binding.pry\<CR>end\<CR>"
  execute "normal! i" . head . "\<CR>" . body . "\<CR>" . tail
endfunction
生成此输出:

begin

  begin

  rescue StandardError =>e
  binding.pry
  end

  Oh lord won't you buy me a Mercedes Benz
  My friends all drive Porsches, I must make amends

  rescue StandardError =>e
  binding.pry
  end

我不关心缩进(可以稍后修复)。请注意,有一个外包装,其中包括一个空的内包装,后跟目标线。我做错了什么?

问题是Vim将执行您的方法两次,因为您选择了两行。如果将
range
参数添加到方法中,它将只执行一次,您将获得所需的效果:

function! BeginRescueWrap() range
  execute "normal! gvd"
  let head = "begin\<CR>"
  let body = @"
  let tail = "rescue StandardError =>e\<CR>binding.pry\<CR>end\<CR>"
  execute "normal! i" . head . "\<CR>" . body . "\<CR>" . tail
endfunction
函数!BeginRescueWrap()范围
执行“正常!gvd”
让head=“开始”
让body=@“
let tail=“rescue StandardError=>e\binding.pry\end\”
执行“正常!头,身体,尾巴
端功能
请注意,尽管出于此特定目的,像这样的映射可能更简洁:

vnoremap ,q sbegin<cr><C-R>1rescue StandardError =>e<cr>binding.pry<cr>end<cr>
vnoremap,q sbegin1rescue标准错误=>ebinding.pryend

,q
的映射删除当前选择的文本,写入
开始
语句,然后放入刚刚删除的内容,然后写入结束语。

问题是Vim将执行您的方法两次,因为您选择了两行。如果将
范围
参数添加到方法中,它将只执行两次只需使用一次,即可达到预期效果:

function! BeginRescueWrap() range
  execute "normal! gvd"
  let head = "begin\<CR>"
  let body = @"
  let tail = "rescue StandardError =>e\<CR>binding.pry\<CR>end\<CR>"
  execute "normal! i" . head . "\<CR>" . body . "\<CR>" . tail
endfunction
函数!BeginRescueWrap()范围
执行“正常!gvd“
让head=“开始”
让body=@“
let tail=“rescue StandardError=>e\binding.pry\end\”
执行“正常!我”。头。"\" . 身体。"\" . 尾
端功能
请注意,尽管出于此特定目的,像这样的映射可能更简洁:

vnoremap ,q sbegin<cr><C-R>1rescue StandardError =>e<cr>binding.pry<cr>end<cr>
vnoremap,q sbegin1rescue标准错误=>ebinding.pryend

,q
的此映射删除当前选定的文本,写入
开始
语句,然后放入刚刚删除的内容,然后写入结束语。

似乎对这两行执行。似乎对这两行执行。