2024最新IDEA插件开发+发布全流程 SelectCamelWords[选中驼峰单词](idea源代码)

2024最新IDEA插件开发(发布)-SelectCamelWords[选中驼峰单词](idea源代码)

参考文档

  • Jetbrains Idea插件开发文档: https://plugins.jetbrains.com/docs/intellij/welcome.html
  • 代码地址:https://github.com/yangfeng20/selected-camel-words
  • 整体流程文档:https://github.com/yangfeng20/idea-plugin-dev-guide/

视频教程地址

  • https://www.bilibili.com/video/BV1TZ421u7dX/

背景介绍

  • 痛点:在idea开发过程中,希望按需驼峰选中文本。
  • 现在默认是一整个单词选中,只有在设置–>智能按键 中开启了使用"CamelHumps单词"时能够驼峰选中。但是这种情况比较粗暴,直接全局开启了。但是在日常开发中,其实选中大部分是整个单词一起选中。只有少部分情况是按照驼峰选中。

image.png

  • 所以就需要一块插件,能够快捷开关驼峰选中的能力,仅在需要的时候开启。

安装Plugin DevKit插件

  • Idea 2023.3 以下版本可以不用安装当前插件。idea自带。2023.3版本及之后的版本没有当前查询,需要自己安装。

image.png

  • 插件商店搜索Plugin DevKit用于安装插件,安装完成之后建议先重启一下,不然可能开发工具可能出不来。

image.png

开启IDEA内部模式(使用UI检查器定位代码)

  • 主菜单栏–>帮助(Help)–>编辑自定义属性

image.png

  • 输入idea.is.internal=true开启内部模式,重启后生效。
  • 参考链接 https://plugins.jetbrains.com/docs/intellij/enabling-internal.html
  • 后面介绍如何使用UI检查器来定位代码位置

新建插件项目

  • 新建项目选择Idea插件(如果没有Plugin DevKit插件,这里就没有当前选项)。

image.png

  • 同时注意jdk版本需要和idea对应。参考:https://plugins.jetbrains.com/docs/intellij/creating-plugin-project.html#creating-a-plugin-with-new-project-wizard

image.png

修改Gradle相关配置

取消gradle构建

  • 先取消默认的gradle构建。先修改一些配置在重新构建。

修改依赖远程仓库地址

  • 修改build.gradle.kts中的repositories,注释中央仓库(mavenCentral)。配置阿里云地址。
repositories {//    mavenCentral()maven {url = uri("https://maven.aliyun.com/repository/public")}
}
  • 如果文件名不是kts结尾,而是gradle结尾,配置可能有些区别。

修改使用本地Idea调试

  • 注释intellij中的version和type(如果指定,需要下载),使用本地安装的idea进行调试。
  • 使用localPath设置本地idea的安装路径。参考:https://plugins.jetbrains.com/docs/intellij/tools-gradle-intellij-plugin.html#configuration-intellij-extension
intellij {localPath.set("D:\\Program Files\\JetBrains\\IntelliJ IDEA 2024.1.2")//    version.set("2023.2.6")//    type.set("IC") // Target IDE Platformplugins.set(listOf(/* Plugin Dependencies */))
}

image.png

重新加载Gradle变更

  • 点击Gradle图标重新加载变更。

image.png

  • 等待构建完成,初次可能比较慢,需要下载依赖等。构建完成之后,文件也就有高亮显示了。

image.png

其他build.gradle相关配置说明

  • https://plugins.jetbrains.com/docs/intellij/tools-gradle-intellij-plugin.html#ide-configuration

plugin.xml解读

  • 参考:https://plugins.jetbrains.com/docs/intellij/plugin-configuration-file.html#configuration-structure-overview
  • plugin.xml文件可以理解是当前插件的相关配置。是插件开发中非常重要的一个文件。

image.png

  • 构建完成之后,它会报错,是因为不能使用默认的模版字符。我们改掉就可以了。

image.png

防止报错

  • kotlin目录名修改为java。选中kotlin目录,按shift+f6修改目录名为java。不修改后面可能会报错。

image.png

创建Action

  • idea中的action概念可以理解为idea中的任意一个动作,点击了某个按钮,就会执行它绑定的Action类的代码。
  • 使用Plugin DevKit 创建一个Action。

image.png

  • 填写actionId,类名,功能名称,功能描述,添加到目标位置。

image.png

  • 创建成功之后就会生成一个Action类和在plugin中注册一个action,表说明他的位置。

image.png

运行插件

  • 点击gradle运行idea插件,它会重新启动一个idea环境,来运行idea插件。

image.png

  • 第一次运行可能较慢,需要等待一会儿。运行成功之后,在工具栏中显示了我们的插件Action。

image.png

  • 点击插件Action,后台也打印了相应的结果。

image.png

找不到你的插件注册的Action,并且控制台报错ClassNotFoundException?

  • 需要将上面说的kotlin目录修改为java。

控制台中文乱码,报错?

  • 修改build.gradle.kts,解决编译中文报错和控制台中文乱码问题。
tasks {// Set the JVM compatibility versionswithType<JavaCompile> {sourceCompatibility = "17"targetCompatibility = "17"// 解决编译时中文报错options.encoding = "UTF-8"}// 添加以下内容,解决运行时控制台中文乱码withType<JavaExec> {jvmArgs = listOf("-Dfile.encoding=UTF-8", "-Dsun.stdout.encoding=UTF-8", "-Dsun.stderr.encoding=UTF-8")}...
}

image.png

定位Action插入位置

  • 我是需要将Action插入到主菜单栏中的Tools菜单,要如何定位呢。这就只要使用我们之前说的内部工具,ui检查器了。
  • 开启内部模式之后,按ctrl+alt+鼠标左键点击ui,就能显示当前ui的详细信息。找到他的Group Id然后创建action时搜索选择就好了。

image.png

定位Idea相关代码

  • 在前面提到,idea设置中的智能按键有提供全局的驼峰选中能力,开启之后的就能够实现驼峰选中了。
  • 我们插件的逻辑也很简单,就是在编辑器中能够快捷开启这个开关。
  • 那我们要如何实现快捷开关呢,其实也很简单,我们只需要去看idea是怎么实现的就好了。

使用ui检查器定位智能按键逻辑

  • 在设置中使用ui检查器定位智能按键的配置类。

image.png

  • 打开idea源代码,搜索类EditorSmartKeysConfigurable

image.png

  • 然后搜索关键字camel,定位到配置,可以看到当前配置项有一个获取配置的方法,和更新配置的方法。然后查看这个editorSettings的来源。可以看到editorSettings的数据源是EditorSettingsExternalizable.getInstance()

image.png

  • 那这样就可以在我的项目中使用当前类的方法去设置快捷开关了。

编写插件逻辑(驼峰选中快捷开关)

  • 在我们的Action中获取到刚刚的编辑器设置,然后对配置项CamelWords的状态取反就可以了。
public class SelectCamelWordsAction extends AnAction {@Overridepublic void actionPerformed(AnActionEvent e) {// 获取到编辑器设置EditorSettingsExternalizable editorSettingsExternalizable = EditorSettingsExternalizable.getInstance();// 对之前的状态取反editorSettingsExternalizable.setCamelWords(!editorSettingsExternalizable.isCamelWords());}
}
  • 运行插件,通过ToolMenu中的SelectCamelWords就能够快捷开启关闭驼峰选中的功能。
  • 但是这还是很麻烦啊,不能够快捷启动。接下来就要使用监听器来监听按键实现对应的快捷启动。

使用监听器监听键盘按键

  • 参考文档:https://plugins.jetbrains.com/docs/intellij/plugin-listeners.html#defining-application-level-listeners
  • 在plugin.xml中注册应用激活时监听,并绑定到我们的监听器中。
<applicationListeners><listener class="com.maple.plugindemo.MyKeyListener" topic="com.intellij.openapi.application.ApplicationActivationListener"/>
</applicationListeners>
  • 添加我们的自定义分发器
public class MyKeyListener implements ApplicationActivationListener {private final KeyEventDispatcher dispatcher = new MyKeyEventDispatcher();@Overridepublic void applicationActivated(@NotNull IdeFrame ideFrame) {KeyboardFocusManager.getCurrentKeyboardFocusManager().addKeyEventDispatcher(dispatcher);}@Overridepublic void applicationDeactivated(@NotNull IdeFrame ideFrame) {KeyboardFocusManager.getCurrentKeyboardFocusManager().removeKeyEventDispatcher(dispatcher);}private static class MyKeyEventDispatcher implements KeyEventDispatcher {// 分发器逻辑}
}
  • 在自定义的事件分发器中监听shift+ctrl+win按下,开启驼峰选中。win键抬起,关闭驼峰选中。
private static class MyKeyEventDispatcher implements KeyEventDispatcher {private boolean shiftPressed = false;private boolean ctrlPressed = false;private boolean winPressed = false;private final EditorSettingsExternalizable editorSettingsExternalizable = EditorSettingsExternalizable.getInstance();@Overridepublic boolean dispatchKeyEvent(KeyEvent e) {int keyCode = e.getKeyCode();int id = e.getID();if (id == KeyEvent.KEY_PRESSED) {switch (keyCode) {case KeyEvent.VK_SHIFT:shiftPressed = true;break;case KeyEvent.VK_CONTROL:ctrlPressed = true;break;case KeyEvent.VK_WINDOWS:winPressed = true;break;}if (shiftPressed && ctrlPressed && winPressed) {// 开启驼峰选中System.out.println("Shift + Ctrl + Win 按下!");editorSettingsExternalizable.setCamelWords(true);}} else if (id == KeyEvent.KEY_RELEASED) {switch (keyCode) {case KeyEvent.VK_WINDOWS:if (shiftPressed && ctrlPressed) {// 关闭驼峰选中System.out.println("Win 键抬起!");editorSettingsExternalizable.setCamelWords(false);}winPressed = false;break;case KeyEvent.VK_SHIFT:shiftPressed = false;break;case KeyEvent.VK_CONTROL:ctrlPressed = false;break;}}return false; // 继续分发事件}
}
  • 至此,插件逻辑就已经大功告成了。由于我没有mac,不清楚mac的快捷键,就没有适配mac快捷键。大家也可以去我的仓库提交pr。

打包插件

  • 通过gradle的task打包插件。构建jar包,最终会输出到build–>libs下

image.png

本地安装验证

  • 打开插件仓库,选择本地安装,找到打包之后的jar

image.png

  • 安装成功,确认,然后测试插件

image.png

发布插件

  • 进入jetbrains插件开发平台:https://plugins.jetbrains.com/developers/intellij-platform
  • 点击登录,或者注册账号

image.png

  • 点击Upload Plugin上传插件,上传插件jar包,填写相关信息,点击upload Plugin.

image.png

  • 上传成功,等待审核。

image.png

兼容不同的idea版本

  • idea-version参考: https://plugins.jetbrains.com/docs/intellij/plugin-configuration-file.html#idea-plugin__idea-version
  • 内部版本号映射参考:https://plugins.jetbrains.com/docs/intellij/build-number-ranges.html#earlier-versions
  • 修改build.gradle.kts中的patchPluginXml,它用来不是兼容的idea版本。该值会覆盖plugin.xml中的idea-versin标签,所有可以直接把兼容版本写在这里。
patchPluginXml {// 最低版本sinceBuild.set("232")// 最高版本untilBuild.set("242.*")
}
<idea-version since-build="232" until-build="242.*"/>
  • 要做到多版本兼容,就是要将最低版本设置的尽可能的小,但是同时需要你设置的版本有你插件当前使用的api。例如applicationListeners就在193.0之后发布,我的最低版本就只能设置193.0。最大版本不设置。

image.png

  • 发布前jetbrains会校验当前插件的兼容性,我这边就是校验通过,显示可以使用的版本。

image.png

后记

  • 插件比较简单,主要是解决开发中的痛点,然后监听按键按下和释放的逻辑是直接让ai写的,可能有一些小bug。
  • 然后mac端我不太清楚选中的快捷键是什么,也就没有做兼容。
  • 感兴趣的话,可以点个在github 点个star。欢迎大家把项目拉下来,然后提交pr。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/32069.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Mybatis框架的缓存

Mybatis框架的缓存 一.为什么使用缓存 缓存(cache&#xff09;的作用是为了减去数据库的压力&#xff0c;提高查询性能。缓存实现的 原理是从数据库中查询出来的对象在使用完后不要销毁&#xff0c;而是存储在内存&#xff08;缓存&#xff09; 中&#xff0c;当再次需要获取…

windows-docker-本地部署-前端

前置条件 docker已有需要打包的文件也已经写好了 打包镜像 ip地址修改 需要根据自身修改的文件 .env.local文件存放你前端访问的端口 172.24.240.1:这部分是自己电脑的ip 如何查看本机ip&#xff0c;使用IPV4的地址。 #本地 #API_HOST_URLhttp://172.24.240.1:8091打包文…

Excel导出实例

在上一节的基础上&#xff0c;本文演示下如何导出excel数据。 Excel导出操作演示 继承ocean-easyexcel SDK <dependency><groupId>com.angel.ocean</groupId><artifactId>ocean-easyexcel</artifactId><version>1.0.0</version> …

架构设计 - 网站性能优化之静态资源CDN配置

摘要: web 应用业务缓存通常3级: 一级缓存:JVM 本地缓存 二级缓存:Redis集中式缓存 三级缓存:Nginx Proxy Cache 缓存 或 Nginx Lua 缓存 四级缓存:静态资源CDN缓存 页面静态化 本文主要分享 怎样通过CDN缓存静态资源的方式 提高系统性能和响应速度。 WEB应用通过CD…

【机器学习】正则卷积群理论及Python代码实现

1. 引言 1.1.卷积神经网络CNN 卷积神经网络&#xff08;CNN&#xff09;的数学模型是深度学习中用于处理图像和其他高维数据的关键组成部分。那么&#xff0c;CNN究竟是什么呢&#xff1f; 总结起来&#xff0c;CNN网络主要完成以下操作&#xff1a; 卷积操作&#xff08;Co…

无线麦克风一拖二哪个牌子好,揭秘目前音质最好的麦克风

在自媒体的世界里&#xff0c;无线领夹麦克风已经成了一种标准配置&#xff0c;它受到广大视频创作者的青睐。无论是刚刚踏入短视频领域的新手&#xff0c;还是已经拥有丰富经验的资深博主&#xff0c;都深知一款好的领夹麦克风对于提升视频音频质量的重要性。它不仅能帮助创作…

SQLCMD完全指南:掌控 SQL Server

SQL Server 拥有被广泛认可的一流管理工具——SQL Server Management Studio&#xff08;简称 SSMS&#xff09;。它提供了丰富的功能&#xff0c;极大地简化了开发人员和数据库管理员&#xff08;DBA&#xff09;的工作。 目录 SQLCMD 入门使用 SQLCMD 连接 SQL ServerSQLCMD …

Java和C语言中基础概念中的区别有哪些?

Java和C语言中基础概念中的区别有哪些&#xff1f; 标识符数据类型运算符加号%号& 和 | 关系表达式函数声明代码规范数组 以下是Java和C语言在一些基础概念中的区别&#xff08;不包含面向对象等的高级知识&#xff09; 标识符 在Java中&#xff0c;标识符可以由数字、字母…

【Java】字节数组 pcm 与 wav 格式互转(附原理概述)

前言 最近实现了一个文字转语音的功能&#xff0c;语音引擎返回的是pcm格式的数据。需要转化成wav格式前端才能播放。本文首先会给出解决方案&#xff0c;后续会讲背后的原理。 场景 1. pcm wav 转化工具类 入参和出参都为byte[]&#xff0c;理论上有了 byte[] 就可以输出…

基于单片机的智能窗户控制系统的设计

摘 要&#xff1a; 根据单片机技术和现代传感器技术 &#xff0c; 本文主要针对基于单片机的智能窗户控制系统的设计进行探讨 &#xff0c; 仅供参考 。 关键词&#xff1a; 单片机 &#xff1b; 智能窗户 &#xff1b; 控制系统 &#xff1b; 设计 在现代科学技术持续发展的带…

Python爬虫基础以及示例讲解

爬虫简介 网络爬虫 爬虫指在使用程序模拟浏览器向服务端发出网络请求&#xff0c;以便获取服务端返回的内容。 但这些内容可能涉及到一些机密信息&#xff0c;所以爬虫领域目前来讲是属于灰色领域&#xff0c;切勿违法犯罪。 爬虫本身作为一门技术没有任何问题&#xff0c;关…

Docker之overlay2的迁移

原因 docker默认将文件及其容器放置在了系统盘的挂载区内&#xff0c;如果长期使用会发现系统挂载区被overlay2挤爆了,因此在一开始我们将其迁移在大容量外挂磁盘上,就可以避免系统盘被挤爆,放心使用. 具体操作 # 停止容器 systemctl stop docker# 修改容器配置&#xff0c…

等差数列和等比数列的介绍及在Java编程中的实现

等差数列 (Arithmetic Sequence) 定义&#xff1a;等差数列是指相邻两项的差相等的数列&#xff0c;这个差值叫做“公差”&#xff08;d&#xff09;。 公式&#xff1a; 第 ( n ) 项的公式&#xff1a; 前 ( n ) 项和的公式&#xff1a; 示例&#xff1a; 假设第一项 (…

AI+前端技术的结合(实现图片识别功能)

随着人工智能技术的不断发展&#xff0c;AI在前端设计页面中的应用变得越来越普遍。比如&#xff1a;在电商平台上&#xff0c;可以利用对象检测技术实现商品的自动识别和分类&#xff1b;人脸识别&#xff1b;车辆检测&#xff1b;图片识别等等......其中一个显著的应用是在图…

数据结构_优先级队列(堆)

目录 一、优先级队列 1.1 堆 1.2 PriorityQueue接口 二、模拟实现优先级队列 2.1 初始化 2.2 创建大根堆 (向下调整) 2.3 堆的插入 2.4 堆的删除 2.5 堆排序 总结 一、优先级队列 优先级队列是一种特殊的队列&#xff0c;其出队顺序与入队顺序无关&#xff0c;而与优…

易支付宝塔一键部署项目 懒人专用包 制作

宝塔一键部署说明 https://www.bt.cn/bbs/thread-33063-1-1.html 1. auto_install.json {"php_ext":"fileinfo","chmod":[],"success_url":"install/?step3&jump1","php_versions":"80","db…

架构师指南:现代 Datalake 参考架构

这篇文章的缩写版本于 2024 年 3 月 26 日出现在 The New Stack 上。 旨在最大化其数据资产的企业正在采用可扩展、灵活和统一的数据存储和分析方法。这一趋势是由企业架构师推动的&#xff0c;他们的任务是制定符合不断变化的业务需求的基础设施。现代数据湖体系结构通过将数…

逻辑地址 线性地址 物理地址 Linux kernel 内存管理设计

linux kernel 2.6以后的MM&#xff0c;受到了兼容 risc arch cpu 的 MM 的启发&#xff0c;新的 MM 架构对 x86 上任务切换的效率上也有明显提高。 新的MM架构&#xff0c;GDT 不再随着进程的创建与结束而创建和删除 新的表项。 TSS段 也只有一个&#xff0c;进程切换时&…

深度学习入门2—— 神经网络的组成和3层神经网络的实现

由上一章结尾&#xff0c;我们知道神经网络的一个重要性质是它可以自动地从数据中学习到合适的权重参数。接下来会介绍神经网络的概要&#xff0c;然后再结合手写数字识别案例进行介绍。 1.神经网络概要 1.1从感知机到神经网 我们可以用图来表示神经网络&#xff0c;我们把最…

上位机图像处理和嵌入式模块部署(mcu之静态库生成和使用)

【 声明&#xff1a;版权所有&#xff0c;欢迎转载&#xff0c;请勿用于商业用途。 联系信箱&#xff1a;feixiaoxing 163.com】 很多同学做了很长时间的mcu和keil开发&#xff0c;都认为keil工程中必须包含所有的源代码&#xff0c;其实这是不对的。如果有一些代码我们不希望别…