【IOC 控制反转】Android 事件依赖注入 ( 事件依赖注入具体的操作细节 | 获取 Activity 中的所有方法 | 获取方法上的注解 | 获取注解上的注解 | 通过注解属性获取事件信息 )

简介: 【IOC 控制反转】Android 事件依赖注入 ( 事件依赖注入具体的操作细节 | 获取 Activity 中的所有方法 | 获取方法上的注解 | 获取注解上的注解 | 通过注解属性获取事件信息 )

文章目录

前言

一、获取 Activity 中的所有方法

二、获取方法上的注解

三、获取注解上的注解

四、通过注解属性获取相关事件信息

前言

Android 依赖注入的核心就是通过反射获取 类 / 方法 / 字段 上的注解 , 以及注解属性 ; 在 Activity 基类中 , 获取该注解 以及 注解属性 , 进行相关操作 ;


在博客 【IOC 控制反转】Android 事件依赖注入 ( 事件三要素 | 修饰注解的注解 | 事件依赖注入步骤 ) 中 , 定义了 2 22 个注解 ,


第一个是方法上的注解 , 用于修饰方法 ;

第二个是修饰注解的注解 , 该注解用于配置注入的方法 ( 事件监听方法 | 监听器类型 | 监听器回调方法 ) ;

事件依赖注入比较复杂 , 涉及到动态代理 , 本博客分析 【IOC 控制反转】Android 事件依赖注入 ( 事件依赖注入代码示例 ) 事件依赖注入的详细步骤 ;



本博客的核心是 : 使用动态代理 , 创建 View.OnClickListener 或 View.OnLongClickListener 或 View.onTouchListener 等接口的动态代理类 ;

拦截相应的 onClick , onLongClick , onTouch 方法 , 执行自己的方法 , 其它方法正常执行 ;






一、获取 Activity 中的所有方法


通过反射获取 Activity 类 , 然后调用 Class 的 getDeclaredMethods 方法 , 获取 Activity 中的所有方法 ;


// 获取 Class 字节码对象
Class<? extends Activity> clazz = activity.getClass();
// 获取所有方法
Method[] methods = clazz.getDeclaredMethods();






二、获取方法上的注解


获取方法的所有注解 , 获取的是 @OnClick({R.id.textView}) // 事件注入 注解 ;


调用 Method 方法的 getDeclaredAnnotations 方法 , 获取方法上的注解数组 ;


   

// 循环遍历类的方法
        for (int i = 0; i < methods.length; i ++) {
            // 获取方法的所有注解
            Annotation[] annotations = methods[i].getDeclaredAnnotations();
  }





三、获取注解上的注解


遍历上个步骤获取的注解数组 , 每个注解上可能有多个修饰注解的注解 , 如下注解是 OnClick 上的 3 33 个注解 ;


@Target(ElementType.METHOD)   // 该注解作用于方法上
@Retention(RetentionPolicy.RUNTIME)    // 注解保留到运行时
@EventBase(
        listenerSetter = "setOnClickListener",
        listenerType = View.OnClickListener.class,
        callbackMethod = "onClick")
public @interface OnClick {
    int[] value();    // 接收 int 类型数组
}


调用 annotationType 方法 , 获取注解的类型 , 只处理 @EventBase 注解 ;


       

// 遍历所有的注解
            for (int j = 0; j < annotations.length; j ++) {
                // 获取注解类型
                Class<? extends Annotation> annotationType = annotations[j].annotationType();
                // 获取 @EventBase 注解
                EventBase eventBase = annotationType.getAnnotation(EventBase.class);
                if (eventBase == null) {
                    // 如果没有获取到 EventBase 注解 , 执行下一次循环
                    continue;
                }
    }






四、通过注解属性获取相关事件信息


最终目的是进行如下设置 :


           

textView.setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                    }
                });


需要获取 textView 组件 , 可以在注解中获取 @OnClick({R.id.textView}) 组件 ID , 根据 ID 获取组件 ;


获取并执行 View 组件的 setOnClickListener 方法 , 通过反射获取该方法 ;


创建 View.OnClickListener 接口实现类 , 并实现 onClick 方法 , 这里特别注意 , 必须使用代理拦截该方法 , 替换成自己的方法 , 即在 MainActivity 中使用 @OnClick({R.id.textView}) 注解修饰的方法 ;


如果使用静态代理 , 则只能创建固定的 View.OnClickListener 接口的静态代理类 , 无法实现为组件设置长按事件 , 触摸事件 ;


因此这里使用动态代理实现 , 使用动态代理 , 创建 View.OnClickListener 或 View.OnLongClickListener 或 View.onTouchListener 等接口的动态代理类 ;



在 @EventBase 注解中配置事件的三要素 , 设置事件监听的方法 , 监听器类型 , 事件触发回调方法 ;


package kim.hsl.ioc_lib;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
 * 自定义注解
 *  用于注解上的注解
 *  用于依赖注入视图
 */
@Target(ElementType.ANNOTATION_TYPE)   // 该注解作用于注解上
@Retention(RetentionPolicy.RUNTIME)    // 注解保留到运行时
public @interface EventBase {
    /**
     * 设置事件监听的方法
     * @return
     */
    String listenerSetter();
    /**
     * 设置监听器类型
     * @return
     */
    Class<?> listenerType();
    /**
     * 事件触发后的回调方法
     * @return
     */
    String callbackMethod();
}


获取注解中的事件三要素 :


             

// 点击事件 View.setOnClickListener
                String listenerSetter = eventBase.listenerSetter();
                // 监听器类型 View.OnClickListener
                Class<?> listenerType = eventBase.listenerType();
                // 事件触发回调方法 public void onClick(View v)
                String callbackMethod = eventBase.callbackMethod();


获取 要拦截的方法 以及 要注入的方法 ,

要拦截的方法是事件监听器的方法 , 要注入的方法是用户在 MainActivity 中使用 @OnClick 注解修饰的方法 ;


最后将这两个方法放在 Map 集合中 ;


           

// 拦截 callbackMethod 方法 , 执行 method[i] 方法
                //      这个 method[i] 方法就是在 MainActivity 中用户自定义方法
                //      被 OnClick 注解修饰的方法
                //      将其封装到 Map 集合中
                Map<String, Method> methodMap = new HashMap<>();
                methodMap.put(callbackMethod, methods[i]
目录
相关文章
|
2月前
|
Android开发
Android面试高频知识点(1) 图解Android事件分发机制
Android面试高频知识点(1) 图解Android事件分发机制
|
2月前
|
Android开发
Android面试高频知识点(1) 图解 Android 事件分发机制
Android面试高频知识点(1) 图解 Android 事件分发机制
40 1
|
2月前
|
XML 前端开发 Android开发
Android面试高频知识点(1) 图解Android事件分发机制
Android面试高频知识点(1) 图解Android事件分发机制
Android面试高频知识点(1) 图解Android事件分发机制
|
2月前
|
Android开发
Android 事件分发机制详细解读
Android 事件分发机制详细解读
42 5
|
3月前
|
编译器 Android开发 开发者
带你了解Android Jetpack库中的依赖注入框架:Hilt
本文介绍了Hilt,这是Google为Android开发的依赖注入框架,基于Dagger构建,旨在简化依赖注入过程。Hilt通过自动化的组件和注解减少了DI的样板代码,提高了应用的可测试性和可维护性。文章详细讲解了Hilt的主要概念、基本用法及原理,帮助开发者更好地理解和应用Hilt。
88 8
|
3月前
|
API Android开发 iOS开发
掌握安卓与iOS应用开发中的依赖注入技术
本文探讨了在安卓和iOS应用开发中,如何有效利用依赖注入技术来提升代码的模块化、可测试性和可维护性。通过对比分析两种平台下依赖注入的实现方式与工具,本文旨在为开发者提供一套清晰、实用的依赖管理策略,助力打造高质量软件产品。
|
4月前
|
图形学 Android开发
小功能⭐️Unity调用Android常用事件
小功能⭐️Unity调用Android常用事件
|
4月前
|
Android开发
Android面试高频知识点(1) 图解 Android 事件分发机制
在Android开发中,事件分发机制是一块Android比较重要的知识体系,了解并熟悉整套的分发机制有助于更好的分析各种点击滑动失效问题,更好去扩展控件的事件功能和开发自定义控件,同时事件分发机制也是Android面试必问考点之一,如果你能把下面的一些事件分发图当场画出来肯定加分不少。废话不多说,总结一句:事件分发机制很重要。
202 9
|
4月前
|
开发工具 Android开发
Android项目架构设计问题之组件A通知组件B某个事件的发生如何解决
Android项目架构设计问题之组件A通知组件B某个事件的发生如何解决
43 0
|
4月前
|
Android开发
AutoX——当Android中clickable属性显示为false,实际可点击的布局如何处理
AutoX——当Android中clickable属性显示为false,实际可点击的布局如何处理
63 0