简介
Flask使用Jinja2作为其模板引擎,Jinja2是一个现代的、设计友好的模板引擎,用于在Python中渲染模板。模板渲染是将模板文件中的变量和表达式替换为实际值的过程,从而生成最终的HTML页面。
模板基本结构
一个基本的Flask模板通常包含以下部分:
-
• 变量:用于在模板中显示数据。
-
• 控制结构:如
if
、for
等,用于在模板中实现逻辑。 -
• 注释:用于在模板中添加说明,不会在最终生成的HTML中显示。
-
• 继承:允许创建一个基础模板,其他模板可以从中继承并扩展。
-
• 包含:允许在一个模板中包含另一个模板的内容。
导入HTML模板渲染
在Flask视图函数中,你需要从flask
模块导入render_template
函数来渲染模板。
# 返回HTML模板文,返回index.html模板
@routes.route('/')
def index():
return render_template('index.html')
变量
在Jinja2中,变量用双大括号{{ }}
表示。当模板渲染时,这些大括号内的表达式会被替换为变量的值。
@routes.route('/user')
def user_profile():
username = '艾则麦提'
return render_template('user_profile.html', # 模板文件名
username=username # 变量名
)
@routes.route('/user/<username>')
def user_profile1(username):
return render_template('user_profile.html', username=username)
user_profile.html
文件代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<h1>用户信息</h1>
<p>用户名:{{ username }}</p>
</body>
</html>
控制循环语句
if
条件语句
if
语句用于条件判断,根据表达式的真假来决定是否执行某些代码。在Jinja中,if
语句的基本用法如下:
{% if [条件] %}
... # 条件为真时执行的代码
{% elif [条件] %}
... # 上一个条件为假,当前条件为真时执行的代码
{% else %}
... # 所有条件都为假时执行的代码
{% endif %}
# if语句
@routes.route('/ifelse/')
def ifelse():
age = 18
return render_template('ifelse.html', age=age)
@routes.route('/ifelse/<int:age>')
def ifelse1(age):
return render_template('ifelse.html', age=age)
ifelse.html
<div>
<p>年龄:{{ age }}</p>
{% if age > 18 %}
<p>成年人</p>
{% elif age == 18 %}
<p>刚满18岁</p>
{% else %}
<p>未成年人</p>
{% endif %}
</div>
for
循环语句
for
循环用于遍历序列(如列表、元组、字典等),并对其中的每个元素执行相同的操作。在Jinja中,for
循环的基本用法如下:
{% for element in sequence %}
... # 对序列中的每个元素执行的代码
{% else %}
... # 序列为空时执行的代码
{% endfor %}
字典:for key,value in 字典.items()
@routes.route('/forlist/')
def forList():
# 列表
names = ['Python', 'Java', 'JavaScript', 'C++', 'Flask', 'Vue3']
# 字典
user = {
'name': '艾则麦提',
'age': 18,
'gender': '男'
}
return render_template('for_item.html', names=names, user=user)
for_item.html
文件代码内容:
<h2>遍历列表</h2>
<ul>
{% for item in names %}
<li>{{ item }}</li>
{% else %}
<li>列表为空</li>
{% endfor %}
</ul>
<h2>遍历字典</h2>
<ul>
{% for key, value in user.items() %}
<li>{{ key }}: {{ value }}</li>
{% endfor %}
</ul>
注释
在Jinja2模板中,注释是用于在模板文件中添加说明或注释代码的部分,这些注释不会在最终生成的HTML中显示。注释对于理解模板的结构和目的非常有用,尤其是对于团队协作或在一段时间后返回自己的代码。在Jinja2中,您可以使用以下方式添加注释:
-
1. 单行注释:单行注释以
{#
开始,以#}
结束。它们可以单独一行,也可以放在代码行的末尾。
{# 这是一个单行注释 #}
<p>这是一个段落。</p> {# 另一个单行注释 #}
-
1. 多行注释:多行注释以
{#-
开始,以-#}
结束。它们可以跨越多行,但不能被嵌套。
{#-
这是一个多行注释,
它可以跨越多行。
-#}
过滤器
定义:在Jinja2模板中,过滤器用于修改或转换变量。它们类似于Python中的函数,可以接受一个或多个参数,并返回一个处理后的值。
基本语法:{{ variable | filter_name }}
或 {{ variable | filter_name(arg1, arg2, ...) }}
作用:过滤器可以用于格式化输出、转换数据类型、执行计算等。
常用过滤器
-
1.
upper
:将文本转换为大写。 -
• 示例:
{{ "hello" | upper }}
输出HELLO
-
2.
lower
:将文本转换为小写。 -
• 示例:
{{ "HELLO" | lower }}
输出hello
-
3.
capitalize
:将文本的首字母转换为大写。 -
• 示例:
{{ "hello" | capitalize }}
输出Hello
-
4.
title
:将文本的每个单词的首字母转换为大写。 -
• 示例:
{{ "hello world" | title }}
输出Hello World
-
5.
default
:如果变量为undefined
或null
,则使用默认值。 -
• 示例:
{{ variable | default('默认值') }}
-
6.
join
:将序列中的元素连接为一个字符串。 -
• 示例:
{{ [1, 2, 3] | join(',') }}
输出1,2,3
-
7.
safe
:标记一个字符串为安全的,可以包含HTML代码,不会被自动转义。 -
• 示例:
{{ "<p>HTML</p>" | safe }}
-
8.
escape
:转义字符串中的HTML特殊字符。 -
• 示例:
{{ "<p>HTML</p>" | escape }}
-
9.
length
:返回序列或集合的长度。 -
• 示例:
{{ ["a", "b", "c"] | length }}
输出3
继承
基础模板 (base.html
)
-
• 位置:
templates/base.html
-
• 作用: 定义页面的基本HTML结构,包括
<head>
、<body>
的初始布局。 -
• 关键点:
-
• 使用块(Blocks)定义可被子模板替换或扩展的部分,如
{% block title %}{% endblock %}
,{% block head %}{% endblock %}
,{% block content %}{% endblock %}
,{% block foot %}{% endblock %}
。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>{% block title %}首页{% endblock %}</title>
<link rel="stylesheet" href="{{ url_for('static', filename='css/base.css') }}">
</head>
<body>
<div class="head">
{% block head %}{% endblock %}
</div>
<div class="content">
{% block content %}{% endblock %}
</div>
<div class="foot">
{% block foot %}{% endblock %}
</div>
</body>
</html>
子模板继承 (header.html
, contents.html
)
-
• 位置: 分别为
templates/header.html
和templates/contents.html
-
• 作用: 扩展
base.html
,填充具体的内容到定义的块中。 -
• 关键点:
-
• 使用
{% extends '父模板路径' %}
来继承基础模板。 -
• 在相应的块中添加内容,例如在
header.html
中定义头部内容,在contents.html
中定义中部内容。
<!-- header.html -->
{% extends 'base.html' %}
{% block head %}
<div><h3>这是子模板定义的头部内容</h3></div>
{% endblock %}
<!-- contents.html -->
{% extends 'base.html' %}
{% block content %}
<div><h3>这是子模板定义的中部内容</h3></div>
{% include 'contents_include.html' %} {# 引入模板嵌套 #}
<div>
<h3>宏定义</h3>
{% from 'contents.html' import render_comment %}
{{ render_comment('张三', 18) }}
</div>
{% endblock %}
宏定义 (render_comment
)
-
• 位置:
templates/contents.html
-
• 作用: 创建可复用的代码片段,这里是一个展示用户信息的宏。
-
• 关键点:
-
• 使用
{% macro 名称(参数列表) %}
开始定义,{% endmacro %}
结束。 -
• 在任何需要使用该宏的地方,通过
{{ 宏名(参数值) }}
调用。 -
• 其他模版中也可以调用该宏。
{% from '文件名' import [宏定义名称] %}
{# 宏定义 : 类似于Python中的函数 #}
{% macro render_comment(name,age) %}
<p>姓名:{{ name }}</p>
<p>年龄:{{ age }}</p>
{% endmacro %}
其他页面调用宏
{% from 'contents.html' import render_comment %}
{{ render_comment("艾则麦提",28) }}
模板嵌套 (contents_include.html
)
-
• 位置:
templates/contents_include.html
-
• 作用: 提供一段可被其他模板插入的内容。
-
• 关键点:
-
• 使用
{% include '模板路径' %}
来插入其他模板的内容。
<!-- contents_include.html -->
<h4><p>include 模板继承</p></h4>
<!-- contents.html -->
{% include 'contents_include.html' %}
最终页面展示 (foots.html
)
-
• 位置:
templates/foots.html
-
• 作用: 综合展示继承、块内容填充、宏使用及模板嵌套。
-
• 关键点:
-
• 继承自
contents.html
,并扩展foot
块。 -
• 引入并使用了宏
render_comment
,同时从外部导入宏定义。
<!-- foots.html -->
{# 继承父模板 #}
{% extends 'contents.html' %}
{% block foot %}
<div>
<p>这是子模板定义的底部内容</p>
</div>
<div>
{# 导入宏定义 #}
{% from 'contents.html' import render_comment %}
{{ render_comment("艾则麦提",28) }}
</div>
{% endblock %}
Flask 路由设置
确保 Flask 应用能够正确渲染最终页面。
@app.route('/base/')
def base():
return render_template('foots.html')
资料与代码
git clone https://gitee.com/ezemeti/FlaskLearn.git
原文始发于微信公众号(索隆程序员):Flask入门 — 模板渲染
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/289666.html