Опубликован: 10.12.2007 | Уровень: специалист | Доступ: платный
Лекция 2:

Верстка с XUL

2.1 XUL - это блоки

При изучении HTML обычно начинают с тегов вроде <P> и <H1>. И только получив некоторый опыт, мы понимаем, как полезен незаметный тег <SPAN>. Тег <H1>, например, можно легко заменить тегом <SPAN> с соответствующими CSS-стилями, например: display:block и font-size:large. И так можно поступить со многими тегами, не только с этим - всего лишь использовать <SPAN> и несколько правил стилей. Изучение HTML обычно не начинают со <SPAN>, поскольку кажется, что сам по себе он "ничего не делает"; обычно он никак не проявляется.

В XUL тег <box> играет ту же роль, что и <SPAN> в HTML, только вот научиться пользоваться <box> нужно с самого начала. Важно, чтобы вы как можно быстрее научились работать с XUL-блоками. В листинге 2.2 приведен фрагмент кода на XUL, демонстрирующий типичное использование блоков для структурирования данных.

<box orient="horizontal">
  <box orient="vertical">
    <description>Яблоки</description>
    <description>Апельсины</description>
  </box>
  <box orient="vertical">
    <description>HTML</description>
    <box orient="horizontal">
      <description>XUL</description>
      <description>XBL</description>
    </box>
  </box>
</box>
Листинг 2.2. Фрагмент кода на XUL, иллюстрирующий использование блоков для структурирования их содержимого

В этом примере тегов <box> так же много, как и "настоящих" тегов. Для XUL это нормально. Нужно привыкать использовать их практически "на автомате". На рисунке 2.1 показано, как эти данные могли бы выглядеть в Microsoft Windows, если бы документ был завершен.

Визуализация блоков

Рис. 2.1. Визуализация блоков

На этом снимке окна вместе с разметкой XUL использовались простые правила стилей CSS, чтобы блоки выглядели нагляднее. В каждом блоке есть два тега, и их содержимое отображается или друг за другом или друг над другом. Такое расположение - цель использования <box>. Обычно видимые границы имеют только один или два блока. В листинге 2.3 приведены правила стилей, использовавшиеся для примера.

box { 
  border : solid;
  border-color: grey;
  padding: 4px;
  margin: 2px;
}
Листинг 2.3. Простая таблица стилей для отображения границ блоков.

Очевидно, что разметка с помощью XUL и оформление с помощью CSS очень похожи на аналогичные процедуры с HTML - по крайней мере, в основном. Но насколько они похожи? Начать изучение с блоков означает освоить правила визуального форматирования. Изучив их, мы сможем экспериментировать с CSS-стилями - таким образом можно узнать о разметке с помощью XUL очень многое.

2.2 Принципы верстки XUL

Верстка внешнего вида документа на XUL - процесс преобразования содержимого тегов к виду, удобному для восприятия человеком. Верстка XUL и проектирование приложения – не одно и то же. О первом автоматически позаботится браузер. Второе - задача для программиста или дизайнера. Здесь описывается автоматическая визуализация разметки документов.

Правила визуальной организации HTML-данных описывают, в частности, модель представления документов в виде блоков, определенную в стандарте CSS 2, раздел 8 (см. http://www.w3.org/TR/REC-CSS2). HTML и XUL используют несколько общих стилей CSS 2, в том числе правила оформления блоков. Несложно догадаться, что такая модель представления также используется XUL. Но это еще не все. Блоки так важны для нас, что лучше прояснить все с самого начала.

Прежде всего, блоки из модели представления и <box> не эквивалентны. Многие теги XUL соответствуют модели представления в виде блоков, но сам <box> описывается ею не полностью.

Кроме того, хотя эта модель определяет одну концепцию визуального форматирования, она не определяет всю стратегию. Для стратегии форматирования необходимо устройство вывода и система, отображающая форматируемое содержимое на это устройство. Если таким устройством является компьютер, требуется модель визуального форматирования (см., например, главы 9 и 10 стандарта CSS 2, абстрагируясь от модели блоков). Для модели форматирования, используемой CSS 2, наиболее важными являются понятия блока ( block, не box ) и строкового блока (тоже block ). Первый представляет собой всего лишь прямоугольную область на экране. Если его содержимое занимает более одной строки, то каждая его строка будет строковым блоком.

Описанная в CSS 2 модель визуального форматирования относится только к HTML. В XUL она своя, отличная от этой и не очень хорошо известная. Модель, используемая в XUL, несколько напоминает расположение строк HTML-таблиц. Но и это сравнение не очень точное.

Расширенная версия CSS 2 в Mozilla - нотация, обеспечивающая правила форматирования и для элементов HTML, и для элементов XUL. Платформа реализует единый универсальный механизм визуального форматирования XUL и HTML. В принципе оба типа форматирования обслуживаются разными правилами CSS 2. На практике же для них существуют общие правила, и XUL- и HTML-форматирование можно смешивать в одном документе. Тем не менее, лучше использовать или чистый XUL, или чистый HTML.

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

Всех этих понятий достаточно, чтобы между приверженцами различных стандартов возникали споры. Чтобы разобраться, прежде всего, нужно представить себе один-единственный тег XUL, а затем - их группу. Мы рассмотрим оба варианта. А пока - краткое описание действительных отношений между описанными выше понятиями:

  • и HTML-, и XUL-элементы следуют правилам модели представления документа в виде блоков;
  • для HTML и XUL используются разные модели визуального форматирования; строковые блоки меняются в размерах в HTML и XUL по-разному;
  • некоторые HTML-теги похожи на строковые контейнеры CSS 2, а некоторые XUL-теги похожи на строковые контейнеры XUL. <box> - строковый контейнер XUL, но он также следует правилам модели представления в виде блоков;
  • у большей части HTML- и XUL-тегов есть свой блок CSS 2 ( block ), прямоугольная область, в которой находятся тег и его содержимое, но это сбивающий с толку термин. В Mozilla термин "блок" в таком значении используется только для HTML, а для XUL мы его будем применять как эквивалент контейнеру box. "Фрейм" - более глубокое понятие, относящееся и к HTML, и к XUL. Говоря об отображении тегов лучше использовать слово "фрейм", а не "блок";
  • и в XUL, и в HTML содержимое может выходить за пределы блока CSS 2 ( block ) своего тега. Это усложняет ситуацию, но лучше не вдаваться в подробности переполнения, пока все остальное не станет ясно, или вообще не задумываться об этом.

Самый простой способ увидеть разницу между XUL и HTML - поэкспериментировать. Для этого мы возьмем код из листинга 2.2 и заменим все теги box на <DIV>. Внесем соответствующие изменения в таблицу стилей. Полученный код вставим в документ XHTML 1.0 и загрузим этот файл в окно chrome. Попробуем изменить размеры окна и сравнить реакцию XUL- и HTML-окон на это действие. Она будет разной. О том, насколько она различается, речь пойдет дальше.

2.2.1. Отображение одного тега

Отображение одиночного XUL-тега подразумевает использование модели представления в виде блоков из CSS 2. Большая часть XUL-тегов, в том числе box, оформляются таким образом. На рисунке 2.2 показана эта модель, основанная на схеме из главы 8.1 описания стандарта.

Модель представления в виде блоков, CSS 2

Рис. 2.2. Модель представления в виде блоков, CSS 2

На рисунке 2.2 показан текст (слово "Что-то") как содержимое блока, но вообще его содержимым может быть буквально что угодно: текст, изображение, кнопка, полоса прокрутки или флажок. Глава 8, "Модель представления документа в виде блоков", и глава 14, "Цвета и фон", - единственные главы стандарта CSS 2, которые полностью соответствуют XUL.

Стандартные правила вычисления размеров также можно применять к XUL-элементам. Поддерживаются свойства:

minwidth width maxwidth minheight height maxheight

Если тег одиночный, то эти правила действуют так же, как и для HTML, но внешний по отношению к рассматриваемому тег может расширить или сузить область, занимаемую элементом, немного не так, как это делается в HTML. То есть вычисления размеров, предложенные в CSS 2, могут быть недостоверными. Свойства top и left работают только в отдельных случаях; свойства bottom и right не применяются вообще. Понимание причин этого неизбежно приводит к вопросу позиционирования. Свойства top и left также обсуждаются в разделе "Стеки и колоды".

Согласно CSS 2, тег-блок можно позиционировать - помещать в определенное место. Позиционирование XUL-тегов гораздо проще, чем позиционирование HTML-тегов, но при этом используются те же самые свойства стилей. В CSS 2 позиционирование выполняется с помощью четырех свойств: display, position, float и visibility.

  • display: в CSS 2 это свойство может принимать множество значений. Но в XUL из них поддерживаются только none и inline. При этом использование none корректно, но лучше применять XUL-атрибут hidden, хотя результат будет один и тот же. Свойство display со значением none применимо ко всем XUL-тегам, тогда как inline используется только для того, чтобы сообщить текущему тегу, что он находится внутри некоторого <box>. В XUL также есть множество собственных значений для свойства display, примерно по одному на каждый элемент, и их назначение часто настолько непонятно, что они просто бесполезны. Одно из этих значений, -moz-box, например, описывается чуть ниже.
  • position: в XUL не поддерживается абсолютное и фиксированное позиционирование. Их следует избегать, так как они могут вызвать аварийное завершение работы Mozilla. Предусмотрена поддержка относительного позиционирования, но только если тег, к которому применяется данное правило стиля - непосредственный потомок тега <stack> или <bulletinboard>.
  • float: в XUL не поддерживается вообще.
  • visibility: со значением hidden это свойство делает элемент невидимым. Хотя это и работающее решение, рекомендуется использовать XUL-атрибут hidden. В XUL нет таблиц, но если присвоить этому свойству значение collapse, эффект будет аналогичный: границы "сожмутся", и элемент не будет виден. Опять же, вместо этого свойства рекомендуется использовать атрибут collapsed, не отличающийся по эффекту от vsibility:collapse. Оба метода можно использовать для всех тегов XUL, кроме <menuitem>, которому доступен только атрибут hidden.

В XUL самым общим из правил стилей является display: -moz-box, особый тип отображения, использующийся в Mozilla. Это значит, что все существующие XUL-теги и теги, определенные пользователем данного документа, будут вести себя как <box>, если для них не указаны собственные стили. Вот почему блоки в XUL так важны. Значение -moz-box делает поведение XUL-тегов непохожим на поведение HTML-тегов.

В chrome есть стандартный архив под названием toolkit.jar. В нем содержится файл xul.css, в котором определены основные стили для всех тегов XUL. Эти стили применяются к XUL-документу прежде всех прочих стилей, в том числе глобальных и стилей отдельных тем. Именно в этой таблице стилей задано значение -moz-box.

2.2.2. Отображение группы тегов

Чтобы отобразить в XUL группу тегов, следует поместить их внутрь <box>. Есть и другие способы, но этот - простейший. Проблема заключается в том, что <box> ведет себя не так, как может вести себя "настоящий" контейнер, например, коробка. На рисунке 2.3 показано, какими способами можно визуально организовать одни элементы внутри других.

Разные варианты хранения одних объектов внутри других

Рис. 2.3. Разные варианты хранения одних объектов внутри других

Очевидно, что любая коробка двумерная, а полка нет. <box> больше похож на полку. На полке может размещаться только один ряд элементов. Если значение атрибута orient - "vertical", <box> больше похож на стеллаж с несколькими полками. В стеллаже, имитируемом элементом <box>, на одной полке может храниться только один объект, как, например, в подставке для компакт-дисков.

Многие HTML-теги тоже похожи на полки, но это сходство обманчиво, так как большая их часть поддерживает перенос, так что если ряд объектов слишком длинен, он разбивается на два и более. В XUL такого обычно не бывает. В XUL при недостатке места слишком длинная строка, например, будет просто усекаться. Если открыть какую-нибудь стандартную программу Microsoft Windows, например, Paint, и начать сжимать окно, мы увидим, что элементы из строки меню переорганизуются в две строки. Если попытаться сжать окно Mozilla, часть строки меню просто исчезнет, а не переместится ниже. Это происходит потому, что <box> не поддерживает перенос строки для своего содержимого, равно как и другие аналогичные теги.

Из этого правила есть два исключения: теги <description> и <label> поддерживают перенос строк по необходимости. Содержимое тега <description> отображается примерно так же, как содержимое большинства HTML-тегов.

Горизонтально ориентированный <box> и его содержимое аналогичны строковым блокам HTML. Основное различие между ними заключается в подсчете размеров. И в HTML, и в XUL строковый блок должен быть достаточно большим, чтобы вместить все содержимое, но возможны исключения. В HTML расчет свободного места, необходимого для размещения содержимого тега, производится до тех пор, пока все объекты не будут размещены. Если размер окна уменьшится, содержимое тега может быть разбито на две строки вместо одной. В XUL же производится расчет необходимого места и выделяется ровно такое количество площади, какое было рассчитано. Содержимое должно разместиться внутри выделенной области. В XUL перенос строк обычно не поддерживается, так что если размер окна уменьшится, <box> попытается сжать свое содержимое так, чтобы оно уместилось в оставшуюся площадь. Если достигнуты минимальные размеры содержимого, ничего не остается, кроме как выйти за границы выделенной области и отсечь эти "выступающие" части. Такое поведение диктуется моделью визуального форматирования.

Вертикально ориентированный <box> аналогичен стопке строковых блоков CSS 2, размещенных один на другом. К ним применяются те же правила, что и к горизонтальным контейнерам <box>, но каждый строковый блок может содержать только одного непосредственного потомка.

Дмитрий Гуменюк
Дмитрий Гуменюк
Россия, Звенигород
Konstantin Grishko
Konstantin Grishko
Россия, Москва, Московский финансово-промышленный университет "Синергия", Москва