1. 程式人生 > >7)Thymeleaf 內聯表示式、文字、JavaScript、CSS

7)Thymeleaf 內聯表示式、文字、JavaScript、CSS

目錄

內聯表示式

th:inline="none" 禁用內聯

內聯 JavaScript

JavaScript ⾃然模版

⾼級內聯表示式JS序列化

內聯 CSS


內聯表示式

     雖然通過 Thymeleaf 標準⽅⾔中的標籤屬性已經⼏乎滿⾜了開發中的所有需求,但是有些情況下更喜歡將表示式直接寫⼊到 HTML ⽂本中:

例如有時候這樣更合適:<p>Hello, [[${session.user.name}]]</p>
⽽不喜歡這樣寫程式碼:<p>Hello, <span th:text="${session.user.name}">Sebastian</span>!</p>

     [[...]] 或 [(...)] 中的表示式就是 Thymeleaf 中內聯表示式,任何在 th:text 或 th:utext 屬性中使⽤的表示式都可以出現在 [[]] 或 [()] 中使用, [[...]] 等價於 th:text(結果將被 HTML 轉義),[(...)] 等價於 th:utext(結果不會執⾏HTML轉義)。

<body>
<!--後臺傳出:model.addAttribute("info", "Love you <b>中國</b>");-->
<!--/*前者會轉義,後者不會轉義*/-->
<p>[[${info}]]</p>
<p>[(${info})]</p>

<!--/*可以是任意的資料型別,如普通的文字,與 th:text、th:utext完全等價*/-->
<p>[[Love]]</p>
<p>[['I Love You Baby']]</p>
<p>[(9527)]</p>
</body>

     提示:當靜態開啟 HTML ⽂件時,內嵌的表示式將逐字顯示在 HTML ⽂件中,因此⽆法將其⽤作設計原型了!比如 “<p>[[${info}]]</p>” 如果是以靜態原型開啟,那麼顯示的就是 <p>[[${info}]]</p>。

th:inline="none" 禁用內聯

     內聯機制可以被禁⽤,因為在實際應⽤中可能會想輸出 [[...]] 或 [(...)] 序列⽽不將其內容作為表示式處理的情況。 為此將使⽤ 
th:inline =“none”

來禁⽤內聯。

<body>
<!--/*禁用內聯表示式*/-->
<p th:inline="none">[[${info}]]</p>
<p th:inline="none">[(${info})]</p>

<!--/*禁用內聯表示式*/-->
<p th:inline="none">[[Love]]</p>
<p th:inline="none">[['I Love You Baby']]</p>
<p th:inline="none">[(9527)]</p>
<p th:inline="none">[[1,2,3,4,5]]</p>
</body>

內聯 JavaScript

     JavaScript 內聯允許在 HTML 模板模式中更好地整合 JavaScript <script>塊。與⽂本內聯⼀樣,這實際上等同於處理指令碼內容,就像它們是JavaScript 模板模式中的模板⼀樣,因此⽂本模板模式的所有功能都可以在內聯指令碼中使⽤。 
     必須使⽤ th:inline ="javascript" 顯式的啟⽤此 JavaScript 模板模式:

<head lang="en">
    <meta charset="UTF-8">
    <title>使用者首頁</title>
    <link type="text/css" rel="stylesheet" th:href="@{/css/userHome.css}">

    <script type="text/javascript" th:inline="javascript">
        /**
         * 後臺輸出:
         * model.addAttribute("info", "Love you <b>中國</b>");
         * model.addAttribute("age", 35);//注意:使用 [(${info})] 時編譯報錯,瀏覽器執行也會報錯
         * model.addAttribute("id", null);
         * model.addAttribute("name", "");
         * @type {*[]}
         */
        var info = [[${info}]];
        var age = [[${age}]];
        var id = [[${id}]];
        var name = [[${name}]];
        console.log(id, name, age, info);
    </script>
</head>

特別提示:th:inline ="javascript" 顯式啟⽤ JavaScript 模板模式只能是在 Html 檔案內部的 JavaScript 程式碼,如上所示。不能在引入的外部 JavaScript 檔案中進行操作,如:

<script type="text/javascript" th:inline="javascript" th:src="@{/js/userHome.js}"></script>

//如果在這個外接的 userHome.js 中進行內聯表示式操作,則 Thymeleaf 無法解析,瀏覽器識別不了而報錯。

JavaScript ⾃然模版

     Thymeleaf 的目標就是希望前後端分離,即同一個 Html 檔案前端人員以靜態原型的方式開啟時,看到的是它們的內容,而後端人員通過伺服器開啟時,看到的是動態的資料。內聯的 JavaScript 同樣可以實現這一點。在 JavaScript 註釋中包含(轉義)內聯表示式即可滿足此需求。

    <script type="text/javascript" th:inline="javascript">
        /**
         * 後臺輸出:model.addAttribute("info", "Love you <b>中國</b>");
         * Thymeleaf 將自動忽略掉註釋之後 和 分號之前的所有內容,如下為 "前端測試"
         */
        var info = /*[[${info}]]*/ "前端測試";
        console.log(info);
    </script>

這種在前後端都可以執行的 JavaScript 指令碼稱為 JavaScript ⾃然模板!

⾼級內聯表示式JS序列化

     關於 JavaScript 內聯的⼀個重要的特性是,內聯表示式的計算結果不限於字串,它能⾃動的將以下物件序列化為 javascript 物件。 Thymeleaf ⽀持以下⼏種序列化物件:

1)Strings
2)Numbers
3)Booleans
4)Arrays
5)Collections
6)Maps
7)Beans (有getter _and _setter⽅法)

     Thymeleaf 對 JavaScript 序列化的⽅式是通過 org.thymeleaf.standard.serializer.IStandardJavaScriptSerializer 接⼝的實
現,可以在模板引擎的 StandardDialect 的例項中進⾏配置。

     該 JavaScript 序列化機制預設將在類路徑中查詢 Jackson 庫,如果存在,將使⽤它。 如果沒有,它將應⽤⼀個內建的序列化機制,內建的序列化機制涵蓋⼤多數場景的需求,並和 Jackson 序列化機制產⽣類似的結果。

     這裡以後臺控制器傳出一個 List<User> 物件為例進行說明,其它都是同理,User 是 Java Beab,提供了 getter、setter 方法。

    <script type="text/javascript" th:inline="javascript">
        /**
         * 後臺輸出:model.addAttribute("userList", userList);
         * userList 是一個 List<User> 的結構,其中有5個元素
         */
        var userList = [[${userList}]];
        /**已經被 Thymeleaf 序列化為 JS 物件,是一個數組加Object 的個數,即陣列中有5個Object*/
        console.log("userList", userList);
        for (let i = 0; i < userList.length; i++) {
            /**取值列印*/
            console.log(i, userList[i], userList[i].uName);
        }
    </script>

內聯 CSS

Thymeleaf 還允許在 CSS <style> 標籤中使⽤內聯,如:

<style th:inline="css">
   ...
</style>

<head lang="en">
    <meta charset="UTF-8">
    <title>使用者首頁</title>
    <link type="text/css" rel="stylesheet" th:href="@{/css/userHome.css}">
    <!--/*為了測試簡單,直接使用 th:with 定義兩個區域性變數;也可以後臺傳輸來的*/-->
    <style type="text/css" th:inline="css" th:with="h4Color='yellow',fontSize='25px'">
        p {
            color: [[${h4Color}]];
            font-size: [(${fontSize}) ];
        }
    </style>
</head>

注意事項:

1)獲取變數賦值時,fontSizt 需要使用 [(...)] 不進行轉義,如果是 [[...]] 轉義則會多出來一個斜槓而導致無效。

2)與內聯 JavaScript ⼀樣,CSS 內聯也允許 <style> 標籤可以靜態和動態地⼯作,即通過在註釋中包含內聯表示式作為CSS ⾃然模板。

<style type="text/css" th:inline="css" th:with="h4Color='yellow',fontSize='25px'">
    p {
        color: /*[[${h4Color}]]*/ red;
        font-size: [(${fontSize})];
    }
</style>

3)如上所示當伺服器動態開啟時,字型顏色為黃色;當以原型靜態開啟時,顯示的是紅色,因為 Thymeleaf 會自動忽略掉 css 註釋之後 和 分號之前的程式碼。

4)因為 CSS 自然模板的問題,所以不能在 css 中像以前一樣添加註釋,因為 Thymeleaf 會將它們當做模板進行處理。

5)與 內聯 JavaScript 一樣,內聯 CSS 同樣只能 Html 內嵌的 <style 標籤中進行使用,不能在外部 關聯的 CSS 檔案中進行使用。

<link type="text/css" rel="stylesheet" th:href="@{/css/userHome.css}" th:inline="css">

//這是錯誤的,不能在 userHome.css 檔案中使用內聯 CSS。