上一篇博客 【Android APT】编译时技术 ( 编译时注解 和 注解处理器 依赖库 ) 中创建并配置了 annotation 编译时注解 依赖库 和 annotation-compiler 注解处理器 依赖库 ;
本博客开始进行开发 编译时注解 依赖库 ;
开发 annotation 编译时注解 依赖库 ;
右键点击包名 , 选择 " New / Java Class " 选项 ,
在弹出的对话框中 , 选择 " Annotation " 注解对话框 , 然后输入注解名称 BindView ,
注解源码开发 :
package kim.hsl.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.CLASS)
public @interface BindView {
int value();
}
元注解解析 :
使用 @Target(ElementType.FIELD) 元注解标注该 BindView 注解 , 说明该 @BindView 注解是作用于成员变量的 ;
使用 @Retention(RetentionPolicy.CLASS) 标注 BindView 注解 , 说明该注解是 编译时注解 ;
注解属性解析 :
使用 value 作为注解属性名 , 并且只有一个 注解属性 , 因此该注解在使用的时候 , 为注解属性赋值可以省略 " value = " , 直接传入注解属性值 ;
注释掉之前的 ButterKnife 的 编译时注解 和 注解处理器 , 使用应用中自己开发的 编译时注解 和 注解处理器 ;
build.gradle 构建脚本 依赖库相关配置 如下 :
dependencies {
//implementation 'com.jakewharton:butterknife:10.2.3'
//annotationProcessor 'com.jakewharton:butterknife-compiler:10.2.3'
annotationProcessor project(path: ':annotation-compiler')
implementation project(path: ':annotation')
}
在 MainActivity 中模仿 ButterKnife 使用 @BindView 注解 , 这是我们自定义的注解 ;
package kim.hsl.apt;
import android.os.Bundle;
import android.widget.TextView;
import androidx.appcompat.app.AppCompatActivity;
import kim.hsl.annotation.BindView;
public class MainActivity extends AppCompatActivity {
@BindView(R.id.hello)
TextView hello;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//hello.setText("ButterKnife");
}
}
下一步开始使用 注解处理器 , 处理上述注解 ;
注解处理器 工作机制 : 当程序在编译时 , 执行注解处理器 , 注解处理器会搜索整个程序中 , 使用到 BindView 注解的位置 , 并获取注解的相关信息 , 所在字节码文件 , 作用位置 ( 类 / 方法 / 字段等 ) ;
注解分类 :
① 源码期注解 : 注解保留到源码阶段 , 只有当类是 .java 文件时才能看到 , 一旦编译成 .class 字节码文件 , 该注解就消失了 , 如 @Override 仅在编译时查看父类是否有该方法 ;
② 编译时注解 : 注解保留到字节码阶段 ;
③ 运行时注解 : 注解保留到运行时 ;
源码期注解 与 编译时注解 对比示例 :
查看 MainActivity.java 源码 : 该源码中有两个注解 @BindView 和 @Override 两个注解 ;
查看 BindView 注解的源码如下 , 其中 BindView 注解是被 @Retention(RUNTIME) 修饰的 , 说明该注解是 运行时注解 , 该注解需要从源码 到 字节码 一直保留 , 知道运行时才开始解析该注解 ;
@Retention(RUNTIME) @Target(FIELD)
public @interface BindView {
/** View ID to which the field will be bound. */
@IdRes int value();
}
查看 Override 注解的源码如下 , 该注解被 @Retention(RetentionPolicy.SOURCE) 修饰 , 说明该注解是 源码期注解 , 注解信息仅在源码阶段保存 , 一旦编译成字节码文件 , 高注解就被删除了 ;
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.SOURCE)
public @interface Override {
}
编译应用后 , 查看 MainActivity.class 字节码文件 , 该字节码文件在 " APT\app\build\intermediates\javac\debug\classes\kim\hsl\apt " 目录下 ;
字节码文件中的 @Override 注解已经消失 , @BindView 注解还存在 ;
@Override 注解是 源码期注解 , 只保留到源码期 , 编译时使用该注解 , 编译完成后 , 该注解就被删除了 ;
@BindView 注解 是 运行时注解 , 该注解需要在运行时使用 , 需要一直保留到运行时 ;
博客源码 :
扫码关注腾讯云开发者
领取腾讯云代金券
Copyright © 2013 - 2025 Tencent Cloud. All Rights Reserved. 腾讯云 版权所有
深圳市腾讯计算机系统有限公司 ICP备案/许可证号:粤B2-20090059 深公网安备号 44030502008569
腾讯云计算(北京)有限责任公司 京ICP证150476号 | 京ICP备11018762号 | 京公网安备号11010802020287
Copyright © 2013 - 2025 Tencent Cloud.
All Rights Reserved. 腾讯云 版权所有