template模板介绍

模板的组成

HTML代码 + 逻辑控制代码

一个完整的渲染过程

Template和Context对象

首先进入该django项目的环境(不一定要在中断测试,也可以在python文件中测试)

python manage.py shell

创建相应的Template对象和Context上下文对象

from django.template import Context, Template

t = Template('<h1>hello {{ name }}</h1>')   # 实例化一个模板
c = Context({'name': 'Eric'})     # 实例化一个模板对象
t.render(c)    # 将上下文对象渲染到模板中

得到的结果是将上下文对象中的变量传入到模板中

>>> 'hello Eric'

上面的过程对比视图函数中的render()方法

render(request, "index.html", {'name': 'Eric'})

  • index.html:模板,相当于Template('index.html')
  • {'name': 'Eric'}:上下文对象,相当于 Context({'name': 'Eric'})

其实视图函数中也是向上面那样渲染模板的,只不过render()方法将一切已经封装好了,我们在使用时只需要将要渲染的模板跟上下文传进去就可以了

万能的句点符

句点符可以帮助变量深度查找,如果从视图函数传来的是一个对象或者列表,在模板中可没有[],所以只能通过句点号(.) 去查找

在视图函数中:

class Animal:
    def __init__(name, sex):
        self.name = name
        self.sex = sex


def index(request):
    l = ['timo', 'seric', 'scartlett', 'taylor']
    a = Animal('Eric', 'male')
    return render(request, 'index.html', locals())

在index.html中:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>index</title>
</head>
<body>
    <h1>hello</h1>
    {{ l.1 }}   # 通过索引点
    {{ l.2 }}
    
    {{ a.name }}  # 对象直接点属性名字
    {{ a.sex }}
</body>
</html>

变量的过滤器(filter)

语法格式

{{ 要处理的变量|过滤器:传给过滤器的参数 }}
{{ obj|filter:param }}

有哪些过滤器

过滤器 说明
add 给变量加上相应的值
addslashes 给变量中的引号前加上斜线
capfirst 首字母大写
cut 从字符串中移除指定的字符
date 格式化日期字符串
default 如果值是False(这里的False是指进行if判断时的False,比如空的列表[],空的字符串''等等,并不是单单值布尔值False),就替换成设置的默认值,否则就是用本来的值
default_if_none 如果值是None,就替换成设置的默认值,否则就使用本来的值
safe 将字符串变成有意义的html代码
upper 将字符串中的所有字符变为大写
lower 将字符串中的所有字符变为小写
filesizeformat 以1024为基数,计算最大值,保留1位小数
first 只取字符串的第一个字母
length 计算字符串的长度
slice 截取字符串指定的前num位
urlencode 对url进行编码

 

过滤器的使用

add

# num = 11
{{ num|add:10 }}

# 结果
>>> 21

capfirst

# value = "aBDDGsds"
{{ value|capfirst }}

>>> ABDDGsds

cut

# value = 'he  llo wo r ld'
{{ value|cut:' ' }}     {# 切掉字符串中所有的空格 #}

>>> helloworld

date

# import datetime
# value = datetime.datetime.now()
{{ value|date:'Y-m-d' }}

>>> 2018-07-03

default

# value= []
{{ value|default:'空的' }}

>>> 空的

default_if_none

# value = None
{{ value|default_if_none:"结果为None" }}

>>> 结果为None

safe

# value = "<a href="sssa">click</a>"
{{ value }}   # 像这样直接渲染是不会被渲染成a标签的,仍旧是原来的字符串<a href="sssa">click</a>
{{ value|safe }}  # 这样就会在页面呈现一个a标签

>>> click

filesizeformat

# value = 4656461645646
{{ value|filesizeformat }}

>>> 4.2 TB

slice

# value = "fdfdsfsdfdsfds"
{{ value|slice:"5" }}

>>> fdfds

标签(tag)的使用(使用{%%}的组合)

语法格式

{% tags %}}

标签介绍

{% if %}标签

# age = 20
# name = 'aaa'
{% if age > 20 %}    # 如果age大于20才显示名称
    <h1>{{ name }}</h1>
{% endif %}

{% elif %}、{% else %}标签

{% if age>20 %}
    <h1>aaa</h1>
{% elif age>30 %}
    <h1>bbb</h1>
{% else %}
    <h1>ccc</h1>
{% endif %}

{% for %}标签

# num = [1, 2, 3, 64, 5, 4, 6]
{% for digtal in num %}
    {{ digtal }}
{% endfor %}

forloop计数器

{{ forloop.counter }}

用在的for循环中,计算当前的循环次数,从几开始由counter后面的数字决定

{% for digtal in num %}
    {{ forloop.counter1 }}    # 从1开始计数
{% endfor %}
(( forloop.revcounter ))

倒序,用法跟counter一致,只是计数的顺序从大变到小

{{ forloop.first }}

当循环是第一次时为True,后面的循环都为False

{% empty %}

判断循环中的当前项是否为空

{% for digtal in num %}
    {{ forloop.counter0 }}
{% empty %}  # 判断digtal是否为空
    <h1>本列为空</h1>
{% endfor %}

{% csrf_token %}标签

在使用post方式提交表单时django会有一个中间件验证,这时必须在form标签之中加上{% csrf_token %}进行验证,该标签会在前端渲染一个type为hidden的input标签,名字是固定的,

值相当于一个钥匙,在第一次请求页面的时候就已经发给浏览器了,只有带着这个钥匙去请求才会被通过

<form action="" method="post">
    <input type="text" name="user">
    {% csrf_token %}  # 必须加上该验证钥匙
    <input type="submit">
</form>

{% with %}标签

用简单的变量名替换复杂的变量名

{% with total=sdsdsdsdsdsdsdsdsdsfdsfsdfsd %}  # 用变量名total代替变量名sdsdsdsdsdsdsdsdsdsfdsfsdfsd
    {{ total }}
{% endwith %}

{% url %}

应用别名代替url

urls.py

urlpatterns = [
    url(r'index/', views.index, name="index"),
]

index.html

<form action="{% url 'index' %}" method="post">
    <input type="text" name="user">
    <input type="text" name="pwd">
    {% csrf_token %}
    <input type="submit">
</form>

{% verbatim %}标签

禁止render(),有的时候希望打印{{ hello }},可是由于模板的特性在双大括号之间的内容会被当成变量渲染,这样就达不成想要的效果,这时可以使用{% verbatim %}禁止render()方法去渲染

其它标签

关于{% load %}、{% extends %}、{% include %}会在下面介绍

自定义filter和simple_tag

a、在app中创建templatetags(名字是固定的!!!)模块(即在应用中创建一个python包,必须)

b、在上一步创建的包中添加一个.py文件,比如my_tags.py

my_tags.py

from django import template

register = template.Library()     # register的名字是固定的,不能够改变


# 定义过滤器
@register.filter
def filter_multy(x, y):
    return x * y


# 定义标签
@register.simple_tag
def simple_tag_multy(x, y, z):
    return x * y * z

c、在使用自定义simple_tag或filter的html文件中导入之前创建的my_tags.py

{% load my_tags %}

d、使用simple_tag和filter

index.html

{% load my_tags %}    # 首行加载
	
<!-- 使用过滤器 -->
{num|filter_multy:3}   # 使用自定义的filter_multy标签,num是从后端传过来的变量


<!-- 使用自定义标签 -->
{% somple_tag_multy 1 2 6 %}

e、在settings中的INSTALLED_APPS配置当前app,不然django无法找到自定义的simple_tag.

filter与simple_tag的优缺点

filter

  • 缺点:只能传一个参数,在需要多个参数的场景中不是很实用,不过可以把多个参数组合成一个列表当做一个参数传进去。
  • 优点:filter可以用在if等控制语句当中

simple_tag

  • 缺点:simple_tag不能用在if等控制语句当中
  • 优点:可以传多个参数,对参数没有限制

as使用:有的时候需要将simple_tag执行的结果保存,这个时候就可以使用as,通过 {% simple_tag_func as variable_name %} 

继承标签extends和添加标签include

extends标签

建立一个模板base.html

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>index</title>
	<link rel="stylesheet" href="/static/index.css">
    </head>
    <body>
        <h1>hello</h1>
	 <!-- 在这里放一个盒子,继承该页面的页面可以在这里面定制想要的内容 -->
	 {% block name %}
	      <h1>WELCOME TO LOGIN</h1>
	  {% endblock %}
    </body>
</html>

在别的页面继承base.html

index.html

{% extends "base.html" %}    # 一般放在顶行
<!-- 在盒子中定义自己想要的代码,与base.html不同的地方 -->
{% block name %}
    {{ block.super }}     # 该变量可以拿到父类盒子中的内容,即<h1>WELCOME TO LOGIN</h1>
    <h1>index.html</h1>
{% endblock %}

include标签

include标签可以将一个html页面引入到另一个html页面中

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>index</title>
        <link rel="stylesheet" href="/static/index.css">
    </head>
    <body>
        <h1>hello</h1>
        <!-- 将index.html页面中的内ring引进来 -->
	 {% include "index.html" %}
    </body>
</html>

  

 

posted @ 2018-07-03 19:17  Jin同学  阅读(1493)  评论(0)    收藏  举报