Я пытаюсь определить лучший способ иметь один ListView, который содержит разные макеты для каждой строки. Я знаю, как создать настраиваемый адаптер строки + настраиваемый массив для поддержки настраиваемой строки для всего представления списка, но как я могу реализовать много разных стилей строк в ListView?
android
listview
listviewitem
w.donahue
источник
источник
Ответы:
Поскольку вы знаете, сколько типов макетов у вас будет - эти методы можно использовать.
getViewTypeCount()
- этот метод возвращает информацию о количестве типов строк в вашем спискеgetItemViewType(int position)
- возвращает информацию, какой тип макета вы должны использовать на основе позицииТогда вы раздуваете макет, только если он нулевой, и определяете тип с помощью
getItemViewType
.Посмотрите на этот учебник для получения дополнительной информации.
Чтобы добиться некоторой оптимизации структуры, которую вы описали в комментарии, я бы предложил:
ViewHolder
. Это увеличит скорость, потому что вам не придетсяfindViewById()
каждый раз вызыватьgetView
метод. Смотрите List14 в демоверсиях API .Я надеюсь, что это поможет вам. Если бы вы могли предоставить некоторую заглушку XML со своей структурой данных и информацию о том, как именно вы хотите отобразить ее в строку, я мог бы дать вам более точный совет. По пикселям.
источник
Вы уже знаете основы. Вам просто нужно, чтобы ваш пользовательский адаптер возвращал другой макет / представление на основе предоставленной информации о строке / курсоре.
ListView
Может поддерживать несколько стилей строк , потому что происходит от AdapterView :Если вы посмотрите на Адаптер , вы увидите методы, которые учитывают использование специфических для строки представлений:
Последние два метода предоставляют позицию, чтобы вы могли использовать ее для определения типа представления, которое вы должны использовать для этой строки .
Конечно, вы обычно не используете AdapterView и Adapter напрямую, а используете или наследуете один из их подклассов. Подклассы Adapter могут добавлять дополнительные функции, которые изменяют способ получения пользовательских макетов для разных строк. Поскольку представление, используемое для данной строки, управляется адаптером, уловка состоит в том, чтобы заставить адаптер возвращать желаемое представление для данной строки. Как это сделать, зависит от конкретного адаптера.
Например, чтобы использовать ArrayAdapter ,
getView()
чтобы надуть, заполнить и вернуть желаемый вид для данной позиции.getView()
Метод включает в себя возможность повторного использования взглядов черезconvertView
параметр.Но использовать производные CursorAdapter ,
newView()
чтобы накачать, заполнить и вернуть желаемый вид для текущего состояния курсора (то есть текущей «строки») [вам также нужно переопределить,bindView
чтобы виджет мог повторно использовать представления]Тем не менее, чтобы использовать SimpleCursorAdapter ,
SimpleCursorAdapter.ViewBinder
с помощьюsetViewValue()
метода для раздувания, заполнения и возврата нужного представления для данной строки (текущего состояния курсора) и «столбца» данных. Метод может определять только «специальные» представления и использовать стандартное поведение SimpleCursorAdapter для «обычных» привязок.Посмотрите конкретные примеры / учебные пособия для типа адаптера, который вы в конечном итоге используете.
источник
BaseAdapter
. Извлечение из BaseAdapter было бы наиболее «гибким», но было бы наихудшим при повторном использовании и зрелости кода, поскольку оно не использует преимущества знаний и зрелости, уже заложенных в другие адаптеры.BaseAdapter
есть для нестандартных контекстов, где другие адаптеры не подходят.CursorAdapter
иSimpleCursorAdapter
.ArrayAdapter
, не имеет значения, какой макет вы передадите конструктору, если онgetView()
раздувает и возвращает правильный тип макетаgetViewTypeCount()
срабатывает только один раз при каждом звонкеListView.setAdapter()
, а не для каждогоAdapter.notifyDataSetChanged()
.Посмотрите на код ниже.
Сначала мы создаем пользовательские макеты. В этом случае четыре типа.
even.xml
odd.xml
white.xml
black.xml
Затем мы создаем элемент списка. В нашем случае со строкой и типом.
После этого мы создаем видодержатель. Настоятельно рекомендуется, поскольку ОС Android сохраняет ссылку на макет для повторного использования вашего элемента, когда он исчезает и снова появляется на экране. Если вы не используете этот подход, каждый раз, когда ваш элемент появляется на экране, ОС Android будет создавать новый, вызывая утечку памяти в вашем приложении.
Наконец, мы создаем наш собственный адаптер, переопределяющий getViewTypeCount () и getItemViewType (int position).
И наша деятельность примерно такая:
Теперь создайте просмотр списка внутри mainactivity.xml, как это
источник
В своем адаптере массива вы переопределяете метод getView (), как вы, вероятно, знакомы с ним. Затем все, что вам нужно сделать, это использовать оператор switch или оператор if, чтобы вернуть определенный пользовательский View в зависимости от аргумента позиции, переданного в метод getView. Android умен в том, что он даст вам convertView только соответствующего типа для вашей позиции / строки; Вам не нужно проверять, что это правильный тип. В этом вы можете помочь Android, переопределив методы getItemViewType () и getViewTypeCount () соответствующим образом.
источник
Если нам нужно отобразить другой тип представления в виде списка, то лучше использовать getViewTypeCount () и getItemViewType () в адаптере вместо переключения вида VIEW.GONE и VIEW.VISIBLE могут быть очень дорогой задачей внутри getView (), которая будет влияет на прокрутку списка.
Пожалуйста, отметьте это для использования getViewTypeCount () и getItemViewType () в адаптере.
Ссылка: the-use-of-getviewtypecount
источник
ListView был предназначен для простых случаев использования, таких как статическое представление для всех элементов строки.
Поскольку вам необходимо создавать ViewHolders, активно использовать
getItemViewType()
и динамически показывать различные XML-элементы макета элементов строки, попробуйте сделать это с помощью RecyclerView , который доступен в Android API 22. Он обеспечивает лучшую поддержку и структуру для нескольких типов представлений.Прочтите это руководство о том, как использовать RecyclerView для того, что вы ищете.
источник