getAdapterPosition somtimes возвращает неправильное значение

#java #android

#java #Android

Вопрос:

Я пытаюсь создать адаптер для RecyclerView, где каждое представление содержит некоторую информацию и две кнопки, одну для удаления представления и одну для обновления информации. Я настраиваю прослушиватель следующим образом, и я заставляю действия работать так, как я хочу (т. Е. removeRecepie и chooseNewRandomRecepie делает то, что я хочу, чтобы они делали).

Однако иногда, по-видимому, случайным образом, getAdapterPosition отправляет неверную позицию. Таким образом, удаление или обновление происходит с неправильным представлением (я протестировал вывод getAdapterPosition , и вывод соответствует изменяющемуся представлению, то есть неправильному). Я написал setListener следующим образом:

     void setListener(View view){
        Button removeButton = view.findViewById(R.id.remove_button);
        removeButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                removeRecepie(getAdapterPosition());
            }
        });
        Button newRandomButton = view.findViewById(R.id.new_random);
        newRandomButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                chooseNewRandomRecepie(getAdapterPosition());
            }
        });
    }
  

Я был бы очень благодарен за любую помощь или указатели на помощь. Пожалуйста, дайте мне знать, если есть какая-либо дополнительная информация, которую я могу включить, чтобы помочь вам помочь мне 🙂

Комментарии:

1. getAdapterPosition в некоторых случаях может возвращать -1 (вы должны проверить это, прежде чем вызывать что-либо с ним), но никогда неправильное положение. Вероятно, в вашем наборе данных есть некоторые противоречивые данные при добавлении или удалении элементов..

2. при добавлении или удалении элемента из адаптера может быть счетчик изменений

Ответ №1:

Вы должны использовать onBindViewHolder .

 public void onBindViewHolder(@NonNull MyViewHolder holder, int position) {
        holder.removeButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                removeRecepie(position);
            }
        });
        holder.removeButton.SetOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                chooseNewRandomRecepie(position);
            }
        });
    }

    public class MyViewHolder extends  RecyclerView.ViewHolder implements View.OnClickListener {

        Button removeButton;
        Button newRandomButton;

        public MyViewHolder(@NonNull View itemView) {
            super(itemView);
            removeButton = itemView.findViewById(R.id.removebutton);
            newRandomButton = itemView.findViewById(R.id.newRandomButton);
        }
    }
  

Комментарии:

1. Нет, нет необходимости выполнять setup clicklistener в onBindViewHolder методе.

2. setListener Метод вызывается для держателя внутри onBindViewHolder (извините, что не указал это ранее). Однако изменение removeButton и newRandomButton полей и создание их экземпляров в конструкторе ViewHolder, похоже, делает свое дело (как в этом ответе). У кого-нибудь есть идеи, почему это может быть?