Android 什么';将BindView与Butterknife一起使用与此相反吗?

Android 什么';将BindView与Butterknife一起使用与此相反吗?,android,Android,我试图在不使用Butterknife方法的情况下编写以下代码,主要用于学习目的。谁能帮我写一本没有用的书 我猜这是一种类似于 TextView textName = findViewById(R.id.post_title); 但看起来不一样,所以我猜我错过了什么 public class FriendsHolder extends RecyclerView.ViewHolder { @BindView(R.id.name) TextView textName; @B

我试图在不使用Butterknife方法的情况下编写以下代码,主要用于学习目的。谁能帮我写一本没有用的书

我猜这是一种类似于

TextView textName = findViewById(R.id.post_title); 
但看起来不一样,所以我猜我错过了什么

public class FriendsHolder extends RecyclerView.ViewHolder {
    @BindView(R.id.name)
    TextView textName;
    @BindView(R.id.image)
    CircleImageView imageView;
    @BindView(R.id.title)
    TextView textTitle;
    @BindView(R.id.company)
    TextView textCompany;

    public FriendsHolder(View itemView) {
        super(itemView);
        ButterKnife.bind(this, itemView);
    }
}

当compile SDK版本大于或等于26时,您可以这样做:

public class FriendsHolder extends RecyclerView.ViewHolder {
    TextView textName;
    CircleImageView imageView;
    TextView textTitle;
    TextView textCompany;

    public FriendsHolder(View itemView) {
        super(itemView);
        textName = itemView.findViewById(R.id.name);
        imageView = itemView.findViewById(R.id.image);
        textTitle = itemView.findViewById(R.id.title);
        textCompany = itemView.findViewById(R.id.company);
    }
}

对于小于26的API版本,只需将
findViewById
方法返回的视图显式类型转换为字段类型

您可能知道,ButterKnife是一种注释处理器,它在编译时获取代码,计算注释(例如
@BindView
)并生成代码以替换它们

现在,在
@BindView
的情况下,注释处理器实际做的是:

  • 通过其ID查找所需的视图
  • 将其强制转换为预期类型
  • 因此,您的示例的函数等价物如下所示:

    public class FriendsHolder extends RecyclerView.ViewHolder {
    
        private TextView textName;
        private CircleImageView imageView;
        private TextView textTitle;
        private TextView textCompany;
    
        FriendsHolder(View itemView) {
            super(itemView);
            bindViews(itemView);
        }
    
        private void bindViews(View root) {
            textName = (TextView) root.findViewById(R.id.name);
            imageView = (CircleImageView) root.findViewById(R.id.image);
            textTitle = (TextView) root.findViewById(R.id.title);
            textCompany = (TextView) root.findViewById(R.id.company);
        }
    }
    
    您可以阅读有关底层流程的更多信息,也可以查看

    您可以看到,它们所做的基本工作是在源代码视图上查找ID,并尝试将其转换为从注释字段读取的预期类型

    摘自
    butterknife.internal.Utils

    public static <T> T findRequiredViewAsType(View source, @IdRes int id, String who, Class<T> cls) {
        View view = findRequiredView(source, id, who);
        return castView(view, id, who, cls);
    }
    
    public static View findRequiredView(View source, @IdRes int id, String who) {
        View view = source.findViewById(id);
        if (view != null) {
          return view;
        }
        // If view is null throw IllegalStateException
    }
    
    public static <T> T castView(View view, @IdRes int id, String who, Class<T> cls) {
        try {
          return cls.cast(view); // <-- casting 
        } catch (ClassCastException e) {
            throw new IllegalStateException
            // Exception handling...
        }
    
    public static T findRequiredViewaType(查看源代码,@IdRes int-id,字符串who,类cls){
    视图=findRequiredView(来源、id、用户);
    返回castView(视图、id、who、cls);
    }
    公共静态视图findRequiredView(视图源,@IdRes int-id,字符串who){
    视图=source.findViewById(id);
    如果(视图!=null){
    返回视图;
    }
    //如果视图为null,则抛出IllegalStateException
    }
    公共静态T castView(视图视图,@IdRes int id,字符串who,类cls){
    试一试{
    
    返回cls.cast(视图);//我相信您缺少对字段预期类型的显式强制转换。目前,
    findViewById
    只会返回一个
    视图
    object@DanielW.这是老办法。如果你用最新的Android SDK版本编译,就不需要显式的类型转换。你可能会提到很棒!没有注意到他们改进了这个。H我已经使用Kotlin很长时间了:P…似乎只有一个小小的警告。从你链接的答案来看:“如果你的compileSdk至少是26,这意味着你可以利用它:)”。也许在你的答案中提到这个限制?以防有人被它绊倒
    findViewById()
    现在支持泛型:@DanielW。现在我添加了它。谢谢。