org.xutils.view.ViewInjectorImpl

package org.xutils.view;



import android.app.Activity;

import android.view.LayoutInflater;

import android.view.View;

import android.view.ViewGroup;



import org.xutils.ViewInjector;

import org.xutils.common.util.LogUtil;

import org.xutils.view.annotation.ContentView;

import org.xutils.view.annotation.Event;

import org.xutils.view.annotation.ViewInject;

import org.xutils.x;



import java.lang.reflect.Field;

import java.lang.reflect.Method;

import java.lang.reflect.Modifier;

import java.util.HashSet;



/**

* @author 注释者:王教成

* @version 注释版:1.0.0

* 视图注入接口实现

*/

public final class ViewInjectorImpl implements ViewInjector {

private static final HashSet<Class<?>> IGNORED = new HashSet<Class<?>>();//创建忽略类集合

   static {

IGNORED.add(Object.class);

       IGNORED.add(Activity.class);

       IGNORED.add(android.app.Fragment.class);

       try {

IGNORED.add(Class.forName("android.support.v4.app.Fragment"));

           IGNORED.add(Class.forName("android.support.v4.app.FragmentActivity"));

       } catch (Throwable ignored) {

}

}//静态初始化块

   private static final Object lock = new Object();//创建锁对象

   private static volatile ViewInjectorImpl instance;//创建视图注入实例,volatile禁止优化关键字

   private ViewInjectorImpl() {

}//构造器



   /**

    * 注册实例方法

    */

   public static void registerInstance() {

if (instance == null) {

synchronized (lock) {

if (instance == null) {

instance = new ViewInjectorImpl();

               }

}

}

x.Ext.setViewInjector(instance);

   }



/**

    * 从父类获取注解View

    * @param thisCls 此类

    * @return 返回contentView注解

    */

   private static ContentView findContentView(Class<?> thisCls) {

if (thisCls == null || IGNORED.contains(thisCls)) {

return null;//此类为null或者类集合包含此类返回null

       }

ContentView contentView = thisCls.getAnnotation(ContentView.class);//通过此类获取注解

       if (contentView == null) {

return findContentView(thisCls.getSuperclass());//注解为null则根据此类的父类返回注解

       }

return contentView;//返回注解

   }



/**

    * 注入对象方法

    * @param handler handler对象

    * @param handlerType  handler类型类

    * @param finder ViewFinder对象

    */

   @SuppressWarnings("ConstantConditions")//忽略ConstantConditions编译警告

   private static void injectObject(Object handler, Class<?> handlerType, ViewFinder finder) {

if (handlerType == null || IGNORED.contains(handlerType)) {

return;//类为null或者类集合不包含,直接返回

       }

injectObject(handler, handlerType.getSuperclass(), finder);//从父类到子类递归



       Field[] fields = handlerType.getDeclaredFields();//获取类所有属性创建数组

       if (fields != null && fields.length > 0) {

for (Field field : fields) {

Class<?> fieldType = field.getType();//属性数组非空大于0,迭代获取属性类型

               if (Modifier.isStatic(field.getModifiers()) ||//不注入静态字段,getModifiers返回修饰符,Modifier判断获取修饰符

                               Modifier.isFinal(field.getModifiers()) ||//不注入final字段,getModifiers返回修饰符,Modifier判断获取修饰符

                               fieldType.isPrimitive() ||//不注入基本类型字段

                               fieldType.isArray()//不注入数组类型字段

                       ) {

continue;

               }

ViewInject viewInject = field.getAnnotation(ViewInject.class);//根据属性获取视图注入注解

               if (viewInject != null) {

try {

View view = finder.findViewById(viewInject.value(), viewInject.parentId());//视图注解非空获取view

                       if (view != null) {

field.setAccessible(true);//如果view非空,将private修饰变得可访问

                           field.set(handler, view);//给handler对象的field字段设置成view

                       } else {

throw new RuntimeException("Invalid @ViewInject for "

                                   + handlerType.getSimpleName() + "." + field.getName());//抛出运行时异常

                       }

} catch (Throwable ex) {

LogUtil.e(ex.getMessage(), ex);//捕获异常记录日志

                   }

}

}

}//注入view代码块



       Method[] methods = handlerType.getDeclaredMethods();//获取类所有方法创建数组

       if (methods != null && methods.length > 0) {

for (Method method : methods) {

if (Modifier.isStatic(method.getModifiers())

|| !Modifier.isPrivate(method.getModifiers())) {

continue;//不注入静态和final字段

               }

//检查当前方法是否是event注解的方法

               Event event = method.getAnnotation(Event.class);//根据方法获取事件注入注解

               if (event != null) {

try {

int[] values = event.value();//根据事件获取ID数组

                       int[] parentIds = event.parentId();//根据事件获取父类ID数组

                       int parentIdsLen = parentIds == null ? 0 : parentIds.length;//父类ID数组为空赋长度为0,否则赋长度为数组长度

                       //循环所有id,生成ViewInfo并添加代理反射

                       for (int i = 0; i < values.length; i++) {

int value = http://www.gunmi.cn/v/values[i];//迭代ID

                           if (value > 0) {

ViewInfo info = new ViewInfo();//如果ID大于0创建ViewInfo对象

                               info.value = http://www.gunmi.cn/v/value;//赋值ID

                               info.parentId = parentIdsLen > i ? parentIds[i] : 0;//父类ID数组长度大于ID数组长度,返回父类ID数组i索引ID,否则返回0

                               method.setAccessible(true);//将private修饰变得可访问

                               EventListenerManager.addEventMethod(finder, info, event, handler, method);//添加事件方法

                           }

}

} catch (Throwable ex) {

LogUtil.e(ex.getMessage(), ex);//捕获异常记录日志

                   }

}

}

}//注入事件代码块

   }



/**

    * 注入view

    * @param view 视图

    */

   @Override

   public void inject(View view) {

injectObject(view, view.getClass(), new ViewFinder(view));//调用本类注入对象方法注入view

   }

/**

    * 注入activity

    * @param activity 活动

    */

   @Override

   public void inject(Activity activity) {

Class<?> handlerType = activity.getClass();//获取Activity的类

       try {

ContentView contentView = findContentView(handlerType);//调用本类方法,根据Activity的类获取ContentView注解

           if (contentView != null) {

int viewId = contentView.value();//获取ContentView注解的value

               if (viewId > 0) {

Method setContentViewMethod = handlerType.getMethod("setContentView", int.class);//ID大于0,通过Activity类获取方法

                   setContentViewMethod.invoke(activity, viewId);//执行方法

               }

}

} catch (Throwable ex) {

LogUtil.e(ex.getMessage(), ex);//记录日志

       }

injectObject(activity, handlerType, new ViewFinder(activity));//调用本类注入对象方法注入activity

   }

/**

    * 注入view holder

    * @param handler view holder

    * @param view 视图

    */

   @Override

   public void inject(Object handler, View view) {

injectObject(handler, handler.getClass(), new ViewFinder(view));//调用本类注入对象方法注入view holder

   }

/**

    * 注入fragment

    * @param fragment 片段

    * @param inflater 布局加载器

    * @param container 容器

    * @return 返回view

    */

   @Override

   public View inject(Object fragment, LayoutInflater inflater, ViewGroup container) {

//注入ContentView

       View view = null;

       Class<?> handlerType = fragment.getClass();//fragment对象获取类

       try {

ContentView contentView = findContentView(handlerType);//根据fragment类获取注解

           if (contentView != null) {

int viewId = contentView.value();//通过注解获取ID

               if (viewId > 0) {

view = inflater.inflate(viewId, container, false);//如果ID大于0加载view

               }

}

} catch (Throwable ex) {

LogUtil.e(ex.getMessage(), ex);//记录日志

       }

//注入资源和事件

       injectObject(fragment, handlerType, new ViewFinder(view));//调用本类注入对象方法注入fragment

       return view;//返回view

   }

}

org.xutils.view.ViewInjectorImpl