Введение
- В этой серии я буду размещать все свои заметки по Android. По мере того, как я узнаю что-то новое о разработке Android, я буду добавлять в эту серию уроки.
Что такое RecyclerView?
- По сути, RecyclerView позволяет легко и эффективно отображать большое количество данных. Мы предоставляем данные и определяем, как выглядит каждый отдельный элемент, а библиотека RecyclerView динамически создает элементы, когда они необходимы.
Шаги по реализации RecyclerView
- Реализация RecyclerView может запутать, поэтому, чтобы упростить задачу, я разбил все на 5 простых шагов:
1) Добавить RecyclerView в XML-файл
2) Создайте отдельные элементы RecyclerView в XML-файле
3) Создайте держатель вида (ViewHolder)
4) Создайте адаптер
5) Установить RecyclerView
- Если вы не знаете, что такое ViewHolder или Adapter, не волнуйтесь, мы поговорим о них позже.
1) Добавление RecyclerView в XML-файл
- Итак, эта часть может быть немного запутанной, в основном потому, что название библиотеки называется
RecyclerView
и название класса такжеRecyclerView
. Поэтому, если я специально не указываю, что мы говорим о библиотеке, всегда считайте, что мы говорим о классе. Теперь добавьте класс RecyclerView в любой XML-файл:
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/recyclerview"
android:layout_width="match_parent"
android:layout_height="match_parent"
/>
layout
,width
иid
зависят от конкретного разработчика. Просто убедитесь, что вы используете соответствующий класс RecyclerView.
2) Создание индивидуального XML-файла элемента RecyclerView
- Как мы уже знаем, RecyclerView используется для простого и эффективного отображения большого количества данных. Одним из шагов является определение того, как будут выглядеть отдельные элементы. Мы делаем это, определяя новый XML-файл, конечно, стиль зависит от вас. Однако я бы настоятельно рекомендовал использовать предоставляемый Android
CardView
:
<androidx.cardview.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginEnd="8dp"
android:layout_marginStart="8dp"
android:layout_marginTop="8dp">
<RelativeLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="8dp">
<TextView
android:id="@+id/text_view_priority"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentEnd="true"
android:layout_marginEnd="154dp"
android:text="This will get replaced by later" />
</RelativeLayout>
</androidx.cardview.widget.CardView>
-
Убедитесь, что
layout_height
CardView установлен наwrap_content
, иначе вы получите РЕАЛЬНО большие CardView. -
Также обратите особое внимание на
android:id="@+id/text_view_priority"
, мы будем использовать этот id позже.
3) Создайте ViewHolder
- ViewHolder описывает представление элемента и метаданные о его месте в RecyclerView. Короче говоря, этот класс будет представлять один элемент внутри RecyclerView. Я хотел бы отметить, что в официальном руководстве, ЗДЕСЬ (и в этом руководстве тоже), класс ViewHolder сделан статическим и вложенным в класс Adapter. Это не обязательно, это сделано просто для удобства использования. Единственным ограничением для пользовательского ViewHolder является то, что он расширяет класс
RecyclerView.ViewHolder
. Таким образом, вы можете создать класс ViewHolder следующим образом:
public static class ViewHolder extends RecyclerView.ViewHolder{
private TextView textView;
public ViewHolder(@NonNull View itemView) {
super(itemView);
//Define click listener for the ViewHolder's View
this.textView = (TextView) itemView.findViewById(R.id.text_view_priority);
}
//GETTERS
public TextView getTextView() {
return textView;
}
//SETTERS
public void setTextView(TextView textView) {
this.textView = textView;
}
}
- Обратите внимание на
TextView
и то, как мы находим его значение поR.id.text_view_priority
.R.id.text_view_priority
— это идентификатор TextView из шага 2. Мы находим представления в этом классе, чтобыAdapter
(следующий шаг) мог привязать к ним данные.
4) Создание адаптера
- Адаптеры обеспечивают привязку специфического для приложения набора данных к представлениям, которые отображаются в RecyclerView. Адаптер будет работать вместе с ViewHolder для создания отдельных представлений и привязки данных к этим представлениям. Адаптер делает это с помощью 3 специфических методов:
1) onCreateViewHolder() : RecyclerView (библиотека, а не класс) вызывает этот метод всякий раз, когда ему нужно создать новый ViewHolder. Метод создает и инициализирует ViewHolder и связанный с ним View, но не заполняет содержимое View. Таким образом, единственная цель этого метода — создать новые экземпляры нашего пользовательского ViewHolder из шага 3.
@Override
public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
//Create a new view, which defines the Ui of the list item
View view = LayoutInflater.from(parent.getContext())
.inflate(R.layout.indiv_recycler_item,parent,false);
return new ViewHolder(view);
}
- Если код
LayoutInflater
сбивает с толку, не волнуйтесь. Единственная задача LayoutInflater — превратить XML-код в объект View, с которым наш код может взаимодействовать.R.layout.indiv_recycler_item
просто означает, что он использует XML файл из папки res.layout и XML файл называетсяindiv_recycler_item
. Имя файла должно быть таким, как называется файл, содержащий содержимое шага 2.
2) onBindViewHolder() : Библиотека RecyclerView вызывает этот метод, чтобы связать ViewHolder с данными. Метод извлекает соответствующие данные для заполнения макета ViewHolder.
@Override
public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
holder.getTextView().setText(localDataSet[position]);
}
—
Объект holder
на самом деле является инстанцированным объектом ViewHolder, возвращаемым из метода onCreateViewHolder()
. Единственное, что я не объяснил, это localDataSet
, который я покажу позже. Сейчас это простой массив в любом месте внутри класса Adapter, в будущем я покажу, как получать данные из базы данных.
3) getItemCount() : Библиотека RecyclerView вызывает этот метод для получения размера набора данных. Очень простой и понятный метод:
@Override
public int getItemCount() {
return localDataSet.length;
}
- Таким образом, в целом класс Adapter будет выглядеть примерно так:
public class CustomAdapter extends RecyclerView.Adapter<CustomAdapter.ViewHolder> {
private String [] localDataSet = {"it","do","be","like","that","sometimes"};
public static class ViewHolder extends RecyclerView.ViewHolder{
private TextView textView;
public ViewHolder(@NonNull View itemView) {
super(itemView);
this.textView = (TextView) itemView.findViewById(R.id.text_view_priority);
}
//GETTERS
public TextView getTextView() {
return textView;
}
//SETTERS
public void setTextView(TextView textView) {
this.textView = textView;
}
}
@NonNull
@Override
public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
//Create a new view, which defines the Ui of the list item
View view = LayoutInflater.from(parent.getContext())
.inflate(R.layout.indiv_recycler_item,parent,false);
return new ViewHolder(view);
}
@Override
public void onBindViewHolder(@NonNull ViewHolder holder, int position) {
holder.getTextView().setText(localDataSet[position]);
}
@Override
public int getItemCount() {
return localDataSet.length;
}
}
5) Создание RecyclerView
- На этом последнем шаге мы хотим сделать три вещи,
1)
найти RecyclerView,2)
установить адаптер,3)
установить менеджер компоновки. Единственное, о чем мы еще не говорили, этоLayoutManager
, поэтому давайте сделаем это.
LayoutManager : Менеджер компоновки — это фактически MVP всей библиотеки RecyclerView. Он определяет, как будет выглядеть RecyclerView, будет ли это сетка или список. Он также определяет, какие элементы больше не являются визуальными на экране и как повторно использовать представления.
- Мы решили реализовать
LinearLayoutManager
, что означает, что наш RecyclerView будет выглядеть как отдельные элементы списка.
public class RecyclerViewFragment extends Fragment {
private RecyclerView recyclerView;
public RecyclerViewFragment(){
super(R.layout.recycler_view_fragment);
}
@Override
public void onViewCreated(View view,Bundle savedInstanceState){
recyclerView = view.findViewById(R.id.recyclerview);
this.recyclerView.setAdapter(new CustomAdapter());
this.recyclerView.setLayoutManager(new LinearLayoutManager(getActivity()));
}
}
- Как вы можете видеть, приведенный выше код используется внутри фрагмента, а именно фрагмента под названием
R.layout.recycler_view_fragment
. Однако RecylerView также может находиться в Activity, так что вы можете решить, какой из них использовать. - На этом мы успешно реализовали простой RecyclerView в Android.
Заключение
- Спасибо, что нашли время, чтобы прочитать эту статью в моем блоге. Если у вас есть какие-либо вопросы или проблемы, пожалуйста, комментируйте их ниже или свяжитесь со мной в Twitter.