Recyclerview Adapter 和 Glide - 每 4-5 行相同的图像

Recyclerview Adapter and Glide - same image every 4-5 rows

我遇到了这个问题 - 出于测试目的,我将 ParseFile 添加到收到列表中的 ParseObject 之一。它不是仅在该行中显示,而是每 4-5 行显示一次,有时更多,有时更少。我怀疑回收观点与此有关。奇怪的是,其他数据(从这个例子中删除)与 position 变量一起工作正常。

@Override
    public void onBindViewHolder(ViewHolder holder, int position) {
        if(parseList.get(position).get("logo") != null){
            ParseFile image = (ParseFile) parseList.get(position).get("logo");
            String url = image.getUrl();
            Glide.with(context)
                    .load(url)
                    .placeholder(R.drawable.piwo_48)
                    .transform(new CircleTransform(context))
                    .into(holder.imageView);


        }

    }

当"logo"为空时,您将获得回收图像而不是清除它。添加此代码以正确清除图像:

holder.imageView.setImageDrawable(null);

RecyclerView 中,每一行都使用新数据进行回收。在您的代码中,您仅在 ImageView 不是 null 时才设置 ImageView ,否则什么也不做。在这种情况下,当它不为 null 时,ImageView 将显示旧图像,因为您没有为当前对象 override。您可以通过添加其他条件并将 ImageView 设置为 null/blank 任何内容来解决此问题。

@Override 
    public void onBindViewHolder(ViewHolder holder, int position) {
        if(parseList.get(position).get("logo") != null){
            ParseFile image = (ParseFile) parseList.get(position).get("logo");
            String url = image.getUrl();
            Glide.with(context) 
                    .load(url)
                    .placeholder(R.drawable.piwo_48)
                    .transform(new CircleTransform(context)) 
                    .into(holder.imageView);


        } 
        else{
            holder.imageView.setImageDrawable(null);
        }
    } 

这里的答案是不正确的,虽然他们在正确的轨道上。

您需要调用 Glide#clear(),而不仅仅是将可绘制图像设置为 null。如果您不调用 clear(),乱序完成的异步加载可能仍会导致视图回收问题。您的代码应如下所示:

@Override 
public void onBindViewHolder(ViewHolder holder, int position) {
    if (parseList.get(position).get("logo") != null) {
        ParseFile image = (ParseFile) parseList.get(position).get("logo");
        String url = image.getUrl();
        Glide.with(context) 
                .load(url)
                .placeholder(R.drawable.piwo_48)
                .transform(new CircleTransform(context)) 
                .into(holder.imageView);
    } else {
        // make sure Glide doesn't load anything into this view until told otherwise
        Glide.with(context).clear(holder.imageView);
        // remove the placeholder (optional); read comments below
        holder.imageView.setImageDrawable(null);
    }
} 

也许你需要尝试这样的事情

.signature(new StringSignature(String.valueOf(System.currentTimeMillis())))

样本:

Glide.with(context)
                .load(url)
                .placeholder(R.drawable.progress_animation)
                .crossFade()
                .signature(new StringSignature(String.valueOf(System.currentTimeMillis())))
                .error(R.drawable.image_error_404)
                .into(iv);

我想是因为你的适配器有 adapter.setHasStableIds(真) 为真且 getItemId 未被覆盖。所以 recyclerView 尝试找到具有相同 id 的 holder 并重用它。