注解(2)-- 定义自己的Annotation Processor

2018-02-08 10:22:40来源:http://blog.cyning.cc/2017/08/17/annotation-for-andrroid-2/作者:小李的博客人点击

分享

大家还记得 [JakeWharton](https://github.com/JakeWharton) 写的翻遍ui注解的库 butterknife 么?


之前我们都是使用findviewById来查找view,有了 butterknife 我们摆脱了这种重复代码,通过注解我们解放了生产力,我们可以把更多的经理放到我们的业务和整体的架构上来,而不是不断重复的代码。


在开始前我们需要了解一下 Annotation Processor ,使用 Annotation Processor 来自动生成可以提高编写代码的效率和质量,手工编写毕竟容易出现纰漏,工具自动生成是有质量保证的。Annotation Processor 主要涉及 3 部分,注解本身(Annotation)、注解处理器(Annotation Processor)以及 如何使用注解器。


Hello world

万事先从一个HelloWorld开始,我们可以通过 Annotation Processor 来自己生成一个类,这个类中的main方法可以打印hello world。


声明注解

需要我们通过Android Studio来新建一个java lib项目 helloAnotation。


其中需要声明一个注解如下:


@Target(ElementType.TYPE)
@Retention(RetentionPolicy.SOURCE)
public @interface HelloWorld {
int version()default 0;
}

Annotation Processor

再来一个java lib项目helloAnotation需要继承 AbstractProcessor 的Processor类的通过 javapoet 生成相关的方法和类。


后面会详细介绍 AbstractProcessor 和 javapoet ,我们先来自己定义一个Processor类。



Processor类
import com.squareup.javapoet.JavaFile;
import com.squareup.javapoet.MethodSpec;
import com.squareup.javapoet.TypeSpec;
import java.io.IOException;
import java.util.Collections;
import java.util.Set;
import javax.annotation.processing.AbstractProcessor;
import javax.annotation.processing.RoundEnvironment;
import javax.lang.model.element.Modifier;
import javax.lang.model.element.TypeElement;
public class HelloWordextends AbstractProcessor{
@Override
public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment roundEnv){
MethodSpec main = MethodSpec.methodBuilder("main")
.addModifiers(Modifier.PUBLIC, Modifier.STATIC)
.returns(void.class)
.addParameter(String[].class, "args")
.addStatement("$T.out.println($S)", System.class, "Hello, World! " )
.build();
TypeSpec helloWorld = TypeSpec.classBuilder("HelloWorldC")
.addModifiers(Modifier.PUBLIC, Modifier.FINAL)
.addMethod(main)
.build();
JavaFile javaFile = JavaFile.builder("com.example.helloworld", helloWorld)
.build();
try {
javaFile.writeTo(processingEnv.getFiler());
} catch (IOException e) {
e.printStackTrace();
}
return false;
}
@Override
public Set<String> getSupportedAnnotationTypes(){
return Collections.singleton("me.cyning.anotationan.HelloWorld");
}
}

如今已经编写完毕了 processor,需要告知系统,我们创建/ src/main/resources/META-INF/services 文件夹,同时在这个文件夹下创建 javax.annotation.processing.Processor 文件,在这个文件下,写入我们的processor的完全路径。


me.cyning.anotationcore.HelloWord

build.gradle


implementation 'com.squareup:javapoet:1.7.0'
implementation 'com.google.guava:guava:23.3-android

使用

在主项目的入口类TestActivity的类使用这个注解


@HelloWorld
public class TestActivityextends AppCompatActivity

再次编译就可以在你的主项目的build/generated/source/apt/debug下看到我们生成的类。


build.gradle


annotationProcessorproject(':AnotationCompiler')
implementation project(': helloAnotation')

居然真的有这个类在我们的build文件夹下,




最新文章

123

最新摄影

闪念基因

微信扫一扫

第七城市微信公众平台