Мне интересно, если это на самом деле ошибка в Android API:
У меня есть такая настройка:
┌----┬---------┐
| | |
| 1 | 2 |
| |┌-------┐|
| || ||
| || 3 ||
└----┴┴-------┴┘
- Это меню, которое загружает фрагмент № 2 (экран поиска) в правой панели.
- Это экран поиска, который содержит фрагмент № 3, который является списком результатов.
- Список результатов используется в нескольких местах (в том числе как функционирующий фрагмент высокого уровня сам по себе).
Эта функция прекрасно работает на телефоне (где 1, 2 и 3 - ActivityFragment
с).
Тем не менее, когда я использовал этот код:
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
Fragment frag = new FragmentNumber2();
if(toLoad != null) frag.setArguments(toLoad);
transaction.replace(R.id.rightPane, frag);
transaction.commit();
Там , где R.id.leftPane
и R.id.rightPane
находятся <fragment>
с в горизонтальной линейной компоновке.
Насколько я понимаю, приведенный выше код удаляет фрагмент, который является резидентным, а затем заменяет его новым фрагментом. Замечательно ... Очевидно, это не то, что происходит, потому что, когда этот код запускается во второй раз, вы получаете следующее исключение:
07-27 15:22:55.940: ERROR/AndroidRuntime(8105): Caused by: java.lang.IllegalArgumentException: Binary XML file line #57: Duplicate id 0x7f080024, tag null, or parent id 0x0 with another fragment for FragmentNumber3
Это вызвано тем, что контейнер для FragmentNumber3 был продублирован и у него больше нет уникального идентификатора. Первоначальный фрагмент не был уничтожен (?) До добавления нового (на мой взгляд, это означает, что он не был заменен ).
Может кто-нибудь сказать мне, если это возможно ( этот ответ предполагает, что это не так), или это ошибка?
Ответы:
Вложенные фрагменты в настоящее время не поддерживаются. Попытка поместить фрагмент в пользовательский интерфейс другого фрагмента приведет к неопределенному и, вероятно, нарушенному поведению.
ПРИМЕЧАНИЕ (согласно этому документу ): « Примечание. Нельзя раздувать макет на фрагмент, если этот макет включает в себя
<fragment>
. Вложенные фрагменты поддерживаются только при динамическом добавлении к фрагменту ».источник
Fragment
s теперь являются частью Android API, да! developer.android.com/about/versions/… .Библиотека поддержки Android также теперь поддерживает вложенные фрагменты , так что вы можете реализовать проекты с вложенными фрагментами на Android 1.6 и выше.
Чтобы вложить фрагмент, просто вызовите getChildFragmentManager () для фрагмента, в который вы хотите добавить фрагмент. Это возвращает FragmentManager, который вы можете использовать, как обычно, из действия верхнего уровня для создания транзакций фрагмента. Например, вот некоторый код, который добавляет фрагмент из существующего класса Fragment:
Чтобы получить больше информации о вложенных фрагментах, пройдите эти учебники.
Часть 1
Часть 2
Часть 3
и вот SO сообщение, в котором обсуждаются лучшие практики для вложенных фрагментов .
источник
.. вы можете очистить ваш вложенный фрагмент в
destroyview
методе родительского фрагмента :источник
У меня есть приложение, которое я разрабатываю и которое похоже на вкладки на панели действий, и которое запускает фрагменты. Некоторые из этих фрагментов содержат несколько встроенных фрагментов.
Я получал ту же ошибку, когда пытался запустить приложение. Кажется, что если вы создадите экземпляры фрагментов в макете xml после того, как вкладка будет отменена, а затем повторно выбрана, я получу ошибку надувания.
Я решил эту проблему, заменив все фрагменты в xml на Linearlayouts, а затем используя диспетчер фрагментов / транзакцию фрагментов для создания экземпляров фрагментов. Похоже, что сейчас все работает правильно, по крайней мере, на тестовом уровне.
Я надеюсь, что это помогает вам.
источник
Я столкнулся с той же проблемой, пару дней боролся с ней и должен сказать, что самый простой способ преодоления, который я нашел, - это использовать frag.hide () / frag.show (), когда tab выбран / не выбран ().
При повороте экрана все родительские и дочерние фрагменты корректно уничтожаются.
У этого подхода есть еще одно дополнительное преимущество - использование hide () / show () не приводит к тому, что представления фрагментов теряют свое состояние, поэтому нет необходимости восстанавливать предыдущую позицию прокрутки для ScrollView, например.
Проблема в том, что я не знаю, правильно ли не отрывать фрагменты, когда они не видны. Я думаю, что официальный пример TabListener разработан с мыслью, что фрагменты можно использовать повторно, и вы не должны загрязнять ими память, однако, я думаю, что если у вас есть всего несколько вкладок и вы знаете, что пользователи будут часто переключаться между ними, будет целесообразно оставить их привязанными к текущей деятельности.
Я хотел бы услышать комментарии от более опытных разработчиков.
источник
Если вы обнаружите, что ваш вложенный фрагмент не удаляется или дублируется (например, при перезапуске действия, при повороте экрана), попробуйте изменить:
в
Если выше не поможет, попробуйте:
Узнал здесь
источник