Android Nougat: почему флажки на Fragment имеют неполное состояние при программном выборе (но выглядят нормально на Lollipop)

Вот как выглядит моя вкладка настроек (фрагмент) до того, как будут сделаны какие-либо выборки:

нет выбора

Из основного фрагмента пользователь может сделать выбор из счетчика -- выглядит следующим образом (после того, как пользователь сделал выбор):

выбран супер

Когда пользователь делает этот выбор, загружаются ранее выбранные пользователем варианты, сохраненные в пользовательских настройках, и устанавливаются соответствующие флажки. Флажки, которые были показаны на первом снимке, теперь выглядят следующим образом:

частично выбрано

Видите, элементы, для которых теперь установлены флажки розового цвета? Эти элементы становятся розовыми, но галочка почему-то не отображается на Nougat. Эти элементы на самом деле выбраны, потому что если я нажму на них один раз, они станут невыбранными.

Lollipop работает, как и ожидалось Однако, если я запускаю программу на Lollipop, элементы отображаются полностью выбранными (с установленными флажками), как и ожидалось.

Ручная установка их в Nougat работает. Кроме того, если я вручную устанавливаю их (нажимаю на них во время работы приложения) в Nougat, тогда все другие элементы, выбранные в счетчике, работают должным образом, пока приложение продолжает работать. .

флажки установлены, как и ожидалось

Вот основы того, что происходит для тех, кто хочет настроиться:

Когда элемент выбран в Spinner, я получаю rootview и вызываю findViewById()

  addCharsTabCheckBox = (CheckBox)rootView.findViewById(R.id.addCharsTabCheckBox);
     maxLengthTabCheckBox = (CheckBox)rootView.findViewById(R.id.maxLengthTabCheckBox);

После этого я просто вызываю setChecked() для каждого CheckBox:

addCharsTabCheckBox.setChecked(currentSiteKey.isHasSpecialChars());

Вы случайно не знаете, почему это может происходить?

Вы видели такое частичное поведение раньше?

Редактировать #1 Во время работы я также обнаружил, что невыбранные элементы будут отображаться так, как если бы они были частично выбраны (флажки, но серые) и выглядеть следующим образом:

не выбрано, но отмечено

Эти серые элементы не на самом деле выбраны. Кроме того, если я изменяю ориентацию устройства при просмотре этого фрагмента настроек, флажки перерисовываются (очевидно) и отображаются не отмеченными, как и ожидалось.

Редактировать №2

Только что протестировано на Marshmallow, и он работает правильно (или, как и ожидалось) на этом уровне API. зефир тоже работает


ИЗМЕНИТЬ 3

Я создал упрощенный проект на основе шаблона TabPage, предоставленного Android Studio 2.3.3, чтобы более подробно изучить эту проблему.

Общедоступный проект GitHub

Я добавил код в общедоступный репозиторий GitHub, чтобы вы могли получить его и попробовать: https://github.com/raddevus/CheckBoxFragTest

Проект немного отличается от приведенного выше, но оба они основаны на шаблоне, предоставленном Android Studio 2.3.3. Тестовый проект включает в себя 3 вкладки, поэтому я мог выяснить, увижу ли я такое же странное поведение на всех вкладках. СПОЙЛЕР: я этого не делал.

Вот как выглядит приложение на первой вкладке:

вкладка 1

Две самые интересные части

  1. Когда вы нажимаете кнопку [Toggle Checkbox] на вкладке Page 1, она вызывает setChecked для двух флажков (1 флажок на tabPage2 и 1 флажок на tabPage3).

  2. Когда вы нажимаете кнопку на TabPage3, он устанавливает флажок, показанный на tabPage1 (см. выше на изображении).

Проблема

В Nougat, когда вы нажимаете кнопку [Toggle Checkbox] на TabPage1, он устанавливает флажок на tabPage2 в странное состояние, которое мы видели в исходном отчете о проблеме. Однако флажок на tabPage3 установлен и полностью проверен, как вы ожидаете.

ИЗМЕНИТЬ 4

Oreo Android v8.0 API уровня 26

У меня больше данных. Я только что запустил приложение на Oreo (эмулятор) и вижу там ту же проблему. Вот версия, на которой я работал:

версия Орео

Вот как это выглядит, когда я впервые нажимаю кнопку [Toggle Checkbox].

частично выбранное состояние Oreo

Но обратите внимание, что флажок на tabpage3 на самом деле установлен правильно, даже если он установлен из того же статического логического значения:

флажок tabpage3 – выбран

Если вы нажмете кнопку [Toggle Checkbox] во второй раз, вы получите странное состояние серого флажка (который на самом деле не выбран.

частично выбрано невыбрано

Однако флажок на tabpage3 фактически не установлен, как и должно быть.

И теперь, если вы снова нажмете [Toggle Checkbox], он правильно установит флажок на tabPage2 и будет работать правильно, пока приложение будет работать после этого.


comment
Вы выяснили, почему это происходит?   -  person Dalmas    schedule 07.12.2017
comment
@Dalmas Я так и не получил ответа по этому поводу. Это довольно запутанно, потому что я не видел, чтобы это затрагивалось где-либо еще. Вы столкнулись с той же проблемой?   -  person raddevus    schedule 07.12.2017
comment
Да точно такая же проблема. Я обнаружил несколько случаев, когда этого не происходит, но я пока не понимаю, что заставляет это работать, а что нет. Это очень сложно, потому что, кажется, никто не сталкивался с этим...   -  person Dalmas    schedule 08.12.2017
comment
По-видимому, вызов jumpDrawablesToCurrentState() сразу после вызова setChecked(true) решает проблему и показывает правильное состояние. Похоже на баг анимации.   -  person Dalmas    schedule 08.12.2017
comment
@Dalmas Хорошая работа с вызовом jumpDrawablesToCurrentState(). В конце концов я отказался от этой ошибки в моем целевом приложении и переместил флажок, чтобы он был на той же вкладке, и тогда он работал нормально.   -  person raddevus    schedule 08.12.2017
comment
такое же поведение отображается для RadioButtons (stackoverflow.com /вопросы/45926301/). Похоже на проблемы с анимацией фрагментов внутри ViewPager. Первая загруженная страница работает, боковые фрагменты толстые не показывают.   -  person Nipper    schedule 31.01.2018
comment
@Nipper Спасибо, что сообщили здесь дополнительную информацию. Очень хорошо иметь второе подтверждение того, что это, похоже, связано с анимацией.   -  person raddevus    schedule 31.01.2018
comment
я сталкиваюсь с той же проблемой для переключателей и флажков   -  person Ramesh kumar    schedule 25.04.2019
comment
этот jumpDrawablesToCurrentState() работает для меня   -  person Ramesh kumar    schedule 25.04.2019


Ответы (1)


просто назовите это jumpDrawablesToCurrentState() после вызова radioButton.setChecked(true) или checkBox.setChecked(true);

Код, который работал у меня в моем случае


CheckBox checkBox   = (CheckBox) clView;   
checkBox.setChecked(true);
checkBox.jumpDrawablesToCurrentState();

RadioButton radioButton = (RadioButton)  clView; 
radioButton.setChecked(true);
radioButton.jumpDrawablesToCurrentState();
person Ramesh kumar    schedule 25.04.2019