От новичка до гуру: Курсы программирования на CyberDuff

Отменить выбор элемента в ListView

Это сценарий: в ListView я хотел бы, чтобы выбранный элемент оставался выбранным, пока пользователь не нажмет кнопку DialogFragment. Проблема в том, что если пользователь нажимает кнопку "Назад" без какого-либо щелчка в DialogView, элемент в ListView остается выбранным.

Я прочитал это сообщение, и решения работают достаточно хорошо: я нажимаю на элемент, появляется диалоговое окно, я нажимаю кнопку «Назад», и селектор исчезает.

Но если я прокручиваю список, селектор возвращается! Где я не прав?

Вот код:

<ListView
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:id="@+id/listView"
        android:layout_gravity="center"
        android:layout_marginLeft="10dp"
        android:layout_marginTop="15dp"
        android:layout_marginRight="10dp"
        android:layout_marginBottom="15dp"
        android:divider="@android:color/transparent"
        android:visibility="visible"
        android:dividerHeight="5dp"
        android:choiceMode="singleChoice"
        android:drawSelectorOnTop="true"
        android:listSelector="@color/primario_1_alfa"/>

и DialogFragment, где я пытаюсь отменить выбор элемента списка

public class MyDialog extends DialogFragment {

    @Override
    public Dialog onCreateDialog(Bundle savedInstanceState) {
        AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
        builder.setMessage("Test dialog view")
                .setPositiveButton("action 1", new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int id) {

                    }
                })
                .setNegativeButton("action 2", new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int id) {

                    }
                });
        return builder.create();
    }
    @Override
    public void onDestroy(){
        super.onDestroy();
        ListView listView = (ListView) getActivity().findViewById(R.id.listView);
        listView.clearChoices();
        listView.requestLayout();
    }
}

  • Вы используете шаблон ViewHolder для своего адаптера списка? 29.07.2015
  • да, я использую этот шаблон 29.07.2015
  • тогда это связано с повторным просмотром просмотров. 29.07.2015

Ответы:


1

Это связано с повторным использованием представлений с использованием шаблона ViewHolder.

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

int selectedPosition;
...
onItemClickListener(int position, ...) {
   selectedPosition = position;
}
...
getView(int position, ...) {

   if (selectedPosition == position) {
      view.setSelected(true);
   } else {
      view.setSelected(false);
   }
}

Что-то в этом роде.

28.07.2015
  • Извините, @androidpotato7, но мне нужна еще подсказка :). После закрытия диалогового окна мне не нужно выбирать какую-либо строку, и я думаю, что view.setSelected(false); для каждой строки было бы достаточно, но это не работает. Как и ваше решение, я изменил метод getView адаптера, как вы предложили, и добавил код selectedPosition = position; в метод onItemClick слушателя. Зачем мне нужна позиция, если я хочу весь раунд без селектора? Спасибо :) 29.07.2015
  • потому что просмотры могут быть переработаны в любой момент, никогда не знаешь. Так что, по крайней мере, selectedPosition и if в getView позволяют вам точно контролировать, кто будет выбран или нет. Реализуйте решение, которое я предложил, и ПОСЛЕ закрытия диалогового окна вызовите notifyDatasetChange() на адаптере, и все представления будут перерисованы, а поскольку позиция не выбрана (укажите selectedPosition = -1), все представления будут отрисованы с selected == false 29.07.2015
  • Новые материалы

    Основы Spring: Bean-компоненты, контейнер и внедрение зависимостей
    Как лего может помочь нашему пониманию Когда мы начинаем использовать Spring, нам бросают много терминов, и может быть трудно понять, что они все означают. Итак, мы разберем основы и будем..

    Отслеживание состояния с течением времени с дифференцированием снимков
    Время от времени что-то происходит и революционизирует часть моего рабочего процесса разработки. Что-то более забавное вместо типичного утомительного и утомительного процесса разработки. В..

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

    Игра в прятки с данными
    Игра в прятки с данными Я хотел бы, чтобы вы сделали мне одолжение и ответили на следующие вопросы. Гуглить можно в любое время, здесь никто не забивается. Сколько регионов в Гане? А как..

    «Раскрытие математических рассуждений с помощью Microsoft MathPrompter и моделей больших языков»
    TL;DR: MathPrompter от Microsoft показывает, как использовать математические рассуждения с большими языковыми моделями; 4-этапный процесс для улучшения доверия и рассуждений в математических..

    Раскройте свой потенциал в области разработки мобильных приложений: Абсолютная бесплатная серия
    Глава 6: Работа в сети и выборка данных Глава 1: Введение в React Native Глава 2: Основы React Native Глава 3: Создание пользовательского интерфейса с помощью React Native Глава 4:..

    Все о кейсах: Camel, Snake, Kebab & Pascal
    В программировании вы сталкивались с ними при именовании переменной, класса или функции. Поддержание согласованности типов и стилей случаев делает ваш код более читабельным и облегчает совместную..