天天看點

Django中的模闆視圖中使用模闆模闆标簽過濾器

代碼說明:

通過 loader 來加載模闆頁面,如前面提到的,這裡是相對 polls/templates 目錄

建立上下文,将需要傳遞到頁面的變量放入上下文變量 context

使用 template 通過上下文來渲染頁面

在 settings.py 中有一個 template_loaders 屬性,并且有一個預設值 django.template.loaders.app_directories.loader,該值定義了從每一個安裝的 app 的 templates 目錄下尋找模闆。當然,你也可以編輯 settings.py 檔案中的 template_dirs屬性手動指定模闆路徑:

上面配置的是系統絕對路徑,最好的方式是使用代碼動态建構這個路徑,例如:

這個例子使用了神奇的 python 内部變量 <code>__file__</code> ,該變量被自動設定為代碼所在的 python 子產品檔案名。 <code>os.path.dirname(__file__)</code>将會擷取自身所在的檔案,然後由 <code>os.path.join</code> 這個方法将這目錄與 templates 進行連接配接。如果在 windows下,它會智能地選擇正确的後向斜杠’/’進行連接配接,而不是前向斜杠’/’。

完成 <code>template_dirs</code> 設定後,下一步就是修改視圖代碼,讓它使用 django 模闆加載功能而不是對模闆路徑寫死。

舉例如下:

一種更加簡潔的編碼方式是使用 <code>render_to_response()</code>:

上面兩個方法都會傳入 context 上下文,将頁面需要的變量傳到前台去,如果變量很多,需要一一輸入。還有一種更加簡單的方式,那就是可以利用 python 的内建函數<code>locals()</code> 。它傳回的字典對所有局部變量的名稱與值進行映射。 是以,前面的視圖可以重寫成下面這個樣子:

使用 <code>locals()</code> 時要注意是它将包括所有的局部變量,它們可能比你想讓模闆通路的要多。 在前例中,<code>locals()</code> 還包含了 request。

上面的例子中提到了模闆 <code>current_datetime.html</code> ,其中的内容如何定義呢?這個就要使用模闆标簽了。django 的模闆系統帶有内置的标簽和過濾器。

if 标簽檢查一個變量,如果這個變量為真(即,變量存在,非空,不是布爾值假),系統會顯示在 if 和 endif 之間的任何内容,例如:

else 标簽是可選的:

一些注意事項:

if 标簽接受 and ,or 或者 not 關鍵字來對多個變量做判斷,或者對變量取反。 if 标簽不允許在同一個标簽中同時使用 and 和 or ,因為邏輯上可能模糊的。 系統不支援用圓括号來組合比較操作。 多次使用同一個邏輯操作符是沒有問題的,但是我們不能把不同的操作符組合起來。 并沒有 elif 标簽, 請使用嵌套的 if 标簽來達成同樣的效果。 一定要用 endif 關閉每一個 if 标簽。

允許我們在一個序列上疊代。 與 python 的 for 語句的情形類似,循環文法是 <code>for x in y </code>,y 是要疊代的序列而x是在每一個特定的循環中使用的變量名稱。 每一次循環中,模闆系統會渲染在 for 和 endfor 之間的所有内容。

給定一個運動員清單 <code>athlete_list</code> 變量,我們可以使用下面的代碼來顯示這個清單:

給标簽增加一個 <code>reversed</code> 使得該清單被反向疊代:

在執行循環之前先檢測清單的大小是一個通常的做法,當清單為空時輸出一些特别的提示。

因為這種做法十分常見,是以 <code>for</code> 标簽支援一個可選的 empty 分句,通過它我們可以定義當清單為空時的輸出内容 下面的例子與之前那個等價:

django不支援退出循環操作。

在每個 for 循環裡有一個稱為<code>forloop</code> 的模闆變量。這個變量有一些提示循環進度資訊的屬性。

forloop.counter 總是一個表示目前循環的執行次數的整數計數器。 這個計數器是從1開始的,是以在第一次循環時 forloop.counter 将會被設定為1。
forloop.counter0 類似于 forloop.counter ,但是它是從0計數的。 第一次執行循環時這個變量會被設定為0。 forloop.revcounter 是表示循環中剩餘項的整型變量。 在循環初次執行時 forloop.revcounter 将被設定為序列中項的總數。 最後一次循環執行中,這個變量将被置1。 forloop.revcounter0 類似于 forloop.revcounter ,但它以0做為結束索引。 在第一次執行循環時,該變量會被置為序列的項的個數減1。 forloop.first 是一個布爾值,如果該疊代是第一次執行,那麼它被置為 true forloop.last 是一個布爾值;在最後一次執行循環時被置為true forloop.parentloop 是一個指向目前循環的上一級循環的 forloop 對象的引用(在嵌套循環的情況下)

ifequal 标簽比較兩個值,當他們相等時,顯示在 ifequal 和 endifequal 之中所有的值。參數可以是寫死的字元串,随便用單引号或者雙引号引起來。

和 if 類似,ifequal 支援可選的 else 标簽。

隻有模闆變量、字元串、整數和小數可以作為 ifequal 标簽的參數。

每當我們使用一次這個标簽後,标簽中的值就會變化,如上,每使用一次下面的 cycle 标簽,輸出的就會在 row1 和 row2 之間切換。

一些情況下,我們希望将cycle當做一個變量一樣來使用,那麼我們可以這樣:

最後,當出現我們不希望 cycle 主動輸出的時候,也就是我麼隻希望它作為一個變量的時候,我們可以這樣設定。

django 中的 url 标簽是用來簡化 url 的定義,其可以通過唯一的名稱引用 urls.py 中定義的 url。

例如:

對于上面的定義,可以在模闆裡通過 hello 名稱來應用 <code>hello/</code> 這個 url。

這樣使用的好處是,無論你怎麼修改 urlpatterns 的位址,template 都會随着改變,省事了不少。在模版中調用url标簽的時候,需要添加下面代碼:

需要注意的是:name是全局的,你整個 urlpatterns 裡隻能一個唯一的name。

如果想在試圖中使用該名稱,可以使用項目代碼(關鍵在于 <code>reverse</code> 函數):

當遇到urlpatterns的位址包含有參數的時候,如:

有兩個參數,最終的位址如歸檔的位址 http://blog.javachen.com/2014/10 ,這時候的标簽使用如下:

當然,在你背景的 views.py 中的方法上也必須有這兩個參數。

而在試圖裡寫法如下:

控制html轉義,參數是:on 或 off。效果和使用 safe 或 escape 過濾器相同。

防止跨站請求僞造。

輸出完整的調試資訊,包括目前的上下文及導入的子產品資訊。

通過可變過濾器過濾變量的内容。

過濾器也可以互相傳輸,它們也可以有參數,就像變量的文法一樣。

例:

注意: escape 和safe 過濾器不能接受參數,而使用 autoescape 标簽用來管理模闆代碼塊的自動轉移。

輸出傳入的第一個不是 false 的變量,如果被傳遞變量都是 false ,則什麼也不輸出。例:

等價于:

extends 标簽聲明這個模闆繼承的父模闆。

上面代碼中,首先用extends标簽聲明這個模闆繼承的父模闆(必須保證其為模闆中的第一個模闆标記)。接着重定義 css 這個 block,在包含了父模闆的基礎上(block.super)引入了新的 css 檔案;替換了 content 這個 block。這就是子模闆所做的全部工作。

所有的 block 标簽告訴模闆引擎,子模闆可以重載這些部分,如果子模闆不重載這些部分,則将按預設的内容顯示。例如:

順便提一下,模闆中的 <code>load staticfiles</code> 表示加載靜态資源,這個一般用于加載 css、js 等靜态檔案時用到

該标簽允許在(模闆中)包含其它的模闆的内容。标簽的參數是所要包含的模闆名稱,可以是一個變量,也可以是用單/雙引号寫死的字元串。每當在多個模闆中出現相同的代碼時,就應該考慮是否要使用 <code>include</code> 來減少重複,這也是為了提高代碼的可重用性。

注釋使用:

如果要實作多行注釋,可以使用 comment 模闆标簽。

模闆過濾器是在變量被顯示前修改它的值的一個簡單方法,過濾器使用管道字元,例如:

顯示的内容是變量 被過濾器 lower 處理後的結果,它功能是轉換文本為小寫。

過濾管道可以 套接 :

有些過濾器有參數。 過濾器的參數跟随冒号之後并且總是以雙引号包含。 例如:

這個将顯示變量 bio 的前30個詞。

當我們使用了網頁編輯器的時候,我們通過編輯器得到的是一串 html 代碼,如果位元組輸出,那麼 django 會将它預設輸出為字元串,進而不能顯示出樣式。這時候,我們可以使用過濾器來實作我們想要的。

這樣,我們的字元串就被當做 html 代碼來輸出了。safe 表示這段代碼是安全的。

一些常見的過濾器:

addslashes:添加反斜杠到任何反斜杠、單引号或者雙引号前面。 這在處理包含 javascript 的文本時是非常有用的。

date:按指定的格式字元串參數格式化 date 或者 datetime 對象,範例: