Сегодня мы поговорим о наследовании шаблонов. С тех пор как был создан Twig, очень многие интересуются – как делать динамические и/или условные шаблоны.
До версии Twig 0.9.6 включительно, тэг extends мог использоваться используется только со статическим именем шаблона.
{% extends "layout.twig" %}
...
Но что если вы хотите изменять имя макета? Скажем в зависимости от того является запрос AJAX или нет? Это стало возможным в Twig 0.9.7.
Во-первых, можно хранить название макета в переменной и передавать ее в шаблон.
{% extends layout %}
Здесь layout – это строковая переменная, которая содержит название шаблона и ее значение задается в контроллере, в зависимости от заголовка запроса.
Но есть и другой способ. Если вы хотите принять решение о подключаемом макете непосредственно в самом шаблоне, можно сделать следующее:
{% extends is_ajax ? 'layout_ajax.twig' : 'layout.twig' %}
Фактически, именем шаблона может быть любое валидное выражение (как это уже сделано с тэгом include); итак, теперь разрешено такое использование тэга extends:
{% extends 'layout' ~ extension %}
Вместо того, чтобы передавать шаблон как строку, вы можете передать непосредственно сам шаблон Twig_Template:
// {% extends layout %}
$layout = $twig->loadTemplate('some_layout_template.twig');
$twig->display('template.twig', array('layout' => $layout));
Заметьте, что аналогичная возможность добавлена и в тэг include:
// {% include template %}
// {% include template %}
$template = $twig->loadTemplate('some_template.twig');
$twig->display('template.twig', array('template' => $template));
Поддержка динамического наследования шаблонов была не простой задачей, так как Twig основывался на наследование классов в PHP. И, конечно, невозможно динамически менять родительский класс в PHP:
$bar = 'SomeBaseClass';
class Foo extends $bar
{
// ...
}
Итак, Twig не использует больше PHP наследование, а просто имитирует его. Тесты производительности показывают, что скорость работы понижается незначительно. Уверен, что этот дает много возможностей и повышает гибкость приложения.
Если вам интересны подробности в коде – взгляните на лог изменений.