Глава 10 (продолжение )
При создании сложной графии необходимы средства группировки графических элементов в один объект. Этой цели служит холст(объект класса Canvas).Холст может быть помещен во фрейм и раскрашен или разрисован посредством соответствующего метода этого фрейма. а может использоваться как неизменное изображение.
Вверх
Пример 10.3
Несколько флагов
Задача
С помощью программы "Создание флагов" нужно вывести на экран разнообразные флаги
Решение
Рассмотрим еще один аспект многооконной программы. Разместить фрейм в позиции с координатами x и y позволяет метод:
Для этого надлежит пронумеровать флаги и расположить окна ступенчато, в направлении к правому нижнему углу (рис 10.5)
Итак программа:
Поскольку в блоке закрытия окна используется оператор e.getWindow().dispose();,
public class FlagMaker2 extends Frame
{
/** General Flag drawing program J M Bishop April 2000
public FlagMaker2()
{
public static void main(String [] args)
{
public static void makeFlag (FlagCanvas canvas)
{
//===========================
String country;
FlagCanvas (String c, Color b1, Color b2, Color b3,int f)
{
public void paint (Graphics g)
{
Методы и классы пакета awt: резюме
В завершение раздела поговорим о том, какие классы пакета awt и какие методы этих классов наиболее часто употребляются. В наших программах применялись главным образом классы Frame, Window, Container и Graphics. Наибольшее распространение получили классы Component(главный класс пакета awt ) и Graphics. Метод setTitle можно получить из класса Frame, а класс Сontainer используется только в тех случаях, когда планируется применение группирующих компонентов, как показано в следующем разделе. Отношения между классами в пакете awt показаны на рис 10.6
Вверх
Обработка графики - это всего лишь один из аспектов GUI. Другой - создание легко реагирующей среды, с помощью которой пользователь сможет взаимодействовать с программой. Для этой цели Java предлагает множество компонентов (рис 10.1). Эти компоненты не реализуются методом paint, а создаются как объекты с определенными значениями конструктора, после чего добавляются во фрейм в соответствии с действительной схемой размещения.
Наиболее простые компоненты - это класс Label, предоставляющий возможность выводить фрагменты текста, и класс Button, который является базисным средством для взаимодействия с программой. Пакет awt содержит много таких компонентов, некоторые из них мы рассмотрим в следующих разделах.
Класс Label обеспечивает вывод простого текста, передаваемого в качестве параметра его конструктору:
Программа. Создается класс Flags, расширяющий класс Canvas и содержащий исправленный конструктор и метод раскраски. Для каждого флага формируется отдельный фрейм, чтобы любой из этих объектов имел свое окно. Для этого разрабатывается метод makeFlag, который создает экземпляр нового фрейма. а затем производит процедуры создания заголовка. назначения размера и т.д. Но в этот раз мы явно добавляем во фрейм холст или компонент.
setLocation(x,y);
для выхода из программы нужно после закрытия всех трех окон нажать клавиши [Ctrl-C]
import java.awt.*;
import java.awt.event.*;
* ====================
* Works for several flags as well as different designs.
* Illustrated inhertiance
**/
flag = new FlagCanvas
("Germany",Color.black,Color.red,Color.yellow,0);
makeFlag(flag);
flag = new FlagCanvas
("The Netherlands",Color.red,Color.white,Color.blue,1);
makeFlag(flag);
flag = new FlagCanvas
("Ethiopia",Color.green,Color.yellow,Color.red,2);
makeFlag(flag);
f.add(canvas);
f.setTitle(canvas.country);
f.setSize(300,250);
f.setLocation(75*canvas.flagNo,75*canvas.flagNo);
f.setVisible(true);
f.addWindowListener(new WindowAdapter()
{
class FlagCanvas extends Canvas
{
Color bar1, bar2, bar3;
int flagNo;
bar1 = b1;
bar2 = b2;
bar3 = b3;
flagNo = f;
// Draw the flag from coloured rectangles
g.setColor (bar1);
g.fillRect (40,40,200,40);
g.setColor (bar2);
g.fillRect (40,80,200,40);
g.setColor (bar3);
g.fillRect (40,120,200,40);
// Label the drawing
g.setColor (Color.black);
g.drawString(country,100,180);
10.3 Компоновка пользовательского интерфейса
Создание объекта Label |
add(new Label("some text"));
|
Метка (объект) Label создается с заданным текстом и добавляется в текущий контейнер(обычно текущий фрейм). |
Например вывести на экран метку Judy Bishop : позволяет следующий оператор:
add(new Label("Judy Bishop :"));
Объект Button создается аналогичным образом, но при этом имеется дополнительное средство, позволяющее реагировать на событие(то есть мы щелкнем на кнопке, которая изображена на экране, а программа совершит некоторое действие). Вот как протекает процесс создания кнопки:
Создание объекта Button |
// объявляется компонент
|
Объявляется объект buttonid, а потом создается экземпляр объекта с заданным текстовым значением.
Затем этот компонент добавляется в текущий контейнер (обычно текущий фрейм). |
Поскольку метод add определяется в классе Container, мы выполняем следующее действие - добавляем кнопку в контейнер, назначенный по умолчанию, то есть во фрейм. с которым работаем. Скоро вы узнаете как объявлять другие контейнеры.
Можно утверждать, что в дальнейшем к кнопкам будут обращаться, поэтому они должны быть представлены переменными с постоянными идентификаторами. Это так же тот случай, когда идентификатор используется вне конструктора, поэтому объектную переменную мы объявляем перед созданием кнопки.
Например, для создания кнопки:
submitButton = new Button("Запуск");
Button submitButton;
add(submitButton);
Почему нет параметров, задающих координаты x и y у фрейма, в который добавляются компоненты? Причина заключается в том, что с этими компонентами( в отличие от графических элементов) работают менеджеры размещения.
Менеджеры размещения
В Java насчитывается пять менеджеров, но мы рассмотрим только три из них: FlowLayout, BorderLayout и GridLayout. Все они реализуют интерфейс LayoutManager, как показано на рис 10.1. Этот интерфейс входит в пакет awt и становится доступным при его импортировании.
Рассмотрим как внедряется менеджер размещения
Подключение менеджера размещения |
setLayout (new Manager(parameters));
|
Один из пять менеджеров размещения реализуется как объект; его экземпляр создается и передается методу setLayout текущего контейнера (например Frame), который затем фиксирует как должны быть расположены компоненты. |
По умолчанию в Java-программе применяется менеджер размещения orderLayout, но для наших целей больше подходит FlowLayout. Он так же является менеджером по умолчанию для апплетов.
Вот пример назначения менеджера размещения:
setLayout (new FlowLayout(FlowLayout.CENTER,horigap,vertigap));
Первый параметр указывает, что элементы, добавляемые во фрейм, должны быть помещены в центр(они так же могут быть выровнены по левому или правому краю). Параметры horigap и vertigap - это константы. которые служат для указания минимального расстояния(в пикселах) между элементами во фрейме. Все эти параметры являются дополнительными, а константа CENTER назначена по умолчанию. Примеры использования менеджера FlowLayout вы найдете в следующих программах.
Реакция на нажатие кнопки
Мы должны предусмотреть не только возможность закрытия окна, но и заставить программу реагировать на нажатие кнопки. В пакете awt.event наряду со слушателем windowListener определен так же actionListener. Этот интерфейс-слушатель имеет только один метда для реализации - actionPerformed. Поэтому кнопки будут связаны посредством ссылок со слушателем actionListener и иметь версии метода actionPerformed. Установка ссылки выполняется в конструкторе немедленно после того, как кнопка объявляется и добаляется в контейнер. Три оператора для кнопкт запуска (submitButton) выглядят следующим образом:
submitButton = new Button("Запуск");
Button submitButton;
add(submitButton);
submitButton.addActionListener(this);
Ссылка this указывает, что текущий фрейм отвечает за определение метода actionPerformed.
На схеме для такой ссылки полезно выделить компоненты GUI и слушатели из массы других классов. В качестве обозначений на схеме выбрали для компонента - прямоугольник с двойной рамкой, для слушателя - конус, а для обработчика событий - стандартный символ метода (рис 10.7).
Метод actionPerformed имеет один параметр - объект ActionEvent, к которому можно обратиться, чтобы выяснить совпадает ли он с одной из кнопок.
Вот в какой последовательности выполняется опрос:
Реакция на нажатие кнопки |
public void actionPerformed(ActionEvent e)
{
|
Рис 10.7 Блок-схема, на которой показана связь между кнопкой, слушателем и обработчиком событий.
Предположим несколько кнопок имеют различные строковые метки. Единственный способ отличить их друг от друга состоит в использовании последовательности операторов if-else, учитывающих все варианты.
Нажатие кнопки - это только одно из событий, поэтому схема, подобная описанной, может пригодиться нам и в дальнейшем. Обработке других событий посвящен раздел 11.2
Применение отступов.
Вверх
Пример 10.4
Предупреждение с двумя ответами
Задача.
Усовершенствуйте программу, которая отображает сообщение о том, что обнаружен вирус, задав вывод двух кнопок в окне сообщения. С помощью одной кнопкт пользователь сможет подтвердить то, что сказано в сообщении. На этой стадии все окно должно стать красным. Вторая кнопка должна имитировать перезагрузку компьютера.
Рис 10.9 Результат работы программы ButtonTest
Алгоритм. Используйте для достижения необходимого результата потоковый менеджер FlowLayout, а так же метки и кнопки. Выберите цвета для фона и переднего плана с помощью класса Color. При нажатии на кнопку загрузить , должно быть закрытие окна. При нажатии кнопкт подтверждение должен измениться цвет фона. Конструктор устанавливает необходимую связь между компонентами и слушателями. Слушатель в свою очередь активизирует метод actionPerformed, который реагирует на события.
Программа.
Программа демонстрирует последовательность программирования GUI. Сообщение, которое будет выведено на экран, объявляется как массив строк. Каждая строка текста выводится на экран путем добавления ее во фрейм в качестве метки. Схема соответствующая программе показана на рис 10.8
class ButtonTest extends Frame implements ActionListener
{
/* The Graphic warning Program by J M Bishop Oct 1996
Button waitButton;
String[] message =
{
ButtonTest ( )
{
public void actionPerformed(ActionEvent e)
{
public static void main(String[] args)
{
Рис 10.9 Результат работы программы ButtonTest
Рис 10.9a Результат работы программы ButtonTest после нажатия на кнопку Wait
Назад |
Начало урока |
Вверх |
Вперед
import java.awt.*;
import java.awt.event.*;
* Java 1.1 by T Abbott Oct 1997
* updated 1.2 by J Bishop May 2000
* produces a warning message but when a warning
* message is pressed, it turns the window red.
* Illustrates buttons, listeners and the handling of events.
*/
Button rebootButton;
"Reboot and run virus",
"remover software"
* up the initial buttons and colour background.
*/
setBackground(Color.cyan);
setForeground(Color.black);
setLayout(new FlowLayout(FlowLayout.CENTER, 15, 10));
for (int i = 0; i < message.length; i++)
add(new Label(message[i]));
waitButton = new Button("Wait");
waitButton.addActionListener(this);
add(waitButton);
rebootButton = new Button("Reboot");
rebootButton.addActionListener(this);
add(rebootButton);
setTitle("Draw Warning");
setSize(180,200);
setBackground(Color.cyan);
setForeground(Color.black);
addWindowListener(new WindowAdapter ()
{
dispose();
System.exit (0);
setBackground(Color.red);
Содержание