linY is not Yasnippet

首先感谢 xfq 同学,他帮我解决了一堆问题的同时,顺便帮我解决了一个最核心的问题:一个拉风的名字!而且现在我也不用再费劲想一个文章的标题,难道这就是传说中的 DRY?-_-!!!

其次要感谢 xfq 同学——本来我是可以一直忍着不用 snippet 的,后来从他处听说 emacs 25 要对 snippet 进行官方的调整,尤其是调整的周期比较长……然后我就不淡定了。凡事就怕惦记着,有一天我终于忍不住了,你懂的

至于 liny 是作什么的,感兴趣的同学可以从标题中看出来,不感兴趣的同学还是闭上眼吧

进入正题,简单介绍 liny 的一些特性(可能有些我一时忘记了,但是不代表没有;可能有些我从来都不知道,但是不代表你不知道)

  1. 速度方面:

    在运行速度方面我不敢作出保证,因为还会有一些功能加入。不过 snippet 并不是插入时解析,而是预解析并缓存的

    在启动速度方面应该不成问题,snippet 是按需加载的,用的时候解析并缓存——也就是说你没有用到的 snippet 不会解析和缓存。

    另一方面,liny 的体积相当小巧,启动时只加载引擎和扩展,如果用上 autoload,那么 emacs 启动时 liny 占用的时间可以直接无视
    (其实我也承认,任何东西用上 autoload ,启动时间都可以无视……所以呢,liny 实际启动也还蛮快的)

  2. 定制方面:

    除了角色需要在插入时确定外,其它的基本都可以自定义:比如默认用 ${xxx} 和 $123 这样的标记作为 snippet 中的域,里面用 : 表示 prompt,用 $ 表示需要计算的表达式,这些都提供列表可以方便的定制……甚至可以同时使用多种不同的格式

    这个 snippet 里用的是另外一种格式,并且和其它的 snippet 互不影响

    当然,有些差别是解析方式造成的,所以要兼容 yas textmate 等格式可能比较难,其实运行时定制语法格式主要是为了扩展用的(好像目前还没有用到 -_-!!!)

    另外在编写的时候考虑到扩展的需求,总体来说还是比较容易扩展的……为了测试扩展的方便程度,我甚至还写了几个扩展

    这里

  3. 用户界面

    支持两种匹配模式:

    传统模式按模式和别名,通过一定规则生成相应的文件名,然后根据文件名加载,必须说这种方式比较二逼,
    比如说 for 的两种循环,很多语言里长得都跟亲兄弟似的,完全没有必要每种模式都写一遍;

    这种模式的好处是:snippet 文件中不需要定义额外的信息,比较简单……

    不过话说回来,很多人习惯在任何文件的头部写上注释,只恨不得把七大姑八大姨的芳名也写进去,
    反正写什么都是写,不如写点有用的东西不是?

    所以这种匹配模式我已经在第一时间给废掉了……当然,如果你就喜欢这个调调,启用也是很简单的……只要禁用另一个名为 smart-match 的扩展就可以了

    因为需要按需加载,所以需要有索引,而又要同时支持这二种匹配模式,所以索引文件也有二个……似乎有点二,不过总比每次启动要重新读取一遍要强

    第一种索引只要生成文件列表就可以了,相当简单,智能匹配也只是读取 snippet 文件中的相关字段

    智能匹配现在还不太完善,因为相关的规则还在摸索中,不过勉强可用了

  4. 功能方面

    首先按顺序编辑域和镜像域是必须的,这个不用多说;

    还有缩进的方式,是按定义时的还是按上下文的,这个也可以选择(目前是由一个变量控制,有时间改下,可以在 snippet 文件中单独控制),

    可能有点小问题(目前在我的使用中还没有出现相关情况,不过我知道那里有点问题,还没有空改,等摊上事儿的时候再说吧)

    skeleton ,参见 head 和 remove-overlays 两个 snippet

    另外还有一些特色的功能,通过扩展实现的:

    • 动态插入,f 这个 alias 的参数部分,随便输点什么按空格,后面会再插入一个域
    • 模板扩展,这个比较强大,不过目前还没有弄好,这块相当的复杂,co 这个 alias 多 tab 几下可以看到效果
    • 跳转时可以选择按插入时的顺序,或者是按 snippet 定义中的编号顺序
  5. 还有一些计划中的功能:

    • 嵌套定义域,由于支持模板扩展的需要,在解析时是匹配括号的,也就是说,忽略内嵌的域定义(其实这样反而更麻烦)。

      因此对于嵌套定义域不是原生支持,不过要支持它难度不大,主要是有没有更广泛的应用方式

      这个特性目前的应用方式我知道的只有:默认语句中的默认参数,如果不同意该语句,全部换掉,如果同意该语句,
      下一个域继续修改参数

    • 自动折行,这个可能要增加一个折行点的定义,貌似比较棘手

    • 增加一个快速添加 snippet 文件的接口

    ……差不多了,等发布0.01版的时候,就这些功能吧……先写在这里,如果我忘了,记得提醒我

最后,抱歉的是,目前 liny 还没有一个单独的版本库,所以
[

https://github.com/ran9er/init.emacs/tree/master/liny](https://github.com/ran9er/init.emacs/tree/master/liny " https://github.com/ran9er/init.emacs/tree/master/liny") 这个文件夹里的东西想办法全部下载,
当然你也可以直接同步我的配置文件,以表示对于 github.com 工作的支持和肯定。

在配置文件中这样写

(let ((key "\C-q")                                        ;; 这里是快捷键
      (path (expand-file-name "liny/liny.el" *init-dir*)) ;; 这里可以写 liny.el 的绝对路径
  (setq liny-expand-maybe-instead-command (key-binding key))
  (autoload 'liny-expand-maybe path "" t)
  (global-set-key key 'liny-expand-maybe))

Read More: