package com.istep.works;
import android.app.Activity;
import android.util.Log;
import android.view.View;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.List;
public class IstepProcessor {
private static void tryInvoke(Object obj, Method method, View v) {
try {
Log.i("zdy", "tryInvoke " + v);
method.invoke(obj, v);
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
}
public static void bind(Activity target) {
View sourceView = target.getWindow().getDecorView();
Class<?> clazz = target.getClass();
parser(target, clazz, sourceView);
}
public static void parser(Object obj, Class<?> clazz, View source) {
Field[] fields = clazz.getDeclaredFields();
for (Field field : fields) {
// 获取方法上的注解MyAnTargetMethod
IstepBindView tm = field.getAnnotation(IstepBindView.class);
if (tm == null) {
continue;
}
Class<?> viewClass = field.getType();
String who = "field '" + field.getName() + "'";
Log.i("zdy", "getAnnotation === " + tm + " " + viewClass + " who " + who);
View view = (View) findOptionalViewAsType(source, tm.viewId(), who, viewClass);
Method method = parserMethod(clazz, tm.viewId());
if (method != null) {
Log.i("zdy", "Method === " + tm.viewId() + " ");
view.setOnClickListener(v -> tryInvoke(obj, method, v));
}
}
}
public static <T> T findOptionalViewAsType(View source, int id, String who,
Class<T> cls) {
View view = source.findViewById(id);
Log.i("zdy", "findViewById " + id + " " + view);
return cls.cast(view);
}
public static Method parserMethod(Class<?> clazz, int id) {
Method md = null;
Method[] methods = clazz.getMethods();
for (Method method : methods) {
// Log.i("zdy","method === "+method+" "+method.getModifiers() );
// 获取方法上的注解MyAnTargetMethod
IstepListener tm = method.getAnnotation(IstepListener.class);
if (tm == null) {
continue;
}
Log.i("zdy", "getAnnotation === " + tm + " ");
Class<?>[] parameterTypes = method.getParameterTypes();
for (Class<?> pm : parameterTypes) {
Log.i("zdy", "getParameterTypes === " + pm + " ");
}
if (tm.viewId() == id) {
md = method;
break;
}
}
return md;
}
@Override
protected void finalize() throws Throwable {
super.finalize();
Log.i("zdy", "finalize ===1111 ");
}
}
ButterKnife 原理简单实现
需积分: 0 181 浏览量
更新于2022-09-18
收藏 2KB 7Z 举报
ButterKnife是一款由Jake Wharton开发的Android绑定库,它简化了在Android应用中将UI元素绑定到Java或Kotlin代码的过程。通过注解处理器,ButterKnife在编译时生成了视图查找和事件处理的代码,避免了在活动中手动找寻和设置控件的繁琐操作。
我们来理解ButterKnife的基本使用。在布局XML文件中,我们可以为控件添加一个特定的ID。然后,在对应的Activity或Fragment中,我们可以使用`@BindView`注解将这些ID与类中的成员变量关联起来。例如:
```java
public class MainActivity extends AppCompatActivity {
@BindView(R.id.button)
Button myButton;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ButterKnife.bind(this); // 这行代码会自动将布局中的控件与注解的字段绑定
}
}
```
在这个例子中,`@BindView(R.id.button)`注解告诉ButterKnife将R.id.button这个ID与myButton变量绑定。在`onCreate`方法中调用`ButterKnife.bind(this)`后,myButton变量就会自动被初始化为布局中对应的Button对象。
ButterKnife还支持事件处理。通过`@OnClick`注解,可以将点击事件直接绑定到方法上:
```java
public class MainActivity extends AppCompatActivity {
@BindView(R.id.button)
Button myButton;
@OnClick(R.id.button)
void onButtonClick() {
Toast.makeText(this, "Button clicked", Toast.LENGTH_SHORT).show();
}
...
}
```
当按钮被点击时,`onButtonClick`方法会被调用,无需在Activity中设置OnClickListener。
了解了基本使用后,我们来看看ButterKnife的原理。ButterKnife的工作主要依赖于Java的注解处理器(Annotation Processor)。在项目编译期间,注解处理器会扫描源代码,找到所有`@BindView`和`@OnClick`等注解,然后自动生成相应的代码。这个过程通常发生在编译时,生成的代码会被添加到最终的编译结果中。
在给定的文件列表中,我们可以看到以下关键组件:
1. `IstepBindView.java`:这可能是一个接口,用于定义ButterKnife绑定视图的方法,例如`bind()`,这个方法在`ButterKnife.bind()`调用时会被使用。
2. `IstepListener.java`:可能定义了一些监听器接口,用于处理各种UI事件,如点击事件。
3. `IstepProcessor.java`:这是注解处理器的核心部分,实现了对`@BindView`和`@OnClick`等注解的处理逻辑,生成绑定和事件处理的代码。
4. `MainActivity.java`:示例中的主活动,包含ButterKnife的使用示例。
ButterKnife通过注解处理器实现了代码的自动化生成,减少了手动操作,提高了开发效率,使得Android开发者能够更加专注于业务逻辑,而不是UI元素的查找和设置。在实际项目中,ButterKnife的使用可以显著提升代码的可读性和可维护性。

IstepGatlin
- 粉丝: 7
最新资源
- 网络营销源码学习.docx
- 中国移动WAP业务应用程序接口规范.doc
- 通信网原理课程设计.doc
- 机电接口技术课程设计.doc
- FPGA实现Cameralink纯逻辑编码解码方案及其在k7z7v7a7系列产品的应用 - 工业相机
- 公司年度网络营销推广服务项目线上推广方案.pptx
- 考研十大热门专业深度分析之计算机应用技术.doc
- 网络营销-渠道策略.pptx
- 神经网络hopfield网络专家讲座.pptx
- 一线通设计方案小区网络监控.doc
- 论项目管理中的人力团队建设与绩效.doc
- 鼎信诺审计软件的四种取数方法.pptx
- 享受健康的网络交往-公开课用.ppt
- 别墅智能家居系统解决方案.doc
- 项目管理的专业化与职业化发展培训课件.ppt
- 自动化专业实习报告书.doc