【Android 组件化】路由组件 ( 注解处理器获取被注解的节点 )

举报
韩曙亮 发表于 2022/01/10 23:41:55 2022/01/10
【摘要】 文章目录 一、设置支持的注解类型二、注解处理器中打印日志三、主应用中使用注解四、注解处理器 获取注解节点五、博客资源 组件化系列博客 : 【Android 组件化】从模块化到组件化【A...

在这里插入图片描述

组件化系列博客 :


【Android 组件化】路由组件 ( 路由组件结构 ) 博客中介绍了组件化中的 " 路由组件 " , 分为 " 自定义注解模块 " , " 注解处理器模块 " , " 依赖库模块 " 3 3 3 个模块 ;

本篇博客中讲解 " 注解处理器 " 开发 ;





一、设置支持的注解类型



在 注解处理器 类上使用 @SupportedAnnotationTypes({}) 注解 , 为该 注解处理器 配置支持的注解 , 在大括号中输入 注解的完整 " 包名.类名 " 字符串 , 多个注解名称之间使用逗号 , 隔开 ;

@SupportedAnnotationTypes({"kim.hsl.router_annotation.Route"})
public class RouterProcessor extends AbstractProcessor {
}

  
 
  • 1
  • 2
  • 3

也可以在 getSupportedAnnotationTypes 函数中设置支持的注解类型 ;

    /**
     * 指明注解处理器可以处理哪些注解
     *
     * @return 字符串类型 Set 集合
     */
    @Override
    public Set<String> getSupportedAnnotationTypes() {
        return super.getSupportedAnnotationTypes();
    }

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

上述两种方法二选一 ;





二、注解处理器中打印日志



注解处理器 中 , 使用 javax.annotation.processing.Messager 打印数据 , 在 init 方法中 , 通过调用 ProcessingEnvironment processingEnvironment 参数的 getMessager 方法 , 获取 Messager 对象 ;


调用 Messager 对象的 printMessage 方法 , 打印日志 , 传入第 1 1 1 个参数是日志级别 , 一般设置成 Diagnostic.Kind.NOTE 参数 , 第二个参数是要打印的字符串 ;


打印结果输出到 Build 面板中 ;

在这里插入图片描述


代码示例 :

public class RouterProcessor extends AbstractProcessor {

    /**
     * 注解处理器中使用 Messager 对象打印日志
     */
    private Messager mMessager;

    /**
     * 该函数在初始化时调用 , 相当于构造函数
     * @param processingEnvironment
     */
    @Override
    public synchronized void init(ProcessingEnvironment processingEnvironment) {
        super.init(processingEnvironment);
        // 获取打印日志接口
        mMessager = processingEnvironment.getMessager();
        mMessager.printMessage(Diagnostic.Kind.NOTE, "Messager Print Log");
    }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19




三、主应用中使用注解



在主应用的 build.gradle 构建脚本中 , 引入注解处理器 与 注解类 依赖 ,

dependencies {
    // 引入注解处理器
    annotationProcessor project(':router-compiler')
    // 引入注解
    implementation project(':router-annotation')
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

Java 类中使用 Route 注解 ;

package kim.hsl.component;

import android.app.Activity;
import android.os.Bundle;

import androidx.annotation.Nullable;

import kim.hsl.router_annotation.Route;

@Route(path = "app/MainActivity")
public class MainActivity extends Activity {
    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17




四、注解处理器 获取注解节点



使用 @Route 注解的节点都是类 , 因此注解节点的类型都是 TypeElement 类型 ;

编译时 , 注解处理器会自动获取使用了 @Route 注解的节点 , 在 注解处理器 的 process 方法中 , 可以获取到这些使用了注解的 TypeElement 节点 ;

package kim.hsl.router_compiler;

import com.google.auto.service.AutoService;

import java.util.Set;

import javax.annotation.processing.AbstractProcessor;
import javax.annotation.processing.Messager;
import javax.annotation.processing.ProcessingEnvironment;
import javax.annotation.processing.Processor;
import javax.annotation.processing.RoundEnvironment;
import javax.annotation.processing.SupportedAnnotationTypes;
import javax.annotation.processing.SupportedSourceVersion;
import javax.lang.model.SourceVersion;
import javax.lang.model.element.TypeElement;
import javax.tools.Diagnostic;

// 自动注册注解处理器
@AutoService(Processor.class)
// 支持的注解类型
@SupportedAnnotationTypes({"kim.hsl.router_annotation.Route"})
// 支持的 Java 版本
@SupportedSourceVersion(SourceVersion.RELEASE_8)
public class RouterProcessor extends AbstractProcessor {

    /**
     * 注解处理器中使用 Messager 对象打印日志
     */
    private Messager mMessager;

    /**
     * 该函数在初始化时调用 , 相当于构造函数
     * @param processingEnvironment
     */
    @Override
    public synchronized void init(ProcessingEnvironment processingEnvironment) {
        super.init(processingEnvironment);
        // 获取打印日志接口
        mMessager = processingEnvironment.getMessager();
        mMessager.printMessage(Diagnostic.Kind.NOTE, "Messager Print Log");
    }

    /**
     * 该函数在注解处理器注册时自动执行, 是处理注解的核心函数
     *
     * Set<? extends TypeElement> set 参数 : 该集合表示使用了相关注解的节点的集合
     *
     * @param set
     * @param roundEnvironment
     * @return
     */
    @Override
    public boolean process(Set<? extends TypeElement> set, RoundEnvironment roundEnvironment) {
        for (TypeElement typeElement: set){
            mMessager.printMessage(Diagnostic.Kind.NOTE, "SupportedAnnotationTypes : " + typeElement.getQualifiedName());
        }
        return false;
    }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59

在编译时 , 在 " Build " 面板中的 " Build Output " 模块中 , 输出 注解处理器 使用 Messager 打印的日志 ;

打印的内容是检测到的在 Android 应用中所有使用到的 " kim.hsl.router_annotation.Route" 类型注解的节点 ;

在主应用中使用了 @Route(path = "app/MainActivity") 节点修饰了 MainActivity , 使用了一次该注解 , 因此在 注解处理器 的 process 方法中 , 可以获取到该注解信息 ;

在 Java 代码中使用了多少次 @Route 注解 , 则在 注解处理器 的 process 方法中就可以获取到对应次数的 注解节点 ;


编译时输出的日志内容 :

: Messager Print Log
注: SupportedAnnotationTypes : kim.hsl.router_annotation.Route

  
 
  • 1
  • 2

在这里插入图片描述





五、博客资源



博客源码 :



在这里插入图片描述

文章来源: hanshuliang.blog.csdn.net,作者:韩曙亮,版权归原作者所有,如需转载,请联系作者。

原文链接:hanshuliang.blog.csdn.net/article/details/116902643

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。