代码之家  ›  专栏  ›  技术社区  ›  Benoit Duffez

用命令输出替换视觉选择

vim
  •  1
  • Benoit Duffez  · 技术社区  · 6 年前

    我想将一行的一部分替换为通过管道传输到命令中的选择结果。

    echo "hello $(echo "world" | base64)" | vim -
    

    这将打开一个缓冲区 hello d29ybGQK 在里面。现在按 wvw 目测选择 d29ybGQK

    然后我试着 :!base64 -d 我希望缓冲区能容纳 hello world

    是否可以只替换可视选择,并且只将该选择传输到命令中?

    我也尝试过 c<c-r>=system('base64 -d') 但这并没有将视觉选择发送到命令的stdin。

    2 回复  |  直到 6 年前
        1
  •  8
  •   sidyll    6 年前

    过滤 ! 总是按行。您的解决方案 c 以及 将输入传递给 system() ,这是它的第二个可选参数。

    因为您刚刚更改了选定的文本,所以它进入了 " 自动地。你只要把它拿回来递给我就行了 getreg() :

    c<C-R>=system('base64 -D', getreg('"'))
    

    请注意 base64 可能会在结尾回响一句新词。如果你想移除 它,要么把整件事都包起来 trim() ,Vim 8中的新函数,或 [:-2] :

    c<C-R>=trim(system('base64 -D', getreg('"')))
    c<C-R>=system('base64 -D', getreg('"'))[:-2]
    

    这是 [0:-2] ,意思是从角色抓起一切 0到结果字符串的倒数第二。

    如果您经常使用可视化地图,请考虑创建它:

    vnoremap <leader>d c<C-R>=system('base64 -D', getreg('"'))[:-2]<CR>
    
        2
  •  1
  •   Ingo Karkat    6 年前

    本质上是基于线的;可敬的 也没有视觉模式。该限制包括使用 :range! ; 它总是过滤完整的行。

    手动解决方案

    :substitute/ /\r/ | execute '.!base64 -d' | -1join
    

    插件解决方案

    system() ),然后用结果替换所选内容。

    我的 SubstituteExpression plugin 有一个 {Visual}g= 可以过滤Vimscript表达式、Vim函数和命令以及外部命令的映射。

    express.vim :MapExpress :MapSubpress TextTransform plugin ,无论如何,您需要将其作为依赖项安装。我的插件提供了更高级(跨模式)的重复,并且 :Ex