Вложенные шаблоны django
это кажется довольно простой вещью, но, хотя я использую Django около года, я еще никогда не сталкивался с этим сценарием.
во многих шаблонах / веб-фреймворках наследование шаблонов работает немного иначе, в том, что обычно оно ведет себя больше как обертки, поэтому, если у вас есть childtemplate.HTML-код, parenttemplate.html и grandparenttemplate.html, то, наконец, рендеринг обычно выглядит примерно так:
grandparent header
parent header
child header
child content
parent content
parent footer
grandparent content
grandparent footer
это не совсем так работает в Django, но мне интересно как это реализовать.
в частности, у меня есть шаблон "ребенок", скажем так, это foo.html
. foo.html
дополнительно получает переменную parent_template
или по умолчанию " base.HTML-код"
{% extends parent_template|default:"base.html" %}
{% block content %}
I am a foo and my title is {{ foo.title }}
{% endblock content %}
Итак, здесь я сталкиваюсь с проблемой. Если parent_template
является шаблоном, этот шаблон должен обернуть содержимое foo.html
а затем поместите результат в base.html
:
{% extends "base.html" %}
{% something_magical_here %}
<div>parent header</div>
# content of foo.html
<div>parent footer</div>
{% end_something_magical_here %}
а потом в base.html
:
<html>
... snip ...
<div id="content">
{% something_else_magical %}
# content of parent_template rendering, or just foo.html if no parent_template given
{% end_something_else_magical %}
что должен render as
<html>
... snip ...
<div id="content">
<div>parent header</div>
I am a foo and my title is Bar
<div>parent footer</div>
если parent_template установлен и
<html>
... snip ...
<div id="content">
I am a foo and my title is Bar
если это не так.
я надеюсь, что моя проблема ясна: мне нужно (необязательно) обернуть шаблон в родительский шаблон, а затем отправить результаты этого в base.html
шаблон.
обычно что-то вроде этого может работать:
#foo.html
{% extends "parent.html" %}
{% block child_content %}
I am a foo and my title is {{ foo.title }}
{% endblock child_content %}
#parent.html
{% extends "base.html" %}
{% block content %}
parent header
{% block child_content %}{% endblock child_content %}
parent content
parent footer
#base.html
base header
{% block content %}{% endblock content %}
base content
base footer
однако, поскольку parent_template может быть пустым, то иногда базовым.html будет получать только child_content
блок, а не content
блок.
кроме того, я хотел бы иметь возможность сделать это без необходимости создавать кучу подблоков (что, если я решу, что foo
приложение должно иметь свой собственный /foo/base.html
что то называет /base.html
)?
какие идеи?
1 ответов
тег шаблона extends может принимать аргумент переменной.
так:
base.html
{% block content %}
<p>BASE</p>
{% endblock %}
parent.html
{% extends "base.html" %}
{% block content %}
{{ block.super }}
<p>PARENT</p>
{% endblock %}
foo.html
{% extends ext_templ %}
{% block content %}
{{ block.super }}
<p>FOO</p>
{% endblock %}
используя основание:
return render_to_response('foo.html', {'ext_templ':'base.html'})
дает вам:
<p>BASE</p>
<p>FOO</p>
использование parent:
return render_to_response('foo.html', {'ext_templ':'parent.html'})
дает вам:
<p>BASE</p>
<p>PARENT</p>
<p>FOO</p>
edit:
один из способов обойти эту проблему, чтобы получить вложенные блоки:
base.html
{% block content %}
{% block top %}
<p>BASE START</p>
{% endblock %}
{% block bot %}
<p>BASE END</p>
{% endblock %}
{% endblock %}
parent.html
{% extends "base.html" %}
{% block top %}
{{ block.super }}
<p>PARENT</p>
{% endblock %}
{% block bot %}
<p>PARENT</p>
{{ block.super }}
{% endblock %}
foo.html
{% extends ext_templ %}
{% block top %}
{{ block.super }}
<p>FOO</p>
{% endblock %}
{% block bot %}
<p>FOO END</p>
{{ block.super }}
{% endblock %}
другой метод, который я могу придумать, - это обернуть блоки {% if ext_templ == 'parent.html' %}
тег, но это, кажется, не очень сухой. Мне любопытно увидеть, как другие народы реагируют на вложенные блоки.