2012-03-09 44 views
28

我有一些html结构可以在很多不同的地方重复使用。它与整体模板不同,所以我不能扩展它,它也可以用来包含复杂的内容,所以我不认为将它定义为模板标签是一件好事。以下是一些伪代码,描述了我的期望结果,当使用template_level2.html时,您可以通过调用其中的块来轻松地将内容放入reusable_pattern_template中。如果我确实使用了这个代码,那么您在template_level_2.html的“实际内容”中编写的内容就不会显示出来。我应该如何处理这个问题?django:在包含的模板中使用块

base.html文件

<html> 
<head></head> 
<body> 
{% block content %}{% endblock %} 
</body> 
</html> 

template_level1.html

{% extends 'base.html' %} 
{% block content %} 
    Something here... 
    {% include 'reusable_pattern_template.html' %} 
    Something else here... 
{% endblock %} 

reusable_pattern_template.html

<div> 
    <div> 
    <div> 
     {% block local_content %}{% endblock %} 
    </div> 
    </div> 
</div> 

template_level2.html

{% extends 'template_level1.html' %} 
{% block local_content %} 
    Actual content here... 
{% endblock %} 

更新: 抱歉,在template_level2.html延伸有一些拼写错误,我只是纠正它。

它可能不是很清楚,但上面的代码中更多的是描述我所希望的结果的伪代码。总之,

  • 我想在我的 模板中包括可重复使用的html模式的小块。
  • 这些图案就像是盒子,您可以将整个HTML 内容放入其中。所以上下文变量可能有点太有限 我的目的
+0

似乎永远不会调用'template_level2.html'。如果你包含了一些代码块,你不需要使用'block'语句,因为你将包括什么时候以及你想要什么 – 2012-03-09 12:13:41

+0

嗨fastreload! 'template_level2.html'是模板的最终级别,所以它不被包含/扩展到任何地方。通过调用'template_level2.html'中的'{%block%}'语句,我打算将内容放入''template_level2.html'中使用的'reusable_pattern_template.html'中。 – 2012-03-09 12:49:58

+0

问题:为什么不使用django-generic-flatblocks?这是一个很棒的应用程序,它提供了一个很棒的模式 – jpic 2012-03-09 13:33:34

回答

40

Django不处理包含文件中的块。

包含标签应被视为“呈现此子模板并包含HTML”的实现,而不是“解析此子模板并将其内容视为其父项的一部分”。这意味着包含模板之间不存在共享状态 - 每个包含都是完全独立的呈现过程。 (Django template tag documentation

+7

尽管如此,来自视图的变量仍然是共享和解析的。 – 2012-03-09 22:41:03

+0

上下文也被赋予包含的模板(这可能与上面的注释相同,但'上下文'比视图中的变量更容易识别。) – 2013-10-20 16:27:49

+7

有帮助的解释,但是_is_有一个标记或其他方法来执行OP希望?我也希望能够包含模板,并且仍然能够使用模板继承 – Ben 2014-08-08 22:04:10

3

看来,最终的模板正试图扩展其本身(如果它是在引号)

你真的不需要那么多的复杂性。它实际上非常简单。

基本模板应该保存模板的骨架,然后可以扩展它以进行自定义。对于你不想在你的每个视图包括,include他们在适当情况下,但不包含的文件中使用任何blockextendsinclude声明可重用的代码块。 Django不会解析那些,但从视图传递的context variable仍然可以使用。

0

您可以将reusable_pattern_template分割为开始和结束模板。然后在level1中你可以去include begin,block,include end。

或者,您可以将模板名称作为上下文变量传递给reusable_pattern_template,然后将其包含在reusable_pattern_template中。这将需要在您的示例中更改level1和level2之间的关系,但通常更强大。

1

我遇到了这个问题,最终导致了下面的妥协,希望别人会觉得它有用。它依靠在子模板中使用with块。

base.html文件想重用一个共同nav.html包括但定义一些区块,其中内nav.html变量可能是由子模板被重写。

<!-- base.html: --> 
<html> 
    [...] 
    <nav class="desktop"> 
    {% block desktop_nav %} 
     {% include "includes/nav.html" %} 
    {% endblock %} 
    </nav> 
    [...] 
    <nav class="mobile"> 
    {% block mobile_nav %} 
     {% include "includes/nav.html" %} 
    {% endblock %} 
    </nav> 
    [...] 

的包括模板依赖于一个名为selected变量,它base.html文件没有定义,默认为:

<!--includes/nav.html:--> 
<a href="/about/" class="{% if selected == 'about' %}selected{% endif %}">About</a> 
<a href="/people/" class="{% if selected == 'people' %}selected{% endif %}">People</a> 
<a href="/contact/" class="{% if selected == 'contact' %}selected{% endif %}">Contact</a> 

但子页面可以按如下覆盖该值:

<!--about.html:--> 
{% extends "base.html" %} 
{% block desktop_nav %}{% with selected='about' %}{{ block.super }}{% endwith %}{% endblock %} 
{% block mobile_nav %}{% with selected='about' %}{{ block.super }}{% endwith %}{% endblock %} 

所以,不完美,我仍然必须有两个独立的块,并使用这些with块两次,但它确实允许我从父模板的include块中覆盖变量。