Android - встановлення ідентифікатора фрагмента


Відповіді:


117

Неможливо встановити ідентифікатор фрагмента програмно .

Однак є те, String tagщо ви можете встановити всередині FragmentTransaction, який можна використовувати для унікальної ідентифікації фрагмента.

Як зазначив Олексій, ви можете передати ідентифікатор FragmentTransaction«S add(int, Fragment)методом. Однак це не визначає ідентифікатор для фрагмента. Він визначає ідентифікатор а, який ViewGroupпотрібно вставити Fragmentв. Це не так корисно для тієї мети, яку я очікую, що у вас є, оскільки вона не однозначно ідентифікує Fragments, але ViewGroups. Ці ідентифікатори є контейнерами , до яких динамічно можна додати один або кілька фрагментів. Використання такого методу для ідентифікації Fragments вимагає від вас ViewGroupдинамічного додавання s до макета для кожної Fragmentвставки. Це було б досить громіздко.

Так що, якщо ваше запитання полягає в тому , щоб створити унікальний ідентифікатор для фрагмента ви додаєте динамічно, то відповідь полягає в використанні FragmentTransaction«s надбудови (INT containerViewId, фрагмент фрагмента, строковий тег) методу і FragmentManager» s findFragmentByTag (String) метод.

В одному зі своїх додатків мене змусили динамічно створювати рядки. Але все одно це не так дорого відносно фактичної FragmentTransaction.

Ще одна перевага методу тегів полягає в тому, що він може ідентифікувати фрагмент, який не додається до інтерфейсу користувача. Дивіться метод додавання FragmentTransaction (Fragment, String) . Fragments не потрібно мати Views! Вони також можуть бути використані для збереження ефемерного стану між змінами конфігурації!


Якщо я використовую тег, а не ідентифікатор для фрагмента, як би я використовував виклик заміни, якому потрібен ідентифікатор ресурсу фрагмента?
Намратха

12
@TomDignan як щодо фрагмента, який буде доданий у ViewPager? Як я можу встановити його тег? Я не можу використовувати транзакції в цій ситуації.
GuilhE

1
@GuilhE Activity забезпечує метод addFragment (), на який можна посилатись із переглядача. Зберігання тегу до цього могло бути виконано за допомогою хешмапу.
Томас Дігнан

1
Чи можна змінити відповідь крихітним підкресленням, щоб підкреслити, що ви можете встановити id у макеті xml? Тому що я особисто не читав інших запитань і мав враження, що взагалі немає способу встановити ідентифікатор фрагменту ...
Іван

41

Виявляється, вам може не потрібно знати ідентифікатор фрагмента.

З документів:

public abstract Fragment findFragmentById (int id)

Finds a fragment that was identified by the given id either
when inflated from XML or as the container ID when added in
a transaction.

Важлива частина - "як ідентифікатор контейнера при додаванні в транзакції".

так:

getSupportFragmentManager()
    .beginTransaction()
    .add(R.id.fragment_holder, new AwesomeFragment())
    .commit();

і потім

AwesomeFragment awesome = (AwesomeFragment)
     getSupportFragmentManager()
          .findFragmentById(R.id.fragment_holder);

отримає вам будь-який (дивовижний) фрагмент у R.id.fragment_holder.


4

У більшості випадків ви можете використовувати тег фрагмента, а також ідентифікатор.
Ви можете встановити значення тегу в FragmentTransaction.add(Fragment fragment, String tag );. Потім ви можете скористатися командою, FragmentManager.findFragmentByTag(String tab)щоб знайти розглянутий фрагмент.


2

Як вже згадують Том та інші, є способи поставити тег на фрагмент і використовувати його для ідентифікації. Наступна проблема, з якою я зіткнувся з цими рішеннями, полягає в тому, що фрагмент не отримує тег, поки він не буде пов'язаний з Діяльністю (або, власне, з FragmentManager). Що робити, якщо потрібно ідентифікувати фрагмент, перш ніж він був позначений?

На сьогоднішній день всі мої рішення покладаються на найдавніший трюк (Java) у світі: створити мінімалістичний фрагмент шаблону, який містить ідентифікатор в одному з його конструкторів і надає getFragmentId()метод, який повертає цей ідентифікатор. Тоді я дозволяю тим фрагментам, які потребують ранньої ідентифікації, розширити цей шаблон і; вуаля! Проблема вирішена.

На жаль, для цього рішення може знадобитися набір фрагментів шаблону, по одному для кожного типу фрагменту ListFragment, DialogFragmentабо звичайний старий Fragment(POFO ?!), який потребує ранньої ідентифікації. Але це піддається управлінню у випадку з фрагментами, які я думаю, враховуючи отримані прибутки.

Вибачте, що роздирає загоюючі рани :-)

Ура!


0

Використовуйте наступне:

Щоб додати фрагмент:

getFragmentManager().beginTransaction().add(R.id.fragment_container, fragmentToBeAdded, tag).commit();

Для ідентифікації наявного фрагмента:

getFragmentManager().findFragmentByTag(fragmentName);

Відповідь не стосується питання. Будь ласка, оновіть відповідь. Щасливе кодування
CodeWithVikas

-1

Під час використання тегу обов'язково додайте

fragmentTransaction.addToBackStack(null); 

метод, щоб ваш фрагмент відновився замість знищеного, як зазначено в посібниках для розробників.

Якщо ви не викликаєте addToBackStack () при здійсненні транзакції, яка видаляє фрагмент, то цей фрагмент знищується, коли транзакція здійснена, і користувач не може повернутися до неї. Оскільки, якщо ви видаєте addToBackStack () під час видалення фрагмента, фрагмент зупиняється і пізніше поновлюється, якщо користувач повертається назад.

Ви можете знайти це в кінці цієї сторінки .

Я втратив приблизно 30 хвилин, намагаючись зрозуміти, чому мій Фрагмент не був знайдений через простий findFragmentByTag();дзвінок


-2

На додаток до відповіді Тома, метод заміни також підтримує тег фрагмента, крім того, щоб додати метод.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.