Android RecyclerView 项目序列问题

Android RecyclerView item sequence issue

我是 Android 的新手。我目前正在尝试构建一个具有列表视图屏幕的应用程序,其中显示了书籍列表。在每个项目上,有一个从 URL 下载的图像和 2 个图标,其图像资源是根据 POJO 对象中设置的值设置的。

我的适配器代码如下:

    Context context = view.getContext();
    view.setLayoutManager(new LinearLayoutManager(context));
    view.setAdapter(new MySearchBooksItemRecyclerViewAdapter(SearchBooks.ITEMS, mListener, getActivity()));

    public void onBindViewHolder(final ViewHolder holder, int position) {
    Log.d(TAG, "onBindViewHolder: binding variables of object: " + position);
    Log.d(TAG, "onBindViewHolder: holder value: " + holder.mItem);
    Log.d(TAG, "onBindViewHolder: holder value: " + holder.mTitle);
    Log.d(TAG, "onBindViewHolder: holder value: " + holder.mISBN);

    holder.mItem = mValues.get(position);
    holder.mTitle.setText(mValues.get(position).getTitle());
    holder.mTitle.setTag(mValues.get(position).getId());
    holder.mISBN.setText(mValues.get(position).getIsbn());
    holder.mDesc.setText(mValues.get(position).getDesc());
    holder.mView.setOnClickListener(new ClickListItem());

    getImages(holder.mBookImage, mValues.get(position).getImage());

    if (bookList.get(mValues.get(position).getId()) != null) {
        holder.mIsFav.setImageResource(bookList.get(mValues.get(position).getId()).isBookmarked() ? R.drawable.ic_favorite_white_24dp : R.drawable.ic_favorite_border_white_24dp);
        holder.mIsDownloaded.setImageResource(new File(bookList.get(mValues.get(position).getId()).getSavedBookName()).exists() ? R.drawable.ic_offline_pin_white_24dp : R.drawable.ic_get_app_white_24dp);
    }

    Log.d(TAG, "onBindViewHolder: variables bound: " + mValues.get(position));
}

@Override
public int getItemCount() {
    Log.d(TAG, "getItemCount: item count: " + mValues.size());
    return mValues.size();
}

    <LinearLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:backgroundTint="@android:color/darker_gray"
    android:orientation="horizontal">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_weight="5"
        android:background="@color/background_material_dark"
        android:orientation="vertical">

        <ImageView
            android:id="@+id/bookImage"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:minHeight="100dp"

            android:layout_weight="2"
            android:src="@drawable/icon_img_tu" />

        <LinearLayout
            android:layout_weight="1"
            android:minHeight="40dp"
            android:layout_gravity="center"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_marginBottom="10dp"
            android:orientation="horizontal">

            <ImageView
                android:id="@+id/is_fav_image"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:layout_weight="1"
                android:src="@drawable/ic_favorite_border_white_24dp" />

            <ImageView
                android:id="@+id/is_downloaded_image"
                android:layout_weight="1"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:background="@color/background_material_dark"
                android:src="@drawable/ic_get_app_white_24dp" />

        </LinearLayout>
    </LinearLayout>

现在当我滚动屏幕时出现问题。在第一次加载中,图标值和图像被完美加载。但是当我滚动并返回 return 时,再次调用 'onBindViewHolder' 并使用了错误的随机值。因此在图像中显示错误的图标。

谁能帮我解决这个问题...?

除非需要,否则我不希望重新加载图像或刷新图标

您应该在检查 id 是否为 null 的地方添加 else 语句,在 else 子句中填充静态图像或任何占位符。

当您没有在 ImageView 中加载图像并且 ImageView 获取随机图像时会发生这种情况。 在您的情况下,您只有 if 语句,因此当 if 语句为 false 时,ImageView 不会加载任何图像。 Recyclerview 回收视图,但我们必须确保填充 recyclerview 行中的所有值,否则将出现之前的 images/data。

希望这对您有所帮助。如果它解决了你的问题,那就接受它。谢谢

解决方案是不要使用 onBindViewHolder.

传递的 position 遍历列表

而是调用 getItemViewType(position) 并使用它来遍历您的列表,在您 return 与每个视图持有者关联的位置之后:

@Override
public int getItemViewType(int position) {
    return position;
}

事实是您的视图持有者没有按顺序保存并且与 onBindViewHolder 提供的顺序无关。通过调用 getItemViewHolder,您实质上是将位置与每个视图持有者相关联。