5. Списки - kpb90/start_android GitHub Wiki
LayoutInflater - это класс, который умеет из содержимого layout-файла создать View-элемент. Метод который это делает называется inflate.
Одна из реализаций – **public View inflate (int resource, ViewGroup root, boolean attachToRoot) **
resource - ID layout-файлаю. Например - R.layout.main
root – родительский ViewGroup-элемент для создаваемого View. LayoutParams от этого ViewGroup присваиваются создаваемому View.
attachToRoot – присоединять ли создаваемый View к root (равносильно команде root.addView(View)).
Если false – то создаваемый View просто получает LayoutParams от root, но его дочерним элементом не становится.
Схема построения списка:
-
Пункты списка создает адаптер. Ему на вход подаются данные и layout-ресурс пункта списка.
-
Адаптер присваивается списку
-
Список при построении запрашивает у адаптера пункты, который их создает и возвращает списку.
ListView – это и есть компонент списка.
Существует большое количество адаптеров:
Интерфейс Adapter описывает базовые методы, которые должны содержать адаптеры: getCount, getItem, getView и пр.
Абстрактный класс BaseAdapter содержит немного своих методов и реализует методы интерфейсов, которые наследует, но не все. Своим наследникам оставляет на обязательную реализацию методы: getView, getItemId, getItem, getCount из ListAdapter. Т.е. если хотите создать свой адаптер – это класс вам подходит.
Итого есть 4 готовых адаптера: HeaderViewListAdapter, ArrayAdapter, SimpleAdapter, SimpleCursorAdapter. Если есть массив строк - то ArrayAdapter. Если работаете с БД и есть курсор, данные из которого надо вывести в список - используете SimpleCursorAdapter.
Простейший пример использования готового адаптера:
public ArrayAdapter (Context context, int textViewResourceId, T[] objects)
// создаем адаптер
ArrayAdapter adapter = new ArrayAdapter(this, android.R.layout.simple_list_item_1, names);
this – контекст
android.R.layout.simple_list_item_1 – это системный layout-файл, который представляет собой TextView
names – массив данных, которые мы хотим вывести в список
Context (контекст) используется для доступа к базовым функциям приложения.
ArrаyAdapter использует LayoutInflater, чтобы конвертнуть layout-ресурс в View. Но получение объекта LayoutInflater – это одна из базовых функций и она недоступна для класса ArrаyAdapter. Поэтому в ArrаyAdapter в качестве контекста передаем ссылку на Activity (Activity имеет доступ к базовым функциям через восходящую иерархию классов). А класс ArrayAdapter внутри себя использует переданный ему контекст, чтобы вызвать LayoutInflater. Без контекста он не смог бы это сделать.
Создание списка на основе BaseAdapter
Схема работы:
-
Наследуемся от BaseAdapter
-
Переопределяем методы:
- getCount - возвращает кол-во элементов.
- getItem - возвращает данные по указанному индексу.
- getItemId - возвращает id элемента (можно вернуть индекс).
-
getView (int position, View convertView, ViewGroup parent) - возвращает View пункта списка.
- cоздаем из layout -> View c помощью LayoutInflater. если пришло convertView -> то можно использовать его, это ускорит работу.
- Синхронизуем данные с контролами
- Возвращаем View
У каждого view есть Tag – это некое Object-хранилище. В него можно помещать необходимые данные. Это может использовать для синхронизации view и модели. Android переиспользует ресурсы, поэтому view item на самом деле создаются не новые, а используется те, которые якобы скрыты от пользователя. Поэтому модель необходимо держать в актуальном состоянии.