学习笔记:打造自己的万能接口,实现类似eventbus的功能(优化篇)

244 阅读3分钟

学习地址:study.163.com/smartSpec/i…

昨天将老师讲的代码手撸了一遍: juejin.cn/post/684490…

今天按照自己的想法优化一下,先上一下使用方法:

调用:

调用的时候不需要bind,直接使用invokeFunction方法就行了

实现:

在onCreate中调用FunctionManager.getInstance().bind(this);
在onDestroy中调用FunctionManager.getInstance().unbind(this);
在需要被调用的方法上添加@FunctionAnnotation注解,方法名字需要和上图中的方法名一致

效果

改造开始

1.编写annotation

//这是一个自定义的注解,主要是为了标识方法
@Target(ElementType.METHOD) // 作用在方法之上
@Retention(RetentionPolicy.RUNTIME)// 运行时
public @interface FunctionAnnotation {
}

2.改造FunctionManager

    public class FunctionManager {

    private static FunctionManager instance;

    private HashMap<String, Function> mFunctionMap;

    // 保存所有target的集合
    private List<Object> targetList;

    // 目标对象
    private Object target;

    // 目标方法tag,用于移除方法
    private String tag;

    //在构造函数中初始化一些对象
    private FunctionManager() {
        mFunctionMap = new HashMap<>();
        targetList = new ArrayList<>();
    }

    public static FunctionManager getInstance() {
        if (instance == null) {
            instance = new FunctionManager();
        }
        return instance;
    }

    // 绑定
    public void bind(Object target) {
        // 将target添加到集合
        targetList.add(target);
        this.target = target;
        this.tag = target.getClass().getSimpleName();
        initAllFunction();
        Log.e("FunctionManager", "bind targetList SIZE:" + targetList.size());
        Log.e("FunctionManager", "bind mFunctionMap SIZE:" + mFunctionMap.size());
    }

    //解绑
    public void unbind(Object target) {
        deleteFunction(target.getClass().getSimpleName());
        deleteTarget(target);
        Log.e("FunctionManager", "unbind targetList SIZE:" + targetList.size());
        Log.e("FunctionManager", "unbind mFunctionMap SIZE:" + mFunctionMap.size());
    }

    //通过反射,自动把方法上有@FunctionAnnotation注解的方法添加到map中
    private void initAllFunction() {
        Class<?> aClass = target.getClass();
        //获取当前注册类所有的方法
        Method[] declaredMethods = aClass.getDeclaredMethods();
        for (Method declaredMethod : declaredMethods) {
            //获取每个方法上的所有注解
            Annotation[] declaredAnnotations = declaredMethod.getDeclaredAnnotations();
            for (Annotation declaredAnnotation : declaredAnnotations) {
                if (declaredAnnotation instanceof FunctionAnnotation) {
                    // 解析方法
                    analysisMethod(declaredMethod);
                }
            }
        }
    }

    private void analysisMethod(Method method) {
        try {
            
            // 获取到方法的返回类型
            Class<?> returnType = method.getReturnType();
           
            //获取到方法的参数类型,这里返回的是一个数组,数组长度为0时表示该方法没有参数
            Class<?>[] parameterTypes = method.getParameterTypes();
          
            //获取到方法的名字
            String name = method.getName();
           
            //方法的返回如果是void表示没返回
            boolean isVoid = returnType.getName().equals("void");

            // 无参数 无返回
            if (parameterTypes.length == 0 && isVoid) {
                addFunction(new NoParamNoResultFunction(name, tag) {
                    @Override
                    public void function() {
                        try {
                            target = getCurrentTarget(method);
                            if (target != null) {
                                method.setAccessible(true);
                                method.invoke(target);
                            }

                        } catch (Exception e) {
                            e.printStackTrace();
                        }
                    }
                });

            }
            // 有参数 无返回
            if (parameterTypes.length != 0 && isVoid) {
                addFunction(new HasParamNoResultFunction(name, tag) {
                    @Override
                    public void function(Object... args) {
                        try {
                            target = getCurrentTarget(method);
                            if (target != null) {
                                method.setAccessible(true);
                                method.invoke(target, args);
                            }
                        } catch (Exception e) {
                            e.printStackTrace();
                        }
                    }
                });


            }
            // 无参数 有返回
            if (parameterTypes.length == 0 && !isVoid) {
                addFunction(new NoParamHasResultFunction(name, tag) {
                    @Override
                    public Object function() {
                        try {
                            target = getCurrentTarget(method);
                            if (target != null) {
                                method.setAccessible(true);
                                return returnType.cast(method.invoke(target));

                            }
                        } catch (Exception e) {
                            e.printStackTrace();
                        }
                        return null;
                    }
                });
            }
             // 有参数 有返回
            if (parameterTypes.length != 0 && !isVoid) {
                addFunction(new HasParamHasResultFunction(name, tag) {
                    @Override
                    public Object function(Object... args) {
                        try {
                            target = getCurrentTarget(method);
                            if (target != null) {
                                method.setAccessible(true);
                                return returnType.cast(method.invoke(target, args));
                            }
                        } catch (Exception e) {
                            e.printStackTrace();
                        }
                        return null;
                    }
                });
            }


        } catch (Exception e) {
            e.printStackTrace();
        }


    }

    /**
     * 添加function
     **/
    private void addFunction(Function function) {
        mFunctionMap.put(function.functionName, function);
    }


    /**
     * 无参数无返回
     **/
    public void invokeFunction(String functionName) {
        if (TextUtils.isEmpty(functionName)) {
            return;
        }
        if (mFunctionMap != null) {
            Function f = mFunctionMap.get(functionName);
            if (f != null) {
                if (f instanceof NoParamNoResultFunction) {
                    ((NoParamNoResultFunction) f).function();
                }
            }

        } else {
            Log.e("FunctionManager", "没有找到该方法:" + functionName);
        }

    }


    /**
     * 有参数无返回
     **/
    @SuppressWarnings("unchecked")
    public <P> void invokeFunction(String functionName, P... p) {
        if (TextUtils.isEmpty(functionName)) {
            return;
        }
        if (mFunctionMap != null) {
            Function f = mFunctionMap.get(functionName);
            if (f != null) {
                if (f instanceof HasParamNoResultFunction) {
                    ((HasParamNoResultFunction) f).function(p);
                }
            }

        } else {
            Log.e("FunctionManager", "没有找到该方法:" + functionName);
        }
    }

    /**
     * 无参数有返回
     **/
    public <T> T invokeFunction(String functionName, Class<T> t) {
        if (TextUtils.isEmpty(functionName)) {
            return null;
        }
        if (mFunctionMap != null) {

            Function f = mFunctionMap.get(functionName);
            if (f != null) {
                if (f instanceof NoParamHasResultFunction) {
                    return t.cast(((NoParamHasResultFunction) f).function());
                }

            }
        } else {
            Log.e("FunctionManager", "没有找到该方法:" + functionName);
        }

        return null;
    }

    /**
     * 有参数有返回
     **/
    @SuppressWarnings("unchecked")
    public <T, P> T invokeFunction(String functionName, Class<T> t, P... p) {
        if (TextUtils.isEmpty(functionName)) {
            return null;
        }
        if (mFunctionMap != null) {
            Function f = mFunctionMap.get(functionName);
            if (f != null) {
                if (f instanceof HasParamHasResultFunction) {
                    return t.cast(((HasParamHasResultFunction) f).function(p));
                }

            }
        } else {
            Log.e("FunctionManager", "没有找到该方法:" + functionName);
        }

        return null;
    }

    //获取到当前方法的target
    private Object getCurrentTarget(Method method) {
        if (target.getClass().getName().equals(method.getDeclaringClass().getName()))
            return target;
        for (Object obj : targetList) {
            if (obj.getClass().getName().equals(method.getDeclaringClass().getName())) {
                return obj;
            }
        }
        return null;
    }

    //移除对应的target
    private void deleteTarget(Object o) {
        targetList.remove(o);
    }
  
    //根据tag删除对应的function
    private void deleteFunction(String tag) {
        Iterator<Map.Entry<String, Function>> mFunctionMapIterator = mFunctionMap.entrySet().iterator();
        while (mFunctionMapIterator.hasNext()) {
            HashMap.Entry<String, Function> map = mFunctionMapIterator.next();
            if (map.getValue().tag.equals(tag)) {
                mFunctionMapIterator.remove();
            }
        }
    }
}

3.没有了