自学Django点滴记录(二)
2013-08-04
模板系统
模板通常用于产生HTML,同时Django的模板也能产生任何基于文本格式的文档。不允许在模板中执行python的语句。
1、两个大括号 {{ val }} val称为变量
2、大括号和百分号 {% tag %} tag称为模板标签 (tag: 仅通知模板系统完成某些工作的标签。)
3、filter过滤器
下面是个例子详细说明:
from django.template import Template, Context raw_template = """<p>Dear {{ person_name }},</p> <p>Thanks for placing an order from {{ company }}. It's scheduled to ship on {{ ship_date|date:"F j, Y" }}.</p> {% if ordered_warranty %} <p>Your warranty information will be included in the packaging.</p> {% else %} <p>You didn't order a warranty, so you're on your own when the products inevitably stop working.</p> {% endif %} <p>Sincerely,<br />{{ company }}</p>""" t = Template(raw_template) import datetime c = Context({'person_name': 'John Smith', 'company': 'Outdoor Equipment', 'ship_date': datetime.date(2009, 4, 2), 'ordered_warranty': False}) t.render(c)
让我们逐步来分析下这段代码:
首先我们导入类Template 和Context ,它们都在模块django.template 里。
我们把模板原始文本保存到变量raw_template 。注意到我们使用了三个引号来标识这些文本,因为这样可以包含多行。
接下来,我们创建了一个模板对象t ,把raw_template 作为Template 类构造函数的参数。
我们从Python的标准库导入datetime 模块,以后我们将会使用它。
然后,我们创建一个Context 对象c 。 Context 构造的参数是 Python 字典数据类型。
在这里,我们指定参数person_name 的值是 'John Smith' , 参数company 的值为 ‘Outdoor Equipment’ ,等等。
最后,我们在模板对象上调用render() 方法,传递 context参数给它。
这是返回渲染后的模板的方法,它会替换模板变量为真实的值和执行块标签。
注意,warranty paragraph显示是因为ordered_warranty 的值为True .
注意时间的显示,April 2, 2009 , 它是按 'F j, Y' 格式显示的。
如果你是 Python 初学者,你可能在想为什么输出里有回车换行的字符 '\n' 而不是显示回车换行?
因为这是Python交互解释器的缘故:
调用t.render(c) 返回字符串,解释器缺省显示这些字符串的真实内容呈 现 ,而不是打印这个变量的值。
要显示换行而不是 '\n' ,使用print 语句:print t.render(c) 。
这就是使用Django模板系统的基本规则: 写模板,创建 Template 对象,创建 Context , 调用 render() 方法。
注意:可以使用同一个模板源渲染多个Context,创建一次模板后多次调用render()方法渲染。
深度变量的查找
模板中遍历复杂数据结构的关键是句点符号( . )
(1) 通过句点( . )访问对象的属性。 如访问对象的变量、dictName.key得到该Value 等。
(2) 通过句点( . )访问对象的方法。 如var='hello' val.upper
注意:只能调用不需要参数的方法,且调用时没有圆括号结尾。
(3) 通过句点访问列表索引。索引从0开始,不允许使用负索引。
基本的模板标签
1、{% if ... %} ... {% endif %}
2、{% if ... %} ... {% else %} ... {% endif %}
3、{% if ... and(or、not) %} ... {% endif %}
注意:{% if %}不允许在同一个标签中同时使用and、or。模板系统不支持用圆括号来组合比较操作。
如果确实需要用圆括号,可考虑将它移到模板之外处理,然后以模板变量的形式传入结果。
4、{% for ... in ... %} ... {% endfor %}
5、{% for ... in ... reversed %} ... {% endfor %}
6、{% for ... in ... %} ... {% empty %} ... {% endfor %}
{% empty %}分支可以定义当列表为空时的输出内容。
注意:Django不支持退出循环、不支持continue语句。
7、每个{% for %}循环中有一个称为 forloop 的模板变量。注意:forloop仅仅能在循环中使用。
forloop.counter 表示当前循环的执行次数的整数计数器。第一次循环时,从1开始。
forloop.counter0 类似于forloop.counter 区别是从0开始计数。
forloop.revcounter 表示循环中剩余项的一个整形变量。最后一次循环执行中,变量被置1。
forloop.revcounter0 类似forloop.revcounter 区别以0 作为结束索引。
forloop.first/last 布尔值。第一次/最后一次执行时为True。
forloop.parentloop 指向当前循环的上一级循环的forloop对象的引用。
8、{% ifequal ... ... %} ... {% endifequal %}
9、{% ifequal ... ... %} ... {% else %} ... {% endifequal %}
注意:{% ifequal %}的参数只能是模板变量、字符串、整数、小数,不支持字典、列表、bool等类型。
其中字符串是可以硬编码的,即用单引号、双引号括起来。
注释
1、单行注释 {# ... #}
2、跨行注释 {% comment %} ... {% endcomment %}
过滤器
1、模板过滤器是在变量被显示前修改它的值。使用管道字符( | )
2、过滤管道可以被套接。即一个过滤器管道的输出又可以作为下一个管道的输入。
3、几个重要的过滤器
addslashes:添加反斜杠到任何反斜杠、单引号、双引号前面。
date:按指定的格式字符串参数格式化date、datatime对象。
length:返回变量的长度。
模板加载
1、from django.template.loader import get_template
get_template(模板名称) :在文件系统中找出模板的位置,打开文件并返回一个编译好的Template对象。
它会自动连接已经设置的TEMPLATE_DIRS目录和传入的模板名称。如果未找到,将引发TemplateDoesNotExist异常。
2、from django.shortcuts import render_to_response
render_to_response(模板名称,**kwargs):一次性载入某个模板文件,渲染它,然后将此作为 HttpResponse返回。
它完成了模板加载、上下文创建、模板解析、HttpResponse创建。 返回HttpResponse对象。
第一个参数必须是要使用的模板名称。
如果要给定第二个参数,那必须是为该模板创建Context时所使用的字典。如果不提供,则使用一个空字典。
3、locals():它返回的字典对所有局部变量的名称与值进行映射。
它囊括了函数执行到该时间点时所定义的一切变量。可鞥比你想让模板访问的要多。
4、get_template、render_to_response中的模板名称前可以加上目录名和一条斜杠(/)一起传入。
如: t = get_template('a/b/c/../d/abc.html')
5、{% include ... %}:当在多个模板中出现相同的代码时,用它来减少重复。
ex. {% include 'a/b.html' %}— 包含了a/b.html模板的内容
{% include teplate_name %}— 包含了变量teplate_name的值为名称的模板内容
如果指定的模板没有找到,DEBUG为True, 抛TemplateDoesNotExist异常。
DEBUG为False, 不引发错误,在标签位置不显示任何东西。
模板继承
它是先构造一个基础框架模板,接着在其子模板中对它所包含站点公共部分和定义块进行重载。
{% block ... %} ... {% endblock %}:它告诉模板引擎,子模板可以重载这些部分。
{% extends ... %}::使用时必须保证其为模板中的第一个模板标记。否则模板继承将不起作用。
多数情况下它的参数是字符串,但如果直到运行时方能确定父模板名,这个参数也可以是个变量。
这使得我们能够实现一些很酷的动态功能。
例子:
<!DOCTYPE HTML PUBLIC "‐//W3C//DTD HTML 4.01//EN"> <html lang="en"> <head> <title>{% block title %}{% endblock %}</title> </head> <body> <h1>My helpful timestamp site</h1> {% block content %}{% endblock %} {% block footer %} <hr> <p>Thanks for visiting my site.</p> {% endblock %} </body> </html>
浙公网安备 33010602011771号