Афоризм
Шаман за скверную погоду недавно в бубен получил.
Последние статьи

 • Активности 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

Урок 14. Интеграция бандлов

В данном уроке рассмотрим вопрос разработки бандла, интерфейс которого можно представить либо в виде отдельного диалогового окна, либо в виде панели, которую можно разместить как в контейнере главного фрейма, так и в контейнере другого бандла. То есть, данный бандл для представления интерфейса будет совмещать в себе возможности использования как базовых модулей base-jdialog и base-jpanel для создания интерфейса, так и базового фрейма base-jframe для предоставления своего контейнера.

Для создания такого универсального интерфейсного бандла в качестве базового модуля используется base-universal. Сразу следует отметить, что расширение функциональных возможностей бандла сопряжено с усложнением его реализации и, соответственно, с восприятием расширенного объема документации. Положительным моментом использования base-universal является то, что подавляющее количество функций, необходимых для межмодульного взаимодействия бандлов приложения, в нем уже реализовано. И в данном уроке основное внимание будет уделено структуре построения бандла и организации механизма «публикации/подписки».

Структура проекта

На скриншоте слева представлен проект templ-universal в IDE Eclipse, детальное описание которого представлено на странице примера использования базового модуля base-universal. Структура проекта включает активатор TemplActivator, классы подготовки создания интерфейсной формы (JDialogForm, JPanelForm), и класс формирования интерфейса CommonGUI. В зависимости от типа представления интерфейсной формы (guimode) активатор использует либо JDialogForm, либо JPanelForm, которые передают в CommonGUI свои контейнеры. Ресурсные файлы проекта, используемые для локализации интерфейса, размещаются в разделе resources/properties.

В конфигурацию приложения данного урока включены четыре разноверсионных сборки бандла 1.0.0, 2.0.0, 1.0.1, 2.0.1. В зависимости от версии бандлы будут по разному стартовать и формировать различный интерфейс. Так, сборки версии 1.0.0 и 2.0.0 будут стартованы главным фреймом с типом интерфейса guimode='jpanel', т.е. это будут родительские бандлы, и свой интерфейс в виде панели они разместят в контейнере главного фрейма.

Бандлы версий 1.0.1 и 2.0.1 будут стартованы из родительских c разными значениями guimode; это дочерние бандлы. Бандл 1.0.1 будет стартован из бандла 1.0.0 со значением guimode='jpanel', т.е. ему нужен родительский контейнер для размещения своей интерфейсной панели. Бандл версии 2.0.1 будет стартован из бандла 2.0.0 со значением guimode='jdialog', т.е. будет открывать диалоговое окно.

Таким образом, в одном флаконе в виде проекта templ-universal будут созданы родительские и дочерние бандлы разных версий.

Особенности использования base-universal

Описывать как проект templ-universal, так и его базовый модуль base-universal не имеет смысла, поскольку это приведет к повторению содержания страниц с их описанием. Поэтому здесь основное внимание уделим задачам, которые должен решать активатор бандла TemplActivator. Остальные классы, предназначенные для формирования интерфейса, управляются активатором бандла, и их бизнес-логика с исходными кодами представлена на странице описания templ-universal.

Чтобы использовать методы базового модуля base-universal необходимо, чтобы активатор TemplActivator наследовал (extends) свойства класса JBActivator.

Старт из главного фрейма

Сначала необходимо поочередно стартовать родительские бандлы 1.0.0 и 2.0.0, из которых можно будет стартовать дочерние. Почему поочередно? Да потому что, в контейнере главного фрейма может разместиться только интерфейс одного бандла. При старте второго, интерфейс первого выгружается и его бандл останавливается.

Поскольку родительские бандлы стартуются главным фреймом, то он должен располагать информацией о типе представления интерфейса guimode. Это значение, доступное главному фрейму, хранится либо в описании структуры «Главного меню», либо в описании «Панели инструментов», т.е. в том месте, откуда будет стартован бандл.

Определение типа интерфейса

Старт бандла выполняется методом активатора start, вызывающий метод суперкласса getGuiMode, который определяет тип создаваемого интерфейса. Если бандл должен быть стартован в режиме guimode='jdialog', будет вызван метод активатора createDialogGUI, который в TemplActivator переопределен. Если его не переопределить, то будет вызван данный метод суперкласса, который не создаст никакого интерфейса. Если бандл должен быть стартован в режиме guimode='jpanel', то он должен у главного фрейма запросить контейнер для размещения своей интерфейсной панели.

Запрос контейнера

Старт подписчика и отправление запроса главному фрейму выполняется суперклассом автоматически. Как только подписчик получит от главного фрейма ответ с контейнером, он вызовет метод активатора getJFrameResponseContainer (Container), который в TemplActivator переопределен. Данный метод стартует процесс создания интерфейсной панели с её размещением в контейнере главного фрейма.

На следующем скриншоте представлен интерфейс бандла версии 1.0.0, размещенный в контейнере главного фрейма.

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

Конечно же, кто-то может возразить такому усложнению алгоритма; почему бы не открыть окно с предупреждением о необходимости предварительно сохранить значения, а потом переходить к другой панели? Но ведь мы работаем в OSGI-приложении, где бандлы между собой не связаны. Поэтому, для реализации данной функции необходимо в бизнес-логику закладывать обмен сообщения о возможности останова одного и старта другого бандла. К тому же надо предусмотреть после сохранения данных или отказа от сохранения выполнение перехода без повторных действий на предыдущем шаге.

Старт из родительского бандла

Старт дочернего бандла выполняется нажатием на кнопку «Стартовать бандл». Процесс подробно представлен на странице описания бандла templ-universal. Как выполняется старт дочернего бандла? Также, как и родительского, с метода start, в котором необходимо определить тип создаваемого интерфейса.

Определение типа интерфейса

Поскольку в структурах описания «Главного меню» и «Панели инструментов» никакой информации о дочерних бандлах данных версий не имеется, следовательно дочерний бандл будет запрашивать режим представления своего интерфейса (guimode) публикацией соответствующего сообщения. Поэтому, при старте дочернего бандла, родительский бандл должен подписаться на соответствующее сообщение, а дочерний бандл при старте перед отправкой запроса должен подписаться на ответ.

Получив ответ о режиме представления интерфейса дочерний бандл принимает решение создавать диалоговое окно, либо запросить контейнер у родительского бандла. На следующем скриншоте представлен интерфейс приложения, на переднем фоне которого мы видим диалоговое окно бандла версии 2.0.1. На заднем фоне представлен интерфейс бандла версии 2.0.0, размещенный в контейнере главного фрейма. Версии бандлов представлены в интерфейсе форм.

Запрос контейнера

Если дочерний бандл создает интерфейс в режиме guimode='jpanel', то между родительским и дочерним бандлами повторно организуется механизм «публикации/подписки» на запрос контейнера. Процесс проходит точно также, как и при запросе типа представляемого интерфейса guimode, с тем отличием, что используются другие сообщения и другие методы/классы. В первоисточнике это представлено наглядно с исходными кодами.

Дочерний бандл, получив контейнер родительского бандла, отображает его в левой панели цветом CYAN, как это представлено на следующем скриншоте : родительский 1.0.0 интегрирует интерфейс дочернего 1.0.1. В верхних частях панелей представлены версии бандлов.

Останов бандлов

Не менее важной задачей является останов дочернего бандла при останове родительского. Родительский бандл получает от главного фрейма соответствующее сообщение об останове, в результате он, при необходимости, может сохранить измененые данные своего интерфейса, чтобы при очередном старте их восстановить. За останов дочернего бандла отвечает родительский, который должен при его активности вызвать команду останова. Если этого не выполнить, в данном сеансе работы приложения невозможно будет его повторно стартовать.

Конфигурация приложения

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

Листинг configuration/bundles.ini

Список используемых в приложении бандлов определяем в файле configuration/bundles.ini. Бандлы с операндом @start и @main после инсталляции во фреймворк сразу же стартуют, т.е. переводятся в активное состояние.

Листинг

bundles=org.apache.felix.eventadmin-1.4.8.jar@start, \
org.apache.felix.log-1.0.1.jar@start, \
util-resources-1.0.0.jar@start, \
util-logger-1.0.0.jar@start, \
base-jframe-1.0.0.jar, \
base-jdialog-1.0.0.jar, \
base-universal-1.0.1.jar, \
gui-menu-1.0.0.jar, \
gui-toolbar-1.0.0.jar, \
gui-widgets-1.0.0.jar, \
templ-universal-1.0.0.jar, \
templ-universal-1.0.1.jar, \
templ-universal-2.0.0.jar, \
templ-universal-2.0.1.jar, \
form-about-1.0.0.jar, \
templ-jframe-1.0.0.jar@main
 

Листинг configuration/toolbar.xml

В файле configuration/toolbar.xml определим структуру панели инструментов и свяжем кнопки с вызываемыми при их нажатии бандлами. Обратите внимание, что описания стартуемых из главного фрейма бандлов templ-universal имеют атрибуты guimode.

Листинг
<?xml version="1.0" encoding="UTF-8"?>
<root name="root" rollover="true" borderpainted="true">
   <toolbar>
      <item name="toolbar.jpanel1" type="button" 
         image="configuration/resources/images/database.png"
         text="toolbar.jpanel1"
         textposition="bottom" width="96" height="64"
         guimode="jpanel"
         groupId="org.jabricks.templates"
         artifactId="templ-universal"
         version="1.0.0" />
      <item name="toolbar.jpanel2" type="button"
         image="configuration/resources/images/database.png"
         text="toolbar.jpanel2"
         textposition="bottom" width="96" height="64"
         guimode="jpanel"
         groupId="org.jabricks.templates"
         artifactId="templ-universal"
         version="2.0.0" />
    </toolbar>
    <toolbar>
      <item name="toolbar.about" type="button"
         image="configuration/resources/images/question.png"
         text="toolbar.about"
         textposition="bottom" width="96" height="64"
         groupId="org.jabricks.about"
         artifactId="form-about"
         version="1.0.0" />
    </toolbar>
</root>

Связанные страницы

Список уроков
Предыдующий, 13-й урок
Следующий, 15-й урок

Скачивание файлов

Бандлы, используемые в уроке 14, файлы конфигурации и файл описания инсталлируемых бандлов собраны и упакованы в один архивный файл configuration.lesson14.zip (493 Кб).

Скачайте и «разверните» архив configuration.lesson14.zip, перенесите файлы в структуру, представленную на странице описания платформы JaBricks.

Используемый в уроке бандл templ-universal можно скачать в виде проекта IDE Eclipse на странице описания templ-universal.

  Рейтинг@Mail.ru