13 Всплывающие окна

advertisement
13
Всплывающие окна
В этой главе рассматриваются:
 создание всплывающих окон;
 установление размеров и позиционирование всплывающих окон;
 коммуникации посредством всплывающих окон;
 закрытие всплывающих окон;
 использование всплывающих окон с предупреждениями Alert.
В предыдущей главе вы узнали, как навигационная функциональность внедряется в приложения, а также на основе каких подходов это может осуществляться.
При создании приложений вам, скорее всего, потребуется обеспечить вывод всплывающих окон или окон редактирования. Flex предусматривает удобный механизм
в виде PopUpManager, который поможет вам в создании, удалении, позиционировании, закрытии и уничтожении окон. При выборе того, какой тип окна следует
добавить в свое приложение, рекомендуется заранее спланировать и решить, какую
роль будет выполнять это всплывающее окно и что в нем будет отображаться. В этой
главе мы рассмотрим разные методики создания всплывающих окон и управления
ими, а также простые способы их стилизации.
13.1. Создание первого всплывающего окна
Создание и манипулирование всплывающими окнами осуществляется посред­
ством PopUpManager. Класс PopUpManager отвечает за инициализацию окон и управление их расположением в разных слоях в приложениях, что избавляет вас от необходимости следить за тем, чтобы не было конфликтов размещения. PopUpManager
прост в использовании и не требует конфигурирования большого числа свойств.
В этом разделе поговорим о создании и удалении всплывающих окон.
13.1.1. Сначала о главном: создание TitleWindow
Создавать всплывающие окна можно несколькими способами. Каждый способ предполагает генерирование минимум одного файла окна, который будет использоваться для отображения этого окна. PopUpManager будет вызывать окно и выполнять его
рендеринг в слое, располагающемся поверх уже имеющихся слоев. Новые всплы-
Глава 13. Всплывающие окна
371
вающие окна будут создаваться аналогичным образом и размещаться поверх других открытых всплывающих окон или окон Alert. При закрытии окна верхнего
уровня на передний план будет выходить окно, располагающееся на следующем по
высоте уровне. Так будет продолжаться до тех пор, пока последнее всплывающее
окно не окажется закрытым, после чего останется основной слой — слой родительского приложения.
В листинге 13.1 используется новый для вас компонент TitleWindow, который
делает все это возможным.
Листинг 13.1. SimplePopupWindow.mxml: компонент TitleWindow в действии
<mx:TitleWindow xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/halo"
width="400" height="100" layout="vertical"
showCloseButton="true"
close="closeMe()">
<fx:Script>
<![CDATA[
import mx.managers.PopUpManager;
protected function closeMe():void{
// данный код мы напишем позднее в этой главе
}
]]>
</fx:Script>
<s:Group>
<s:Label text="Hello there! I’m a simple popup window." />
</s:Group>
</mx:TitleWindow>
При создании всплывающего окна вы сможете воспользоваться компонентомконтейнером, на котором будет базироваться это окно (он также называется базовым
тегом). Одним из самых распространенных и простых в использовании тегов является TitleWindow, содержащий специфичную для окна функциональность (кнопку
закрытия, заголовок и т. п.). Вы также можете использовать Group, HGroup, VGroup или
прочие распространенные контейнеры.
После того как вы сконфигурируете TitleWindow в качестве базового тега всплывающего окна, сможете добавить любые другие теги MXML или ActionScript. В листинге 13.1 мы использовали компонент Label для отображения простого текстового сообщения на экране. Мы обернули данный компонент в контейнер Group, чтобы
сделать его дочерним компонентом TitleWindow, который является компонентом
Halo. Далее по ходу изложения материала рассмотрим оставшиеся секции кода.
Совет по миграции
Если вы решите добавить дочерние контейнеры в контейнер Halo, то они должны быть расширением UIComponent. Примитивы Flex 4 и прочие не основанные на UIComponent компоненты можно
обернуть в Group, который является расширением UIComponent.
Теперь давайте посмотрим, как данное окно можно представить пользователю
посредством PopUpManager.
372
Часть II. Поток и структура приложения
13.1.2. Использование PopUpManager
для открытия окна
Разобравшись к текстом всплывающего окна, вы можете задействовать его на практике, создав код, который будет его использовать. Для этого выполните следующие
шаги.
1. Создайте в Flash Builder проект с именем CH13.
2. Создайте пакет с именем windows в папке проекта CH13 с именем scr.
3. Создайте новый компонент MXML с именем SimplePopupWindow.mxml в пакете
windows.
4. Скопируйте код из листинга 13.1 в новый файл SimplePopupWindow.mxml.
5. Создайте файл testSimplePopup.mxml в (пакет по умолчанию) и скопируйте в него
содержимое листинга 13.2.
Совет
Знайте, что пакет — это то, что в Flash Builder называется папкой, в которой содержатся исходные
файлы.
Листинг 13.2 генерирует всплывающее окно, показанное на рис. 13.1, которое
будет выводиться на экран, как только приложение загрузится.
Рис. 13.1. Базовое всплывающее окно, в котором отображаются простое
текстовое сообщение и пустой заголовок
Листинг 13.2. testSimplePopup.mxml: генерирование всплывающего окна для отображения
Глава 13. Всплывающие окна
373
Это наиболее распространенный и простой механизм вызова нового всплывающего окна. Экземпляр компонента SimplePopupWindow создается и сохраняется в защищенной переменной simpleWindow, благодаря чему вы сможете взаимодействовать с ним, однако об этом мы поговорим чуть позже в данной главе.
Первым аргументом метода addPopUp() является экземпляр компонента, который должен выводиться на экран. Второй аргумент — this — указывает, что родителем всплывающего окна будет являться компонент, который инициировал вывод
этого окна, в нашем случае это Application. Последний аргумент определяет, будет
ли окно модальным. Модальные окна ограничивают пользователей в том плане, что
разрешают им щелкать мышью только в рамках всплывающего окна и не позволяют делать это за его пределами. Поскольку родителем всплывающего окна выступает основное приложение, попытки щелкнуть мышью где-либо за пределами
всплывающего окна будут игнорироваться.
Совет
Важно знать, что родителем всплывающего окна может выступать любой дочерний объект отображения компонента Application, а всплывающее окно будет являться дочерним по отношению к этому объекту отображения, а не к Application.
Теперь, когда вы уже научились создавать всплывающее окно, вам потребуется
знать, как будет происходить его закрытие, когда пользователь решит убрать его
с экрана.
13.1.3. Закрытие всплывающего окна
На рис. 13.2 вы заметите наличие значка × в верхнем правом углу всплывающего
окна. Как вы уже знаете, данный значок является всеми узнаваемой кнопкой закрытия, которая используется во многих веб-приложениях, а также в настольных
приложениях.
Рис. 13.2. Обратите внимание на наличие кнопки закрытия
в правом верхнем углу всплывающего окна
374
Часть II. Поток и структура приложения
Кнопка закрытия будет доступна как опция при использовании тега TitleWindow.
Вы можете получить доступ к этой опции посредством свойства showCloseButton
компонента TitleWindow, которое может принимать значение либо true, либо false,
как показано в листинге 13.1. Если задать для свойства showCloseButton значение
true, то в углу всплывающего окна будет отображаться кнопка закрытия. При щелчке на этой кнопке мышью TitleWindow будет отправлять событие close, которое может использоваться в качестве триггера компонентами, которые назначены для
его прослушивания. В листинге 13.1 событие close, отправляемое TitleWindow, вызывает функцию closeMe.
Вот фрагмент кода, где наглядно иллюстрируется метод closeMe(), использу­
емый для удаления всплывающего окна из поля зрения:
protected function closeMe():void{
PopUpManager.removePopUp(this);
}
Как и функция addPopUp, функция removePopUp может использоваться для ссылки
на любой дочерний объект. Например, основное приложение может прослушивать
событие close от SimplePopupWindow и руководить его закрытием. В данном случае
в качестве замены следует использовать simpleWindow — имя переменной всплывающего окна.
Благодаря тому, что всплывающие окна можно открывать и закрывать, вы получаете возможность создавать собственные пользовательские всплывающие окна
для предупреждения пользователей о произошедших изменениях, получения от
них информации либо для достижения бесчисленного числа прочих целей. Созданное ранее всплывающее окно будет отображаться в левом верхнем углу приложения. Далее поговорим о том, как контролировать позиционирование всплывающих окон.
13.2. Контроль над позиционированием
всплывающих окон
При первом выводе всплывающего окна на экран вы заметите, что оно не позицио­
нируется автоматически в его центре. Вам необходимо предусмотреть для всплывающего окна соответствующие инструкции, связанные с позиционированием,
в противном случае оно будет отображаться в левом верхнем углу родительского
объекта, в котором оно было создано. Далее мы покажем вам, как обеспечивается
автоматическое центрирование всплывающих окон и как вручную контролировать их позиционирование.
13.2.1. Использование метода centerPopUp()
В составе PopUpManager предусмотрен метод centerPopUp(), который позволяет (что
вполне ожидаемо) центрировать всплывающие окна. Метод centerPopUp() принимает один аргумент типа IFlexDisplayObject, которым может быть любой визуальный
компонент, — это имя всплывающего окна, как показано в следующей строке кода:
Глава 13. Всплывающие окна
375
PopUpManager.centerPopUp(IFlexDisplayObject);
IFlexDisplayObject может быть любой переменной всплывающего окна, которую
вы определите. Например, создавая всплывающее окно, мы сохраняли его в переменной simpleWindow. Чтобы применить данный подход в приведенном ранее примере, вам потребуется такой код:
protected function openSimpleWindow():void{
simpleWindow = new SimplePopupWindow();
PopUpManager.addPopUp(simpleWindow, this, false);
PopUpManager.centerPopUp(simpleWindow);
}
Поскольку simpleWindow объявляется как SimplePopupWindow, который реализует
IFlexDisplayObject посредством наследования, как отмечалось в главе 2, simpleWindow
можно напрямую передать методу centerPopUp().
Работа метода centerPopUp()не во всем интуитивно понятна. Большинство Flexпрограммистов полагают, что центрирование всплывающего окна означает, что
оно будет выводиться в центре окна браузера. Однако это не так. Центрирование
всплывающего окна предполагает задание позиции в центре родительского объекта, в котором это всплывающее окно было создано. Если родительский объект
будет занимать небольшую область в правом верхнем углу окна браузера, то метод
centerPopUp()центрирует всплывающее окно в этой области, а не в середине экрана, как определяется главным окном браузера.
Наиболее простая стратегия решения сложных проблем, связанных с позицио­
нированием, заключается в том, чтобы воспользоваться родительским объектом,
располагающимся как можно ближе к корневому элементу приложения, и сделать
видимую на экране область этого родительского объекта максимально большой.
Можно также возложить на основное приложение обязанности по выполнению
всех процедур открытия всплывающих окон (например, отправлять события, прослушивание которых будет вести основное приложение, и, соответственно, генерировать всплывающие окна).
В большинстве случаев метод centerPopUp() отлично подойдет для центрирования всплывающих окон, если речь не будет идти о более точном их позиционировании в соответствии с вашими потребностями. В большинстве ситуаций он станет
единственным инструментом, который вам потребуется для управления позиционированием всплывающих окон.
13.2.2. Расчет размещения всплывающего окна
Всплывающее окно центрируется довольно легко, однако вы сможете задавать для
него и другое место размещения при выводе на экран, а также манипулировать его
размерами. Давайте рассмотрим наглядный пример, для чего создадим в папке scr/
windows еще одно всплывающее окно в виде файла с именем MoveWindow.mxml. Также потребуется создать еще одно тестовое приложение в (пакет по умолчанию) с именем
testMoveWindow.mxml, которое будет использоваться как приложение по умолчанию. В данном проекте (рис. 13.3) во всплывающем окне имеются кнопки, которые посред­ством
щелчка мышью позволят перемещать это окно в любой угол или центр экрана.
376
Часть II. Поток и структура приложения
Рис. 13.3. MoveWindow.mxml: посредством щелчка кнопкой мыши можно манипулировать
координатами x и y и вносить изменения в позиционирование всплывающего окна
Хотя позиционирование всплывающих окон на экране вручную позволяет более
точно задавать место их размещения, оно требует выполнения большего количе­
ства расчетов и большего внимания к тому, где эти окна будут позиционироваться.
В листинге 13.3 представлен фрагмент кода, который позволяет определять текущее местоположение всплывающего окна и его размеры (позже мы будем манипулировать его местоположением, когда станем перемещать данное окно в каждый
из четырех углов экрана). Переменные x и y соответствуют координатам по горизонтали и вертикали.
Листинг 13.3. Доступ к координатам местоположения и размерам всплывающего окна
var
var
var
var
currentX:Number = x;
currentY:Number = y;
currentWidth:Number = width;
currentHeight:Number = height;
Представьте, что линии образуют на экране сетку (рис. 13.4), x и y будут выступать в роли точек позиционирования всплывающего окна или любого другого интересующего вас объекта на этой сетке. В листинге 13.3 x и y — это точки на
сетке.
Рис. 13.4. Визуализация параметров позиционирования всплывающего окна
Глава 13. Всплывающие окна
377
Переменные x и y являются точками, доступными при использовании любого объекта, который может отображаться на экране, и соответствуют текущему положению
объекта на экране. Значения x и y определяют одну конкретную точку на экране.
Если оценить свойства x и y нового всплывающего окна без применения какоголибо позиционирования, то можно заметить, что оба они имеют нулевое значение
(0) (см. верхний левый угол на рис. 13.4). Если соотнести эти значения с высотой
и шириной окна, то можно определить местоположение объекта на экране.
Используя все это как предпосылку для перемещения всплывающего окна, в листинге 13.4 мы демонстрируем, как можно использовать сравнение размеров всплывающего окна с размерами родительского компонента (которым в данном случае
является основное приложение) для расчета нового местоположения этого окна.
Чтобы все стало еще интереснее, мы добавили отступ 10 пикселов от краев.
Листинг 13.4. MoveWindow.mxml: манипулирование позиционированием всплывающего окна
378
Часть II. Поток и структура приложения
Как уже отмечалось, при расчете и задании местоположения всплывающего
окна особенно важно помнить, что все вычисления координат должны выполняться относительно размеров и местоположения родительского объекта, а не координат главного окна.
Сложность позиционирования всплывающих окон может оказаться значительной, когда вы будете иметь дело с модальными окнами. Реализация худшего сценария — когда вы определите модальное окно, которое будет выводиться за пределами
видимой части экрана, — приведет к невозможности использования приложения,
поскольку пользователь не сможет закрыть всплывающее окно или щелкнуть мышью в любой другой части экрана, чтобы высвободить элемент управления модального окна приложения, если не будет предусмотрено какого-либо встроенного механизма закрытия, например, основанного на нажатии клавиши.
Реализация механизма на основе нажатия клавиши
Для реализации механизма, основанного на нажатии клавиши, вам потребуется слушатель событий, связанных
с клавиатурой.
Вот пример:
stage.addEventListener(KeyboardEvent.KEY_UP, onKeyUp, false, 0, true);
...
protected function onKeyUp(event:KeyboardEvent):void{
if(event.keyCode == Keyboard.ESCAPE) close();
}
Это простой пример прослушивания нажатия клавиши: в данном случае, когда пользователь отпустит нажатую
клавишу Esc на клавиатуре, произойдет вызов метода close() для закрытия всплывающего окна.
Задание местоположения всплывающих окон в приложениях является весьма
важным визуальным и функциональным аспектом. Следующим, о чем мы поговорим, является отправка и получение данных из всплывающих окон.
Download