[Назад]   [Вперед]

Виктор Кон,   vkBook, Java-Second

Класс webFrame - браузер вэб-страниц

Рассмотрим теперь класс webFrame, который позволяет просматривать html-форматированные файлы, иначе говоря, вэб-страницы. Браузер сделан в режиме разумной достаточности, ничего лишнего. Все установки по умолчанию. Все гиперссылки открываются в новом окне, которое накладывается на предыдущее, но затем может быть сдвинуто в любое место. Размеры любого окна можно менять, но следующее окно открывается стандартным образом, как было вначале. Естественно, что прибавив дополнительный код можно прибавить браузеру функциональности. Но следует отметить, что он поддерживает только основные конструкции языка html первых версий и неспособен показывать правильно любую страницу в интернете. Однако для показа вашей собственной информации, должным образом сформатированной, он вполне годится и даже очень удобен.

Итак открываем код класса по ссылке и начинаем смотреть, что там написано. Как видите кода совсем немного. Это опять следствие наличия виртуальной машины. Конструктор имеет два аргумента: путь к файлу и параметры окна. Параметры окна копируются во внутренние переменные класса для использования в других внутренних методах. Затем формируется объект класса URL, который хранит гиперссылки. В нашем случае предполагается чтение файла с локальной машины, поэтому вместо конструкции "http://" мы добавляем "file:". Наклонные черты писать не надо, так устроен браузер Java. После этого мы просто вызываем метод createInternalFrame(), у которого два аргумента: первым является объект, возвращаемый методом createEditorPane(fileUrl), у которого аргументом является гиперссылка, а вторым - название окна, для которого мы используем путь к файлу. И все. Но оба этих метода надо еще написать, так как их нет в JVM.

Метод createInternalFrame(Component c, String t), как мы теперь видим имеет первым аргументом объект класса Component. Этот класс является прямым наследником прародителя - класса Object - и в свою очередь является родителем всех классов, реализующих графический интерфейс с пользователем. Первой командой мы заказываем объект уже знакомого нам класса JInternalFrame, но в данном случае мы его не расширяем, а используем непосредственно конструктор. У конструктора первым аргументом стоит имя окна, а затем 4 логические переменные, устанавливающие режимы изменения размеров окна, закрытия окна крестиком, способность максимально открыть окно, или свернуть его в иконку. Чтобы не перепутать, в нижней строке написан комментарий - подсказка. Мы заказали первые два свойства и отказались от последних двух. При желании это можно изменить. Даже можно вынести эти свойства в файл Second.ini как входные параметры. Но мне и так хорошо, а вы можете попробовать по другому. Далее мы передаем внутреннюю панель окна прямо объекту ifr. Раньше, как вы помните, мы для этого открывали объект класса Container. С контейнером нагляднее читать, но можно и так. И сразу передаем этой панели наш объект класса Component из аргументов. Остальной код вам уже знаком. Кстати объект ifr объявлен как final. Это просто означает, что мы не намерены его переопределять. Это указание позволяет компилятору оптимизировать работу программы, но и без него все бы прекрасно работало.

Таким образом, первый метод достаточно прост и понятен. Рассмотрим второй метод. createEditorPane(URL u). Он возвращает объект класса Component, как написано в заголовке. На самом деле он возвращает объект класса JScrollPane(new JEditorPane()), как следует из оператора return. Это нормально, так как последний класс является наследником первого класса. Просто в такой постановке код удобно переписывать в будущем на любые другие объекты. Итак мы возвращаем объект класса JEditorPane, вставленный при необходимости в рамку из линеек прокрутки, которую генерирует объект класса JScrollPane. Класс JEditorPane специально сделан как программа, способная работать, в частности показывать, не только с простым текстом, но и с html-форматированным текстом, а также с rtf-форматированным текстом. Это и есть наш браузер в готовом виде. Мы устанавливаем свойство только показа текста методом setEditable(false). Но нам необходимо еще обеспечить работу по разрешению гиперссылок. Вот здесь как раз используется достаточно сложная конструкция

ep.addHyperlinkListener
(new HyperlinkListener()
 {public void hyperlinkUpdate(HyperlinkEvent event)
  {if(event.getEventType() == HyperlinkEvent.EventType.ACTIVATED)
   {createInternalFrame(createEditorPane(event.getURL()),event.getURL().toString());
 }}}
);
Попробуем разобраться. Вызывается метод addHyperlinkListener, аргументом которого является объект класса HyperlinkListener. Но сразу, после указания конструктора этого класса, записан в фигурных скобках сам класс. Это и есть самый внутренний класс, который только может быть. Я упоминал о них в лекциях цикла First. Так как он достаточно компактный, то для него не делается формальной атрибутики, а он сразу записывается после конструктора. В этом классе есть только один метод public void hyperlinkUpdate(HyperlinkEvent event), и в этом методе отслеживается событие по использованию гиперссылки. Если гиперссылка вызывается (кликается), то запускается снова известный нам метод createInternalFrame(createEditorPane(event.getURL()),event.getURL().toString()), но у которого теперь другие аргументы, а именно, адрес файла взят из события.

В чем тут сложность для понимания. Мы видим рекурсию. Одна подпрограмма вызывает другую, а та в свою очередь, вызывает первую, которая ее вызвала. В старых языках такое было бы невозможно. Но в объектно-ориентированном языке это нормально. Ведь внутренняя подпрограмма вызывает новый объект внешнего класса. Старый объект этого класса (объявленный final) остается на экране и с ним ничего не происходит. Но появляется новое окно, вот и все. То есть реально никакой рекурсии нет, а есть размножение объектов, в нашем случае окон с веб-страницами. Остаток кода просто устанавливает содержание файла по гиперссылке в окно браузера методом setPage. Как видите, код очень компактный и практически все делается виртуальной машиной. При желании можно было бы добавить разных настроек, но это в другой раз. А пока с этим классом все.


[Назад]   [Вперед]
Hosted by uCoz