在使用omap
或onoremap
声明映射时,我希望能够处理运动将是块状,线性或标准的情况。
例如,让我们考虑以下块:
abcd
efgh
ijkl
mnop
光标位于字母f上。假设我定义了从K
到:normal! vjl
的运算符映射(转到字母k)。
onoremap K :normal! vjl<cr>
有趣的是,当我运行dvK
,dK
,d^VK
时,我分别得到了
abcd abcd abcd
el el eh
mnop mnop il
mnop
但是,当我运行dVK
时,它将无效,我与dvK
完全相同。
我尝试使用visualmode()
(映射定义为@=visualmode()<cr>jl<cr>
但这不起作用。当您使用v
时,似乎不会立即影响此函数的返回值,{运算符挂起模式下的{1}}或CTRL-V。
有人有线索吗?
谢谢
答案 0 :(得分:0)
我已经在操作员挂起的映射上写了一些答案。在one of them 1 中,我根据文档概述了应该处理各种情况(字符,行,块方式选择)的函数大纲:
g@{motion} Call the function set by the 'operatorfunc' option.
The '[ mark is positioned at the start of the text
moved over by {motion}, the '] mark on the last
character of the text.
The function is called with one String argument:
"line" {motion} was |linewise|
"char" {motion} was |characterwise|
"block" {motion} was |blockwise-visual|
Although "block" would rarely appear, since it can
only result from Visual mode where "g@" is not useful.
{not available when compiled without the |+eval|
feature}
以下是使用<F4>
计算空格数的示例:&gt;
nmap <silent> <F4> :set opfunc=CountSpaces<CR>g@
vmap <silent> <F4> :<C-U>call CountSpaces(visualmode(), 1)<CR>
function! CountSpaces(type, ...)
let sel_save = &selection
let &selection = "inclusive"
let reg_save = @@
if a:0 " Invoked from Visual mode, use '< and '> marks.
silent exe "normal! `<" . a:type . "`>y"
elseif a:type == 'line'
silent exe "normal! '[V']y"
elseif a:type == 'block'
silent exe "normal! `[\<C-V>`]y"
else
silent exe "normal! `[v`]y"
endif
echomsg strlen(substitute(@@, '[^ ]', '', 'g'))
let &selection = sel_save
let @@ = reg_save
endfunction
答案 1 :(得分:0)
要实现您的目标,您只需定义
即可onoremap K :<c-u>normal! jl<cr>
请注意,由ex命令形成的此动作始终是字符(请参阅:h movement
然后,您可以自由使用dv
,dV
或d^V
来强制将动作变为另一种类型,并获得您想要的效果。