close
当前位置: 物联网在线 > 技术文库 > android >

打造酷炫AndroidStudio插件

前面几篇文章学习了AndroidStudio插件的基础后,这篇文章打算开发一个酷炫一点的插件。因为会用到前面的基础,所以如果没有看前面系列文章的话,请先返回。当然,如果有基础的可以忽略之。先看看本文实现的最终效果如下(好吧,很多人说看的眼花):

打造酷炫AndroidStudio插件

最终效果

虽然并没有什么实际用途,但是作为学习插件开发感觉挺有意思的。

1. 基本思路

基本思路可以归结如下几步:

通过 Editor 对象可以拿到封装代码编辑框的 JComponent 对象,即调用如下函数: JComponent component = editor.getContentComponent();

获取输入或删除的字符(或字符串。通过选中多个字符删除或粘贴则为字符串)。可以通过添加DocumentListener,监听文本变化。重写beforeDocumentChange函数,并通过DocumentEvent对象取得新的字符和旧的字符。分别通过函数: documentEvent.getNewFragment() 、 documentEvent.getOldFragment() 。它们代表着输入的字符串和删除的字符串。

将输入或删除的字符串在编辑框中显示出来。只需将各个字符串分别封装到 Jlabel 中,并将 JLabel 加入到 JComponent 中即可显示出输入或删除的字符串(或字符)。

获取用于显示各个字符串的 Jlabel 对象在 JComponent 中的坐标位置。添加 CaretListener ,监听光标的位置。每次光标位置发生变化,就刷新到临时变量中。当要添加一个 JLabel 时,获取当前的临时变量中保存的位置即为 Jlabel 应存放的位置。

动画效果。开启一个线程,对于输入的字符串,只需不断修改字体大小。对于删除的字符串,不断修改 JLabel 的位置和字体大小。

插件状态保存到本地。用户点击开启或者关闭插件以及其他开关选项,需要保存起来,下一次开启AndroidStudio时可以恢复。只需实现PersistentStateComponent接口即可。

用户未点击Action时,能自动注册DocumentListener。这主要是考虑到,用户开启了插件,下一次打开AndroidStudio时无需点击Aciton,直接输入时就能自动注册监听Document变化。由于注册DocumentListener需要Editor对象,而想要取得Editor对象只有两种方式:通过AnActionEvent对象的getData函数;另一种是通过DataContext对象,使用

PlatformDataKeys.EDITOR.getData(dataContext) 方法。显然第一种方法只能在 AnAction 类的 actionPerformed 和 update 方法中才能取得。因此只能考虑用第二种方法,而在前面文章中介绍过,监听键盘字符输入时,可以取得 DataContext 对象。即重写 TypedActionHandler 接口的 execute 函数,execute参数中传递了 DataContext 对象。

可以看到,以上用到的知识都是前面3篇文章中介绍过的内容,并不复杂。只有第6条没有介绍,本文中会学习本地持久化数据。

2. 插件状态本地持久化

先看看如何实现本地持久化。首先定义一个全局共享变量类GlobalVar,使之实现 PersistentStateComponent 接口。先来个视觉上的认识,直接看代码。

/** * 配置文件 * Created by huachao on 2016/12/27. */ @State( name = "amazing-mode", storages = { @Storage( id = "amazing-mode", file = "$APP_CONFIG$/amazing-mode_setting.xml" ) } ) public class GlobalVar implements PersistentStateComponent<GlobalVar.State> { public static final class State { public boolean IS_ENABLE; public boolean IS_RANDOM; } @Nullable @Override public State getState() { return this.state; } @Override public void loadState(State state) { this.state = state; } public State state = new State(); public GlobalVar() { state.IS_ENABLE = false; state.IS_RANDOM = false; } public static GlobalVar getInstance() { return ServiceManager.getService(GlobalVar.class); } }

使用 @State 注解指定本地存储位置、id等。具体实现基本可以参照这个模板写,就是重写loadState()和getState()两个函数。另外需要注意一下getInstance()函数的写法。基本模板就这样,没有什么特别的地方,依葫芦画瓢就行。

还有一点特别重要,一定要记得在 plugin.xml 中注册这个持久化类。找到 <extensions> 标签,加入 <applicationService> 子标签,如下:

<extensions defaultExtensionNs="com.intellij"> <!-- Add your extensions here --> <applicationService serviceImplementation="com.huachao.plugin.util.GlobalVar" serviceInterface="com.huachao.plugin.util.GlobalVar" /> </extensions>

这样写完以后,在获取数据的时候,直接如下:

private GlobalVar.State state = GlobalVar.getInstance().state; //state.IS_ENABLE //state.IS_RANDOM 3. 编写Action

主要包含2个Action: EnableAction 和 RandomColorAction 。 EnableAction 用于设置插件的开启或关闭, RandomColorAction 用于设置是否使用随机颜色。由于二者功能类似,我们只看看EnableAction的实现:

/** * Created by huachao on 2016/12/27. */ public class EnableAction extends AnAction { private GlobalVar.State state = GlobalVar.getInstance().state; @Override public void update(AnActionEvent e) { Project project = e.getData(PlatformDataKeys.PROJECT); Editor editor = e.getData(PlatformDataKeys.EDITOR); if (editor == null || project == null) { e.getPresentation().setEnabled(false); } else { JComponent component = editor.getContentComponent(); if (component == null) { e.getPresentation().setEnabled(false); } else { e.getPresentation().setEnabled(true); } } updateState(e.getPresentation()); } @Override public void actionPerformed(AnActionEvent e) { Project project = e.getData(PlatformDataKeys.PROJECT); Editor editor = e.getData(PlatformDataKeys.EDITOR); if (editor == null || project == null) { return; } JComponent component = editor.getContentComponent(); if (component == null) return; state.IS_ENABLE = !state.IS_ENABLE; updateState(e.getPresentation()); //只要点击Enable项,就把缓存中所有的文本清理 CharPanel.getInstance(component).clearAllStr(); GlobalVar.registerDocumentListener(project, editor, state.IS_ENABLE); } private void updateState(Presentation presentation) { if (state.IS_ENABLE) { presentation.setText("Enable"); presentation.setIcon(AllIcons.General.InspectionsOK); } else { presentation.setText("Disable"); presentation.setIcon(AllIcons.Actions.Cancel); } } }
(责任编辑:ioter)

用户喜欢...

用AndroidStudio开发自定义 Gradle plugin

利用AndroidStudio,编写自定义Gradle plugin MavenDeployer 发布plugin 使用Gradle plugin 简介 项目中引入自定义Gradle plugin一般有三种方法: 直接写在 build.gradle中. plugin源码放到rootProjectDir/buildSrc/src/main/groo...


手把手教你AndroidStudio多渠道打包

最近不断有朋友向我咨询AndroidStudio多渠道的打包方法,今天整理一下之前积累的打包套路,写一篇文章,手把手的教给大家。 说到多渠道,这里不得不提一下友盟统计,友盟统计是大家日常...


从零开始打造一个Android 3D立体旋转容器

回到正题,这次带来的效果,是一个Android 的3D立体旋转的效果。 当然灵感的来源,来自早些时间微博上看到的效果图。 非常酷有木有!作为程序猿我当然要把它加入我的下一个项目中啦!...


AndroidStudio之如何使用aar

aar 是一个类似于 jar 的文件格式。但是他们之间是有区别的。 jar :仅仅包含class和清单文件,没有资源文件。 aar :包含了class文件和资源文件。说白了就是Android的专属“jar” 将代码打包成...


AndroidStudio的Gradle插件版本更新简介

Android构建系统使用Android的Gradle插件通过Gradle的构建工具来支持构建Android程序。Android的Gradle插件独立于AndroidStudio运行,所以该插件和Gradle构建系统需要独立更新。 更新Android的Gradle插件 自动...


AndroidStudio模版

AndroidStudio模版可以很快捷的开发项目,增加开发效率,也能对项目的规范有一定的限制,也不用每次都写一些重复的代码,也能避免一些不必要的Bug出现,只需要注重具体代码实现就好. 二、...