【问题标题】:How to imap a character in Vim based on previous character如何根据前一个字符在 Vim 中映射一个字符
【发布时间】:2014-04-18 09:38:32
【问题描述】:

我创建了以下映射来模拟某些 IDE 中的行为,当您在 foo() 之类的函数声明之后插入 { 时,会自动插入关闭 } 并自动插入空行并将光标设置为空行选项卡位置。

:imap { {<CR><CR>} <up><Tab>     

当我在任何上下文中插入{ 时,这当然会发生这种行为。如何根据之前插入的字符进行操作?一定是涉及到vim脚本函数吗? 注意:我不想使用外部 vim 插件。

【问题讨论】:

  • 这不是您问题的实际答案,但可以使用 sn-ps 实现类似的行为(例如snipmate plugin
  • 让我直截了当地说,你想完成一些类似 IDE 的功能,在你的 ~/.vimrc 文件的一行中嗅探一行的语法吗?这将导致幼稚的imap 在许多情况下必然会失败。这是一种平衡行为,您要么获得仅在部分时间正确的简单映射,要么使用更高级的解决方案,该解决方案需要更好的功能或插件。您反对函数或使用插件有什么问题?

标签: vim editor vi


【解决方案1】:

IDE 通常在输入 { 后进行这种扩展,这在 vimscript 中很容易做到:

:imap {<CR> {<CR><CR>} <up><Tab>

如果您继续在同一行输入其他内容,这将不会扩展。

需要注意的是,使用此映射键入 { 时会有一点延迟。有关详细信息,请参阅“超时”和“超时”选项。

【讨论】:

  • @SJMP: 是回车的缩写。请参阅:h key-notation 了解更多信息。
【解决方案2】:

这些代码 sn-ps 在插入模式下为您提供光标前后的字符:

let previous_character = getline(".")[col(".")-2]
let next_character     = getline(".")[col(".")-1]

您可以在&lt;expr&gt; 映射中使用它们:

:inoremap <expr> { getline(".")[col(".")-2] == " " ? "{^M}^OO" : "{"

上面毫无意义的映射会在决定插入{ 还是扩展的{} 之前检查光标之前的字符是否为空格。

如果您想要一个“智能”映射,您将无法避免编写一个或多个函数。例如,我使用的是 69 行。

【讨论】:

    【解决方案3】:

    您可以在Automatically append closing characters Vim Tips Wiki 页面上找到多种方法和插件列表。请注意,虽然有一些简单的解决方案,但它们通常有一些缺点,不幸的是,整个方法在 Vim 7.4 中在撤消方面被破坏了。

    【讨论】:

      猜你喜欢
      • 2016-08-28
      • 2012-08-05
      • 1970-01-01
      • 2019-08-01
      • 2019-09-04
      • 1970-01-01
      • 2013-05-26
      相关资源
      最近更新 更多