文章目录
1、表达式
1.1、简单表达式
${...}
变量表达式
*{...}
选择变量表达式
#{...}
消息表达式
@{...}
链接url表达式
1.2、三元运算、条件表达式:
a? b:c # 如果a为true,则输出b,否则输入c。 相当于 (if else)
a? b # 如果a为true,则输出b,否则输入'' 。 相当于 a? b:''
示例:
Controller :
@RequestMapping("/thymeleaf")
public String thymeleaf(ModelMap map) {
map.put("name", "zhangsan");
return "/grammar/thymeleaf";
}
html:
<h3> 条件表达式语法</h3>
<div >
1. <span th:text="${name}"></span ><br>
2. <span th:text="${name} ? ${name}+'学习好':'李四体育好 '"></span ><br>
3. <span th:text="${name} ? ${name}+'学习好' "></span ><br>
4. <span th:text="${name2} ? '李四体育好 '"></span ><br>
</div>
运行结果:
说明:
第2个表达式: name不为空时,即是true,则输出第一个值 zhangsan学习好
。
第3个表达式: name不为空时,即是true,则输出第一个值 zhangsan学习好
。
第4个表达式: name2不存在,即是false,则输出 ' '
,即空。
从第2与第4 可以看出 a? b
相当于 a? b:''
。
解析后的 html 代码:
<h3> 条件表达式语法</h3>
<div >
1. <span>zhangsan</span ><br>
2. <span>zhangsan学习好</span ><br>
3. <span>zhangsan学习好</span ><br>
4. <span></span ><br>
</div>
1.3、默认表达式
当我们取一个值,可能为空时,我们可以提前设置一个默认值 。
语法:
?: b
相当于 ${a} ? ${a}:b
如果 a不为空时,输出a的值,否则输入b的值。
示例:
Controller :
@RequestMapping("/thymeleaf")
public String thymeleaf(ModelMap map) {
map.put("name", "zhangsan");
return "/grammar/thymeleaf";
}
html:
<h3> th:text 默认值</h3>
<div >
<div th:text="${name ?: '李四'}"></div >
<div th:text="${name2 ?: '李四'}"></div >
</div>
说明:
已经设置了name 为 zhangsan,则第一个表达式,输出zhangsan 。
第2个表达式,name2不存在,为空,则输入默认值李四
。
运行结果:
解析后的html 代码:
<h3> th:text 默认值</h3>
<div >
<div>zhangsan</div >
<div>李四</div >
</div>
2、字符串连接、拼接
字符串连接有两种方式 :
- 通过
' '
和+
拼接字符串 ; | |
拼接字符串(推荐);
示例1
html 代码:
变量:[[${hello}]]
<!-- 通过 '' 和 + 拼接字符串 -->
<div th:text="'哈哈,'+${hello}+','+${name}+'!'" ></div>
<!-- 通过 | | 拼接字符串(推荐) -->
<div th:text="|哈哈,${hello},${name}!|" ></div>
运行结果:
解析后的html 代码:
变量:hello world
<!-- 通过 '' 和 + 拼接字符串 -->
<div >哈哈,hello world,张三!</div>
<!-- 通过 | | 拼接字符串(推荐) -->
<div >哈哈,hello world,张三!</div>
示例2:
<!-- 通过 '' 和 + 拼接字符串 -->
<a href="javascript:void(0)" th:onclick=" 'javascript:permission_audit('+ ${id} +') '">通过</a>
<!-- 通过 | | 拼接字符串(推荐) -->
<a href="javascript:void(0)" th:onclick="|javascript:permission_audit(${id})|">通过</a>
解析后的代码:
<a href="javascript:void(0)" onclick="javascript:permission_audit(12) ">通过</a>
<a href="javascript:void(0)" onclick="javascript:permission_audit(12)">通过</a>
3、th:attr 的使用
th:attr 的用处就是把数据以属性值的保存起来。
多个属性时,请逗号(,)的方式分割。格式如下:
th:attr="attr1=${value1}, attr2=${value2}"
说明:
th:attr
标签定义多个属性的使用方式已经过时了,不推荐使用。推荐的方式:
attr1="${value1}" attr2="${value2}"
示例1:
@RequestMapping("/thymeleaf")
public String thymeleaf(ModelMap map) {
map.put("cityName", "北京");
map.put("cityId", "00001");
map.put("regionId", "010");
map.put("title", "这是一张图片哦");
map.put("logo", "风景图");
return "/grammar/thymeleaf";
}
html:
<h3> th:attr </h3>
<div id="cityBtn" class="btn" th:attr="data-cityId=${cityId}, data-regionId=${regionId}" th:text="${cityName}" >上海
<span class="fa fa-angle-down"></span>
</div>
运行结果:
解析后的代码:
<h3> th:attr </h3>
<div id="cityBtn" class="btn" data-cityId="00001" data-regionId="010" >北京</div>
说明:
可以看到数据以标签属性的方式保存起来。
示例2:
<img src="../../images/ccc.jpg"
th:attr="src=@{/images/ccc.jpg},title=${title},alt=${logo},myName=${logo}" />
运行结果:
解析后的代码:
<img src="/images/ccc.jpg" title="这是一张图片哦" alt="风景图" myName="风景图" />
4、th:href URL链接中传参
url 的参数 写在 括号内,多个参数时,用逗号分割。
示例:
Controller :
@RequestMapping("/thymeleaf")
public String thymeleaf(ModelMap map) {
map.put("id", "12");
map.put("name", "zhangsan");
return "/grammar/thymeleaf";
}
html:
<h3> 在 th:href url 中实现参数传递 </h3>
<a th:href="@{/show( id=${id } ,name=${name} )}">相对路径-传参</a>
运行结果:
解析后的代码:
多个参数时,用逗号分割
<h3> 在 url 中实现参数传递 </h3>
<a href="/show?id=12&name=zhangsan">相对路径-传参</a>
5、th:insert 、th:replace、th:include 代码片段引入时传参
Controller :
@RequestMapping("/contentPage2")
public String contentPage2(ModelMap map) {
map.put("varA", "aaaaaa");
map.put("varB", "bbbbbbb");
return "/fragments/contentPage2";
}
html:
/fragments/pagefrag3.html 代码片段:
<div th:fragment="frag (varC,varD)">
<p th:text="${varC} + ' - ' + ${varD}">...</p>
</div>
contentPage2.html :
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>thymleaf th:include 传参</title>
</head>
<body>
<div th:include="fragments/pagefrag3::frag(${varA},${varB})">...</div>
<div th:include="fragments/pagefrag3::frag(varC=${varA},varD=${varB})">...</div>
</body>
</html>
运行结果:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>thymleaf th:include 传参 </title>
</head>
<body>
<div>
<p>aaaaaa - bbbbbbb</p>
</div>
<div>
<p>bbbbbbb - aaaaaa</p>
</div>
</body>
</html>
对于 th:include="fragments/pagefrag3::frag(varC=${varA},varD=${varB})
指定参数名的方式时,
- 代码片段中也有对应的参数名,否则报错;
- 代码片段中是按照参数名的顺序来的, 无关主页面与代码片段指定的参数名是否一致。
6、th:inline 内联
虽然通过Thymeleaf标准⽅⾔中的标签属性已经⼏乎满⾜了我们开发中的
所有需求,但是有些情况下我们更喜欢将表达式直接写⼊我们的HTML⽂
本。 例如,我们喜欢这样写代码:
<p>Hello, [[${session.user.name}]]!</p>
⽽不喜欢这样写代码:
<p>Hello, <span th:text="${session.user.name}">Sebastian</
span>!</p>
[[...]]
或 [(...)]
中的表达式被认为是在Thymeleaf中内联的表达式。
thymeleaf 在html标签内可通过th标签加${}表达式访问model里的对象数据。
但如果不想通过th标签,而是简单地访问model对象数据,或是想在 javascript代码块里访问model中的数据,则要使用内联的方法。
th:inline 内联的取值有三种:text、javascript、 none
使用方式:
[[${ 变量名 }]]
7.1、th:inline=“text” 文本内联
Controller
@RequestMapping("/thymeleaf")
public String thymeleaf(ModelMap map) {
map.put("id", "12");
map.put("name", "zhangsan");
return "/grammar/thymeleaf";
}
html:
<p>Hello, [[${name}]]!</p>
运行结果:
解析后的代码:
<h3>th:inline 内联</h3>
<p>Hello, zhangsan!</p>
约等于 th:tex 标签:
<p>Hello, <span th:text="${name}">Sebastian</span>!</p>
解析事的代码是
<p>Hello, <span>zhangsan</span>!</p>
7.2、th:inline=“javascript” 脚本内联
如果想在javascript中 获取 变量值时,则需要加上th:inline="javascript"
:
<script type="text/javascript" th:inline="javascript">
var max = [[${name}]];
console.log(max);
</script>
注意:
由于thymeleaf 的版本不同,有时变量外层要加引号(单引号,双引号都可以),即var max = "[[${name}]]"
7.3、th:inline=“none” 禁止内联
因为内联的表达式是双层中括号 [[${ 变量名 }]]
, 当使用数组、二维数组时,就会与thymleaf 语法冲突,如果还想使用数据,此时必须禁止内联 h:inline="none"
,才使用常规的 javascript语法。
<input type="text" id="maxSumOfDateInYear" value="aaaaaaaaa"/>
<script type="text/javascript" th:inline="none">
var max = document.getElementById("maxSumOfDateInYear").value;
var data = [["2012-05-07", 6], ["2012-04-16", 4]];
console.log(max);
console.log(data);
</script>
此处,data表示二维数组,如果不禁止内联时,模板解析会出错的,所有要加上`th:inline=“none”,禁止使用 thymeleaf 语法,使用常规的 javascript 。
7、th:each 循环
在 th:each
迭代的同时,我们也可以获取迭代的状态对象 stat
:
stat 对象包 含以下属性:
- index,从0开始的角标
- count,元素的个数,从1开始
- size,总元素个数
- current,当前遍历到的元素
- even/odd,返回是否为奇偶,boolean值
- first/last,返回是否为第一或最后,boolean值
controller
@RequestMapping("/thymeleaf")
public String thymeleaf(ModelMap map) {
List list=new ArrayList();
list.add(new User(10,"张三",20,"北京"));
list.add(new User(25,"李四",34,"上海"));
list.add(new User(28,"王五",56,"深圳"));
list.add(new User(32,"赵六",66,"广州"));
map.put("userList", list);
return "/grammar/thymeleaf";
}
class User{
private int id;
private String name;
private int age;
private String address;
public User(int id, String name, int age, String address) {
super();
this.id = id;
this.name = name;
this.age = age;
this.address = address;
}
// setter/getter 省略
}
html :
<h3> th:each 循环</h3>
<div th:each="user,stat : ${userList}">
<span th:text="${stat.index}">index</span>
<span th:text="${user.name}">name</span>
<span th:text="${user.age}">age</span>
<span th:text="${user.address}">address</span>
<span th:if="${stat.even}">奇行</span>
<span th:if="${stat.odd}">偶行</span>
<span th:if="${stat.first}">第一行</span>
<span th:if="${stat.last}">最后一行</span>
</div>
运行结果:
解析后的代码:
<h3> th:each 循环</h3>
h3> th:each 循环</h3>
<div>
<span>0</span>
<span>张三</span>
<span>20</span>
<span>北京</span>
<span>偶行</span>
<span>第一行</span>
</div>
<div>
<span>1</span>
<span>李四</span>
<span>34</span>
<span>上海</span>
<span>奇行</span>
</div>
<div>
<span>2</span>
<span>王五</span>
<span>56</span>
<span>深圳</span>
<span>偶行</span>
</div>
<div>
<span>3</span>
<span>赵六</span>
<span>66</span>
<span>广州</span>
<span>奇行</span>
<span>最后一行</span>
</div>
8、th:remove 删除模板片段
th:remove 的值如下:
- all : 删除包含标签和所有的孩子 ;
- body : 不包含标记删除,但删除其所有的孩子 ;
- tag : 包含标记的删除,但不删除它的孩子 ;
- all-but-first : 删除所有包含标签的孩子,除了第一个 ;
- none :什么也不做。这个值是有用的动态评估 。
示例1
Controller
@RequestMapping("/thymeleaf")
public String thymeleaf(ModelMap map) {
map.put("id", "12");
return "/grammar/thymeleaf";
}
html:
<h3> th:remove </h3>
<div >
all:<div th:remove="all"><div id="hello">你好11</div></div>
body:<div th:remove="body"><div id="hello">你好11</div></div>
tag:<div th:remove="tag"><div id="hello">你好11</div></div>
tag:<div th:remove="none"><div id="hello">你好11</div></div>
</div>
运行结果:
解析后的代码:
<h3> th:remove </h3>
<div >
all:
body:<div></div>
tag:<div id="hello">你好33</div>
tag:<div><div id="hello">你好44</div></div>
</div>
示例2、th:remove 支持条件表达式
<h3> th:remove 支持条件表达式 </h3>
<div >
<!-- 表达式1与表达式2效果 一样的 -->
表达式1:<div th:remove="${id}==12 ? tag"><div id="hello">你好11</div></div>
表达式2:<div th:remove="${id}==12 ? tag:none"><div id="hello">你好22</div></div>
<!-- 表达式3: id==12时,返回body,即删除子标签的内容-->
表达式3:<div th:remove="${id}==12 ? body:tag"><div id="hello">你好33</div></div>
</div>
说明:
表达式1与表达式2效果 是一样的。id=12时,返回tag, 否则,返回’’ ,即为none 。
表达式3:id==12 时,返回body,即删除子标签的内容;id不等于12时,返回tag,删除当前标签。
运行结果:
解析后的代码:
<h3> th:remove 支持条件表达式 </h3>
<div >
<!-- 表达式1与表达式2效果 一样的 -->
表达式1:<div id="hello">你好11</div>
表达式2:<div id="hello">你好22</div>
<!-- 表达式3: id==12时,返回body,即删除子标签的内容-->
表达式3:<div></div>
</div>
9、th:with 定义局部变量
9.1、th:with 定义一个局部变量
thymeleaf - html:
<div th:with="hello2=${name}+',你好' ">
<div id="hello" th:text="${hello2}"></div>
</div>
解析后的代码:
<div>
<div id="hello">zhangsan,你好</div>
</div>
9.2、th:with 定义的局部变量有是作用范围的
th:with 定义的局部变量有作用范围的, 作用域限定于子标签以内。
thymeleaf - html:
<div th:with="hello2=${name}+',你好' ">
<div id="hello" th:text="${hello2}"></div>
</div>
<div id="hello" th:text="${hello2}"></div>
解析后的代码:
<div>
<div id="hello">zhangsan,你好</div>
</div>
<div id="hello"></div>
说明:
hello2 在作用域外使用,没有任何输出,为空的。
9.3、th:with 一次性定义多个变量
一次性定义多个变量,用逗号分割。
thymeleaf - html:
<div th:with="hello2=${name}+',你好',cityName2=${cityName}+',真美丽' ">
<div th:text="${hello2}"></div>
<div th:text="${cityName2}"></div>
</div>
解析后的代码:
<div>
<div>zhangsan,你好</div>
<div>北京,真美丽</div>
</div>
9.4、th:with 定义的变量可以复用
h:with 定义的变量可以复用,但必须在作用域内。
thymeleaf - html:
<div th:with="cityName2=${cityName}+',真美丽' , myDream=${cityName2}+',我真的好想去' ">
<div th:text="${myDream}"></div>
</div>
解析后的代码:
<div>
<div>北京,真美丽,我真的好想去</div>
</div>
说明:
myDream 复用了 cityName2 的值。
10、th:block 空标签,标签本身不显示
<th:block> </th:block>
是 Thymeleaf 提供的唯一的一个Thymeleaf块级元素,其特殊性在于Thymeleaf模板引擎在处理 <th:block>
的时候会删掉它本身,标签本身不显示,而保留其内容,应用场景主要有如下两个:
10.1、同时控制相连两个标签是否显示
如下代码:
<div id="div1" th:if="...">
</div>
<div id="div2" th:if="...">
</div>
div1 和 div2 中两个if条件一样时,可以改成如下写法:
<th:block th:if="...">
<div id="div1">
</div>
<div id="div2">
</div>
</th:block>
示例:
thymeleaf - html:
<th:block th:if="${id}==12">
<div id="div1">
张三的新增权限
</div>
<div id="div2">
张三的删除权限
</div>
</th:block>
解析后的代码:
<div id="div1">
张三的新增权限
</div>
<div id="div2">
张三的删除权限
</div>
10.2、循环同级标签
比如在表格中需要使用 th:each
循环 两个 tr,在不知道 th:block
标签时,可能会用 th:each
配合 th:if
使用,但是使用 th:block
就简单了,如下:
<table>
<th:block th:each="...">
<tr>...</tr>
<tr>...</tr>
</th:block>
</table>
10.3、用于占位符
Controller :
@RequestMapping("/main")
public String main(ModelMap map) {
return "/fragments5/main";
}
模板代码片段 base.html :
<head th:fragment="common_header(title,links)">
<title th:replace="${title}">The awesome application</title>
<!-- 共用的css和js -->
<link rel="stylesheet" type="text/css" media="all" th:href="@{/css/awesomeapp.css}">
<link rel="shortcut icon" th:href="@{/images/favicon.ico}">
<script type="text/javascript" th:src="@{/sh/scripts/codebase.js}"></script>
<!-- 额外添加的链接 -->
<th:block th:replace="${links}" />
</head>
主页面 main.html
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head th:replace="/fragments5/base :: common_header(~{::title},~{::link})">
<title>Main页面</title>
<link rel="stylesheet" th:href="@{/css/bootstrap.min.css}">
<link rel="stylesheet" th:href="@{/themes/smoothness/jquery-ui.css}">
</head>
<body>
<h1>th:replace</h1>
</body>
</html>
运行结果:
解析后的代码:
<!DOCTYPE html>
<html>
<head>
<title>Main页面</title>
<!-- 共用的css和js -->
<link rel="stylesheet" type="text/css" media="all" href="/css/awesomeapp.css">
<link rel="shortcut icon" href="/images/favicon.ico">
<script type="text/javascript" src="/sh/scripts/codebase.js"></script>
<!-- 额外添加的链接 -->
<link rel="stylesheet" href="/css/bootstrap.min.css"><link rel="stylesheet" href="/themes/smoothness/jquery-ui.css">
</head>
<body>
<h1>th:replace</h1>
</body>
</html>
具体参考文章:
https://blog.csdn.net/xiaojin21cen/article/details/102919572
11、th:if 条件判断
11.1、th:if 多条件判断,使用 &&
、||
<ul class="nav nav-second-level">
<li th:each="cmenu : ${menu.children}">
<a class="J_menuItem" th:if="${cmenu.text!= '角色管理' && cmenu.text!= '系统菜单'}"
href="graph_echarts.html" th:text="${cmenu.text}"
th:href="${cmenu.attributes.url}">系统管理</a>
</li>
</ul>
11.2、if elseif else 即 th:switch th:case
如果要实现if elseif else
判断表达式,在thymeleaf要使用 th:switch
代替,th:case="*"
表示默认,需写在最后
<div class="top" th:switch="${area}">
<div class="logo" th:case="'a'">
<img th:src="@{/static/images/logo-A.png}">
</div>
<div class="logo" th:case="'b'">
<img th:src="@{/static/images/logo-B.png}">
</div>
<div class="logo" th:case="*">
<img th:src="@{/static/images/logo-c.png}">
</div>
</div>
注意:th:case
所在的标签必须在 th:switch
所在标签的里面。