Изменённая логика RecyclerView

141
11 апреля 2021, 12:30

Задача: Сделать карусель фотографий, где последний элемент будет добавлять в карусель новые фотографии

Этот элемент должен находиться всегда в конце.

Функционал у карусели должен быть такой: Удаление любого элемента, добавление новых в конец списка (перед добавочным элементом).

Как делал Adapter:

 var files: ArrayList<File> = arrayListOf(File(null, null))
 override fun onBindViewHolder(h: RecyclerView.ViewHolder, position: Int) {
    val holder = h as DocumentFilesViewHolder
    if (position != files.size - 1) {
        holder.file.setImageBitmap(files[position].bitmap)
        holder.cancel.setOnClickListener {
            deleteFileCallback!!(position)
        }
    } else {
        holder.file.setOnClickListener {
            addFileCallback!!(position)
        }
    }
}

А вот это функционал (удаление и добавление):

    adapter.addFileCallback = {
        PickImageDialog.build(PickSetup()).setOnPickResult { result ->
            if (result.error == null) {
                val i = adapter.files.size - 1
                adapter.files.add(i, File(result.bitmap, result.path))
                adapter.notifyItemInserted(i)
            }
        }.show(fragmentManager)
    }
    adapter.deleteFileCallback = {
        val s1 = adapter.files
        val s2 = it
        adapter.files.removeAt(it)
        adapter.notifyItemChanged(it)
        adapter.notifyItemRangeRemoved(it, 1)
    }

Но, к сожалению, возникает множество багов с определением этого последнего элемента.

Вопрос: Как можно реализовать данный функционал максимально эффективно и правильно (может есть какая-то библиотека для этого?). Буду рад каждому, кто поможет мне!

Answer 1

В RecyclerView может быть несколько разных видов ViewHolder одновременно. Вам надо сделать 2 - один для картинок, второй для кнопки добавления. В адаптере должно быть примерно следующее:

@Override
public int getItemCount(){
    files.getSize() + 1; //число картинок + 1 на кнопку добавления
}
@Override
public int getItemViewType(int position) {
    return position == files.getSize() ? 1 : 0 //если это последний элемент - значит кнопка, возвращаем соответствующую ей единицу. Если нет - это картинка. Возвращаем 0
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
    if(viewType== 0) 
        return createImageHolder(); //функция createImageHolder возвращает холдер с картинкой
    else if(viewType == 1)
        return createAddHolder(); //эта, соответственно, с кнопкой
}
@Override
public void onBindViewHolder(@NonNull ViewHolder holder, int position){
    if(position != files.getSize())
       fillImageHolder(holder) //если это не кнопка - заполняем данными, если кнопка - ничего не делаем. Чем ее там заполнять? =)
}
READ ALSO
RecyclerView неправильно отображает item

RecyclerView неправильно отображает item

В моем приложении есть тестВ каждом из вопросов можно выбрать один из 5 вариантов ответа

118
Как получить Uri записи SQLite Android

Как получить Uri записи SQLite Android

у меня имеется база данных SQLite в которую я добавляю и удаляю данные по принципу описанному ниже

124
Вопрос по стеку и объектам в java

Вопрос по стеку и объектам в java

Объекты находятся в куче, методы и локальные переменные в стеке, стек со всеми методами начинает выполняться при создании объекта, значит...

137
Контролер не изменяет .jsp Spring MVC + Tomcat

Контролер не изменяет .jsp Spring MVC + Tomcat

Контролер возвращает не изменяетjsp файл

122