Butterknife的BindView

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/zhang___yong/article/details/82113511

引入:

    implementation 'com.jakewharton:butterknife:8.5.1'
    annotationProcessor 'com.jakewharton:butterknife-compiler:8.5.1'

butterknife的工作原理是在编译器根据扫描的注解通过JavaPoet生成一个和target(activity,fragment)对应的java文件A.java,这个生成类A(extends UnBinder)的构造方法中完成了一切实质的的绑定操作。在target中调用了bind(this)后,通过反射(target类名+_ViewBinding)获取A的构造器并实例化返回。

来看个代码,我在MainActivity中用@BindView修饰SurfaceView sv,然后make project。生成了MainActivity_ViewBinding:

// Generated code from Butter Knife. Do not modify!
package com.example.zhangyong.myapplication;

import android.support.annotation.CallSuper;
import android.support.annotation.UiThread;
import android.view.SurfaceView;
import android.view.View;
import butterknife.Unbinder;
import butterknife.internal.Utils;
import java.lang.IllegalStateException;
import java.lang.Override;

public class MainActivity_ViewBinding implements Unbinder {
  private MainActivity target;

  @UiThread
  public MainActivity_ViewBinding(MainActivity target) {
    this(target, target.getWindow().getDecorView());
  }

  @UiThread
  public MainActivity_ViewBinding(MainActivity target, View source) {
    this.target = target;

    target.sv = Utils.findRequiredViewAsType(source, R.id.sv, "field 'sv'", SurfaceView.class);
  }

  @Override
  @CallSuper
  public void unbind() {
    MainActivity target = this.target;
    if (target == null) throw new IllegalStateException("Bindings already cleared.");
    this.target = null;

    target.sv = null;
  }
}

可以看到构造器接收的参数是MainActivity,然后对被注解的属性(非private和static)进行操作,最终走的肯定还是findViewById,只不过是调用了DecorView的findViewById,可以进findRequiredViewAsType看看。

其他的一些注解就差不多了,比如设置点击事件什么的,拿到了MainActivity,也就拿到了view。

unBind里就是对这些属性赋值null,target=null的一步避免了内存泄漏。

猜你喜欢

转载自blog.csdn.net/zhang___yong/article/details/82113511