Опубликован: 10.12.2007 | Доступ: свободный | Студентов: 821 / 20 | Оценка: 5.00 / 5.00 | Длительность: 58:33:00
Лекция 14:

Шаблоны

14.3.6. Тег <bindings>

Тег <bindings> - необязательная часть расширенного синтаксиса запроса. Он не имеет специальных атрибутов, и может содержать только теги <binding>. Теги <bindings> и <binding> постоянно используются в Mozilla, особенно в XBL. Между их применением в шаблонах и где угодно еще нет прямой связи. В терминах SQL, они являются реализацией инструкции "outer joins" и нулевых значений.

Тег <bindings> следовало бы называть <extra-groundings>, поскольку это вовсе не "привязка" в смысле XBL (или XPConnect или IDL или XPIDL). binding -переменная это просто добавочная переменная, которая может быть обоснована добавочным запросом. Это же значение имеет и тег <binding>.

Раздел правила <bindings> - это место, где можно поместить добавочные переменные, не ограничивая результатов <conditions> запроса. Сделать это очень просто. В секции <conditions> все переменные должны быть обоснованы, чтобы было найдено решение. Это решение передается в секцию bindings. Далее процессор запроса пытается обосновать все переменные, перечисленные в секции <bindings>. Если лишь некоторые из них удается обосновать, процессор просто присваивает остальным нулевые значения. Это значит, что решения <conditions> никак не ограничиваются переменными <bindings>. Фактически, секция <bindings> подобна RDBMS инструкции outer join - если что-то подходит, об этом сообщается, в противном случае вы получаете только то, что найдено по запросу.

Переменные в секции <bindings> должны быть расширенными переменными шаблона. Переменные из раздела <conditions> можно использовать здесь, но не наоборот. Чтобы секция <bindings> имела смысл, должна быть использована по крайней мере одна из переменных секции <conditions>.

14.3.6.1. Тег <binding>

Тег <binding> идентичен тегу <triple> по атрибутам и способу использования. Он отличается от <triple> только в правилах, применяемых для обоснования его переменных, как описано в разделе <bindings>.

14.3.7. Тег <action> и контент, порождаемый запросом с простым синтаксисом

Тег <action> используется в <rule> с расширенным синтаксисом запроса. Он дает контент, который будет генерироваться для каждого результата данного запроса. Контент правила <rule> с простым синтаксисом генерируется точно так же, как контент тега <action>. Здесь описывается система генерации.

Контент тега <action> состоит из обычных XUL тегов и расширенных переменных запроса. Система шаблонов замещает значение каждой переменной при генерации контента. Таким образом, переменные используются в теге <action>, хотя определяются и обосновываются в теге <conditions> (они определяются и обосновываются автоматически при простом синтаксисе). Система шаблонов добавляет атрибут id каждому тегу каждый раз, когда генерируется контент. Тег <action> не может включать тег <script>.

Контент тега <action> должен быть организован так, как показано в листинге 14.14

<action> // simple syntax: 
<rule> 
  <box id="A"> 
    <box id="B"> 
      <box id="C" uri="?var"> // simple syntax: uri="rdf:*" 
        <box id="D"/> 
          <box id="E"> 
            <box id="F"/> 
            </box> 
        </box> 
    </box> 
  </box> 
</action>
Листинг 14.14. Пример иерархического контента <action>.

Мы используем этот пример, чтобы объяснить, что и как здесьработает. В общем случае теги могут вкладываться на произвольную глубину внутри <action>, и может быть использован любой XUL-код. Специальный случай шаблонов, основанных на деревьях, обсуждается отдельно.

Контент тега <action> делится на тег, содержащий атрибут uri, порождающие его теги и наследующие ему теги. В листинге 14.14 С содержит uri ; A и B - теги-предки; D, E и F - дочерние теги.

Теги-предки A и B порождаются лишь однажды, независимо от того, как много решений обнаружит запрос. Если переменные запроса (расширенные для контента <action>, простые для контента <rule> ) используются в A и B, они будут иметь значения, найденные в первом решении запроса. Если A и B имеют дочерние теги, эти теги могут быть неадекватны. Рекомендуется их избегать.

Тег C - начало повторяющегося контента, поскольку он имеет атрибут uri. И С, и его контент могут генерироваться как целое ноль и более раз. Чтобы контент был сгенерирован хоть один раз, должны быть выполнены два условия. Во-первых, запрос должен обнаружить хоть одно решение. Во-вторых, значение атрибута uri тега C в этом обнаруженном решении должно быть другим. Самый простой способ удостовериться, что это именно так - установить его в значение переменной, упоминаемой как дополнение в некотором кортеже. Примером может быть часть child тега <member>. В этом случае необходимо использовать ?item:

<member container="?seq" child="?item"/>

В наиболее общем случае, атрибуту uri должно быть присвоено значение подлежащего или дополнения, разные для каждого решения, обнаруженного запросом. Атрибут id принимает данное уникальное значение для каждого тега C во время генерации контента. Тег C не должен иметь дочерних тегов, это может привести к ошибке. Рекомендуется в данном случае дочерних тегов избегать.

Если требуется построение контента с задержкой ("ленивое"), тег C должен быть одним из следующих XUL-тегов:

<menu> <menulist> <menubutton> <toolbarbutton> <button> <treeitem>

Теги D, E, и F - обычные теги, генерируемые один раз на каждое найденное решение запроса. Они могут иметь дочерние теги и обширный собственный контент. Если эти теги имеют переменные шаблона, такие переменные будут замещены найденными решениями.

14.3.7.1. Контент шаблонов, основанных на теге <tree>

Контент шаблонов, основанных на теге <tree>, может нарушать правило, согласно которому теги-родители uri-тега генерируются лишь однажды.

Если шаблон основан на теге <tree>, каждый <treeitem> в финальном дереве может иметь тег <treechildren> как свой второй дочерний тег. Этот тег может содержать любое число поддеревьев. К счастью, контент тега <action> должен представлять единственную строку дерева. Конструктор шаблона, обрабатывающий тег <tree>, достаточно разумен, чтобы скопировать этот контент в каждое поддерево. Другими словами, он достаточно разумен, чтобы определить необходимость рекурсивного запроса. Контент тега <action> нужно прописать достаточно аккуратно, чтобы такая конструкция работала. Она показана в Листинге 14.15.

<action> 
<treechildren> //simple syntax: use <rule>
  <treeitem uri="?var"> //simple syntax: use uri="rdf:*" 
    <treerow>
      ... any normal treerow content ... 
    </treerow> 
  </treeitem>
</treechildren> 
</action>
Листинг 14.15. Пример иерархического контента тега <action> для шаблона на теге <tree>.

Все теги в этой конструкции могут иметь добавочные атрибуты. Не следует использовать атрибут id для тега <treeitem>. Переменная ?var обычно соответствует переменной в дополнении тегов <member> или <triple>.

Данный синтаксис можно слегка изменить, и даже использовать такой шаблон внутри другого шаблона. Например, так, что тег <treeitem> порождается из одного источника RDF, а его дочерние теги <treechildren> - из другого. Подобные вложения следует тщательно тестировать, потому что они не используются широко и, следовательно, не являются достаточно надежными.

Шаблоны, основанные на деревьях, используют рекурсивные запросы. С каждым шагом рекурсии вглубь дерева фактов контент тега <action> перед uri-тегом удваивается. Это означает добавочную копию тега <treechildren>, см. листинг 14.15. Эта новая копия становится затем отправной точкой для всех решений, найденных новым запросом.

14.3.7.2. Тег <textnode>

И простые, и расширенные переменные могут появляться только в значениях атрибутов XML. Некоторые теги XUL порождают текстовое содержание между их открывающей и закрывающей частями. Например, тег <Description>.

Тег <textnode> предоставляет способ поместить переменную в контент, не являющийся атрибутом. Предположим, переменная ?var в некоторый момент содержит строку "red". Тогда строка

<tag>
<textnode value="big ?var truck"/>
</tag>

будет эквивалентна строке

<tag>big red truck</tag>

Тег <textnode> можно поместить в любое место внутри тега <action>. Тег <textnode> не может быть использован, если запрос задействует простой синтаксис. На данном теге мы завершим рассмотрение тегов шаблона.