自定义IDEA代码提示插件开发

背景简介

在项目开发过程中,随着代码的积累和重构,自然地积累了一些代码框架和代码模板,通过IDEA、Goland等编译器的代码提示工具便捷地生成模板代码,可以避免相似代码的重复编写,在部分开发场景下大大提高开发效率。

代码提示工具

简介

编译器自带了代码提示能力,可以手动开启、关闭、设置排序方式等。代码提示能力一般默认开启,在日常开发中会频繁使用。扩展插件后,这些基本的设置仍然生效,可以作用于自定义插件添加的结果中。
在这里插入图片描述
注:由于在日常的开发中会频繁使用默认的代码提示工具,自定义插件对默认结果的影响需要尽量降低。

自定义代码提示

基本方法

自定义代码提示基本思路是对IDEA编译器的代码提示工具进行扩展,对提示结果进行二次加工后返回。
通过插件对代码提示(CompletionContributor)进行扩展的方式有两种:

  1. 实现自定义类。
  2. 覆盖fillCompletionVariants方法,这种方式是更便捷和灵活的

实现方案

CompletionContributor

CompletionContributor是自动补全的贡献器,是实现自定义代码提示必须关注的内容,它的输入是上下文信息和当前的字符串(前缀),返回匹配的结果。我们要做的就是覆盖这个类的fillCompletionVariants方法。这个方法在每次Contributor的默认流程执行完后都会执行,因此可以覆盖这个方法对结果进行修改

override fun fillCompletionVariants(parameters: CompletionParameters, result: CompletionResultSet){}
  1. 参数CompletionResultSet是根据默认的前缀匹配器匹配到的结果集合(LookupElements)。
  2. 参数 CompletionParameters保存着一些上下文,包括当前的文件、位置等信息,可以依据这个参数,再在不同的场景下执行不同的补全策略
  3. 排序的实现是通过给结果赋予权重实现的 PrioritizedLookupElement.withPriority。目前我们通过字符串与模板key的编辑距离赋予权重,保证更匹配的结果排在更前的位置。
  4. 使用LookupElementBuilder来创建元素,可以对结果的展示形式进行更灵活的配置。
                result.addElement(PrioritizedLookupElement.withPriority(LookupElementBuilder.create(codeMap[key]!!).withPresentableText("${key}->${codeMap[key]!!}").  // 替换提示文本但是不改变补全文本//withLookupString("额外匹配文本").     // 额外匹配文本//withItemTextForeground(Color.BLUE). // 文本颜色//withIcon(ImageIcon("/Users/bytedance/go/src/code.byted.org/ecom/AIXCodeCompletionHelper/img.png")).// 图标withTypeText("AIXcode")//.bold() // 加粗, TextDistanceUtil.getSimilarity(prefix, key)*2000.0))
PrefixMatcher

PrefixMatcher是前缀匹配器,是实现自定义代码提示需要关注的另一个重点,它比较重要的两个职责是匹配和排序。

  1. 匹配时需要看结果集中的内容是否和前缀匹配(默认contain)
  2. 排序时依据权重、字母顺序等等进行排序。

默认的匹配器中,权重的优先级是最高的,我们在结果中依据匹配程度赋予权重大小,就可以实现命中代码模板的结果的正确排序,不需要重新实现一个匹配器。

总结

只需要简单的开发,就可以自定义地扩展代码提示工具,通过key-template的方式可以实现模板代码的快速生成,并结合个人的编码习惯自定义各种模板代码。如果有一定的机器学习基础,还可以尝试使用自己的代码训练专用的预测模型,实现适用性更强的代码提示工具。但是在模型准确率较低的时候,可能会降低使用体验。


本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场,不承担相关法律责任。如若转载,请注明出处。 如若内容造成侵权/违法违规/事实不符,请点击【内容举报】进行投诉反馈!

相关文章

立即
投稿

微信公众账号

微信扫一扫加关注

返回
顶部