Афоризм
Терпи, любимый. Я ж к тебе привыкла.
Последние статьи

 • Активности Android
Многоэкранные Android приложения
 • Fragment dynamic
Динамическая загрузка фрагментов в Android
 • Fragment lifecycle
Жизненный цикл Fragment'ов в Android
 • Fragment example
Пример Fragment'ов в Android
 • Data Binding
Описание и пример Data Binding
 • Пример MVVM
Пример использования MVVM в Android
 • Компонент TreeTable
Описание компонента TreeTable для Swing
 • Пример TreeTable
Пример использования TreeTable
 • Хранилища Android
Внутренние и внешние хранилища данных
 • Пример SQLite
Пример использования SQLite в Android
 • WebSocket
Описание и пример реализации WebSocket
 • Визуальные компоненты
Улучшен компонент выбора даты из календаря
 • Анимация jQuery
Описание и примеры анимации элементов DOM
 • APK-файл Android
Создание apk-файла для android устройств, .dex файлы
 • платформа JaBricks
Платформа OSGi-приложения JaBricks
Поддержка проекта

Если Вам сайт понравился и помог, то будем признательны за Ваш «посильный» вклад в его поддержку и развитие
 • Yandex.Деньги
  410013796724260

 • Webmoney
  R335386147728
  Z369087728698

Фрагменты в Android

Включение в Android-приложение нескольких активностей (activity) не всегда может быть оправданным. Так, если для смартфонов с небольшими экранами использование разных Activity выглядит довольно неплохо, то на больших экранах (планшетах, телевизорах) окна Activity могут занимать небольшую часть экрана. Именно поэтому и появилась концепция фрагментов (Fragment).

Fragment имеет небольшое схожество с Activity; у фрагмента есть свой жизненный цикл, во многом совпадающий с жизненным циклом активности. Пожалуй, это и есть единственное сходство с активностью. С жизненным циклом фрагмента можно познакомиться здесь.

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

Фрагменты появились в Android начиная с версии API 11, позволяя разработчикам разрабатывать более гибкие пользовательские интерфейсы под устройства с разными размерами экранов, как это представлено на следующем рисунке.

Фрагменты android

Плюсы по сравнению с использованием activity видны сразу :

  • c помощью Fragment можно легко создать дизайн, адаптивный под смартфоны и планшеты;
  • приложение состоит из набора функциональных модулей, поддержка которых обходится «дешевле».

Таким образом, фрагменты облегчают построение адаптивного интерфейса из «шаблонов», которые можно динамически отобразить на экране устройства, скрыть или заменить другим фрагментом.

AndroidX Fragment Library

Первоначально для старых устройств, в целях совместимости приложений, была создана специальная библиотека. Длительное время сосуществовали два класса Fragment для старых и для новых устройств, у которых названия методов и классов были очень похожи. При разработке нового и поддержке существующего приложения это приводило к путанице; в одном проекте смешивались два разных несовместимых класса. Спустя некоторое время от такого разделения фрагментов решили отказаться; класс для новых устройств признали deprecated, а класс из библиотеки поддержки старых устройств вошёл в состав библиотеки AndroidX.

В настоящее время, чтобы использовать все функциональные возможности фрагментов, необходимо в проекте подключить AndroidX Fragment Library, которая располагается в отдельной библиотеке. Подключение библиотеки выполняется в файле модуля/проекта build.gradle (см. пример).

...
dependencies {
    implementation "androidx.fragment:fragment:1.4.1"
    ...
}
 

Включение фрагмента в активность

Включить фрагмент в активность можно как статически, так и динамически. При статическом размещении фрагмента необходимо в шаблоне интерфейса активности (main_activity.xml) использовать тег <fragment>, при динамическом – контейнер <FrameLayout>. В следующем примере представлены секции статического и динамического включения фрагментов в интефейс активности. При статическом подключени фрагмента необходимо указать класс (android:name) и интерфейсный шаблон (tools:layout). С примером статического и динамического включения фрагментов в активность Вы можете познакомиться здесь.

<fragment
    android:id="@+id/fragment1"
    android:name="com.example.FragmentExample1"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_weight="1"
    tools:layout="@layout/fragment_example1">
</fragment>
<FrameLayout
    android:id="@+id/fragment2"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_weight="1">
</FrameLayout>
 

Создание фрагмента

Класс фрагмента должен наследовать androidx.fragment.app.Fragment. Существует подклассы фрагментов : ListFragment, DialogFragment, PreferenceFragment, WebViewFragment. В следующем скрипте представлен пример описания класса фрагмента.


class FragmentExample extends Fragment {
    public FragmentExample() {
        super(R.layout.fragment_example);
    }
}
 

Фрагмент – это не картинка в интерфейсе, а набор необходимых компонентов для отображения некоторого контента и реализации заданной бизнес-логики. Как было отмечено выше, фрагмент также, как и активность, имеет свой жизненный цикл, на определенных этапах которого фрагмент может взаимодействовать с активностью и с другими фрагментами. В следующем примере представлен класс фрагмента с двумя методами жизненного цикла, которые вызываются системой. В методе onAttach фрагмент определяет «родительскую» активность (activity). В методе onCreateView класс фрагмента подключает к своей кнопке (определена в шаблоне) обработчик события onClick.


import androidx.fragment.app.Fragment;
import androidx.appcompat.app.AppCompatActivity;

class FragmentExample extends Fragment
{
    @Override
    public void onAttach(Context context)
    {
        super.onAttach(context);
        AppCompatActivity activity = null;
        if (context instanceof AppCompatActivity) {
            activity = (AppCompatActivity) context;
        }
    }
	
    @Override
    public View onCreateView(LayoutInflater inflater,
                             ViewGroup container,
                             Bundle savedInstanceState)
    {
        View    view = null;
        Button  btn  = null;

        view = inflater.inflate(R.layout.fragment1, null);
        button = (Button) view.findViewById(R.id.button);

        btn.setOnClickListener(new View.OnClickListener(){
            public void onClick(View v) {
                // ...
            }
        });
        return view;
    }
}
 

Примечание
1. Статическое и динамическое включение фрагмента в активность, а также взаимодействие фрагмента с активностью и с другим фрагментом интерфейса рассмотрено в примере.
2. Подробное описание жизненного цикла фрагмента представлено здесь.

FragmentManager, FragmentTransaction

Класс android.app.FragmentManager предназначен для выполнения таких операций, как добавление, удаление и замену фрагментов, а также добавления этих операций (иначе называемых транзакциями) в стек (back stack). Чтобы внутри активности получить реализацию FragmentManager необходимо использовать метод getSupportFragmentManager(). Внутри фрагмента менеджер можно получить либо методом getChildFragmentManager() для дочерних объектов, либо методом getParentFragmentManager() родительской активности.

Для непосредственного выполнения операций с фрагментами менджер FragmentManager использует android.app.FragmentTransaction. Ниже представлен код размещения фрагмента в интерфейсе активности. В примере параметр R.id.fragmentContainer определяет контейнер фрагмента типа FragmentLayout. Для добавления фрагмента в контейнер активности был использован метод add класса FragmentTransaction.


Fragment1           fragment1 = ...;
FragmentManager     fragmentMgr  ;
FragmentTransaction fragmentTrans;

fragmentMgr   = getSupportFragmentManager();
fragmentTrans = fragmentMgr.beginTransaction();

fragmentTrans.add(R.id.fragmentContainer, fragment1);

fragmentTrans.commit();

Чтобы удалить фрагмент из активности необходимо использовать метод remove(fragment). Ну, а если нужно заменить один фрагмент на другой необходимо использовать метод replace(container, fragment), как это представлено в следующем примере.


Fragment2 fragment2 = ...;

fragmentMgr   = getSupportFragmentManager();
fragmentTrans = fragmentMgr.beginTransaction();

fragmentTrans.replace(R.id.fragmentContainer, fragment2);

fragmentTrans.commit();
 

Таким образом, методы добавления add и замены replace в качестве параметров получают идентификатор контейнера и реализацию (класс) фрагмента. Метод удаления фрагмента remove(Fragment) – только фрагмент.

BackStack

Как было отмечено выше система позволяет сохранять манипуляции с фрагментами в BackStack, а кнопкой устройства Назад (стрелка на устройстве <) отменять. Также можно откатить транзакцию программно. Чтобы записать транзакцию в стек необходимо использовать метод addToBackStack. А чтобы вернуть её назад — метод popBackStackImmediate.

addToBackStack (String name)
Метод добавляет транзакцию в стек. Транзакция фиксируется в стеке, после того, как она завершена (commit).

fragmentMgr   = getSupportFragmentManager();
fragmentTrans = fragmentMgr.beginTransaction();

fragmentTrans.add(R.id.fragmentContainer, fragment1);
fragmentTrans.addToBackStack(null);
fragmentTrans.commit();

popBackStackImmediate ()
Метод возвращает транакция из стека назад, т.е. восстанавливает предыдущее состояние интерфейса.

fragmentMgr   = getSupportFragmentManager();
fragmentTrans = fragmentMgr.beginTransaction();

fragmentMgr.popBackStackImmediate();
fragmentTrans.commit();

Более подробно о константах и методах класса FragmentTransaction можно прочитать в документации FragmentTransaction.

  Рейтинг@Mail.ru