Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

RecyclerView doesn't show items until scrolling

This question has been asked a few times but those answers doesn't apply to me. I would like a more general answer about what causes this issue generally.

I have a recyclerview in my activity layout. Rows of the recyclerview is a constraint layout with one imageview and textview:

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="50dp"
    android:clickable="true">

    <ImageView
        android:id="@+id/file_icon"
        android:layout_width="50dp"
        android:layout_height="50dp"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintTop_toTopOf="parent"/>

    <TextView
        android:text="File"
        android:id="@+id/file_name"
        android:layout_width="0dp"
        android:layout_height="0dp"
        app:layout_constraintLeft_toRightOf="@+id/file_icon"
        app:layout_constraintTop_toTopOf="parent"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintRight_toRightOf="parent"/>

</android.support.constraint.ConstraintLayout>

I have several items to show in this row structure. I set up the adapter properly. However, when I run my application, textviews that are on the screen doesn't get shown, until I scroll-down and scroll-up again. Basically, in order for those textviews to be shown, they need to be discarded from display and enter again. Here is my adapter code:

public class FileViewAdapter extends RecyclerView.Adapter<FileViewAdapter.Viewholder> {

    private Context context;
    private List<File> files;

    public FileViewAdapter(Context context, List<File> files) {
        this.context = context;
        this.files = files;
    }

    public FileViewAdapter(Context context){

        this.context = context;
    }

    @Override
    public Viewholder onCreateViewHolder(ViewGroup viewGroup, int i) {
        LayoutInflater inflater = LayoutInflater.from(context);
        View layout = inflater.inflate(R.layout.file_list_item, viewGroup, false);
        return new Viewholder(layout);
    }

    @Override
    public void onBindViewHolder(Viewholder viewholder, int i) {
        File file = files.get(i);
        if (file.isDirectory()) {
            viewholder.fileIcon.setImageDrawable(
                    context.getResources().getDrawable(R.drawable.ic_folder_black_24dp));
            viewholder.wholeThing.setOnClickListener(null);
        } else {
            viewholder.fileIcon.setImageDrawable(
                    context.getResources().getDrawable(R.drawable.ic_insert_drive_file_black_24dp));
            viewholder.wholeThing.setOnClickListener(null);
        }
        viewholder.fileName.setText(file.getName());
    }


    @Override
    public int getItemCount() {
        return files.size();
    }

    public void clear() {
        files.clear();
        notifyDataSetChanged();
    }

    public void addAll(List<File> newFiles) {
        files.addAll(newFiles);
        notifyDataSetChanged();
    }

    class Viewholder extends RecyclerView.ViewHolder {
        View wholeThing;
        ImageView fileIcon;
        TextView fileName;

        public Viewholder(View itemView) {
            super(itemView);
            wholeThing = itemView;
            fileIcon = (ImageView) itemView.findViewById(R.id.file_icon);
            fileName = (TextView) itemView.findViewById(R.id.file_name);
        }
    }

}

EDIT: How I am calling the constructor of adapter on activity.

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_file_viewer);    
    recyclerView = (RecyclerView) findViewById(R.id.recyclerView);
}

@Override
public void onResume() {
     adapter = new Adapter(this, /*A list of File items*/);
     recyclerView.setAdapter(adapter);
     recyclerView.setLayoutManager(new LinearLayoutManager(this));
}
like image 925
Bora Avatar asked Jul 18 '17 12:07

Bora


People also ask

How can show all data in RecyclerView without scrolling?

In RecyclerView use android:nestedSrollingEnabled="false" and use NestedScrollView as a parent Scroll View. This was the only answer that worked for me - I had a ScrollView wrapping two RecyclerViews.

Does RecyclerView automatically scroll?

Does RecyclerView automatically scroll? There is a method in RecyclerView which is smoothScrollToPosition() which take position of recyclerview to scroll that position to current position.

What are Recycler views?

RecyclerView is the ViewGroup that contains the views corresponding to your data. It's a view itself, so you add RecyclerView into your layout the way you would add any other UI element. Each individual element in the list is defined by a view holder object.


2 Answers

The problem from what i see is that the notifyDataSetChanged doesnt ocurr in the UiThread so if run ur setData method like this it will work.

 this.runOnUiThread(new Runnable() {
        public void run() {
            mAdapter.setNewData(newDataListForAdapter);
            mAdapter.notifyDataSetChanged();

        }
    });
like image 77
Catluc Avatar answered Sep 21 '22 12:09

Catluc


As stupid as it might sound, calling this line of code after setting data for recyclerView, helped me for this issue:

recyclerView.smoothScrollToPosition(0)

PS: technologies that I was using that may have something to do with this were: RJava, Retrofit2, NavigationUI, Fragments, LiveData, and Databinding.

like image 27
Amin Keshavarzian Avatar answered Sep 19 '22 12:09

Amin Keshavarzian