Node模板引擎学习(1)--Jade

Jade

安装:

npm install jade –global

安装后本地随便新建一个sample.jade文件,执行:

jade sample.jade

就能将其翻译成标准的sample.html源文件了
命令参数:
-P(大写,命令参数是大小写敏感的)。Jade默认编译出来的html源文件里是没有缩进的,不便于开发。加上-P参数后,编译出来的html源文件里就有缩进了:

jade -P sample.jade

-w用来watch监视jade文件,每次改动保存后自动编译成html文件,省去手动执行命令的麻烦:

jade -P -w sample.jade

-O用来给jade文件传递对象或JSON文件,用以替换模板内的变量:

jade -P -w sample.jade -O sample.json

标签和属性

省略尖括号,直接写标签名。标签间的嵌套关系用换行加空格来实现。紧接在标签名后加上.xx或#xx,就能给标签添加css类名和id。

标签名后第一个空格后面的内容会被编译成标签内的文本内容

标签属性的正统写法应该是写入()括号内

多行文本

在每行前加上|竖线符

用这种写法,可以用Jade语法来嵌套标签, 不仅可用于p标签等,也常见于style和script标签

p
  span 第1行文本
  | 第2行文本
  | 第3行文本
  | 第4行文本

//编译出来的结果
<p><span>第1行文本</span>第2行文本
  第3行文本
  第4行文本
<p>
script.
  console.log("open mind");
  console.log("learning quick");
  console.log("work hard");

变量

变量声明很简单,前面加上-横杠。使用变量只要#{变量名}就行了。例如:

- var cs = 'UTF-8'
meta(charset='#{cs}')

//编译出来的结果
<meta charset="UTF-8">
input(value='#{aaa}')
input(value=aaa)

//编译出来的结果
<input value="undefined">
<input>

如果不想HTML转码,可以将#改成!叹号

可以前面加\反斜杠来让Jade引擎不编译变量

可以在标签后面紧接=等号(不转义用!=)来输出变量

可以看出用#{}如果变量未定义,将会编译成undefined作为初始值。但用=等号来编译变量的话,如果变量未定义就忽略

有了变量就能轻松实现前后端分离。数据保存在JSON文件里。前端用Jade模板制作页面,在需要显示数据处用变量来实现。例如sample.json文件里:

{
  "charset": "UTF-8",
  "title": "My First Jade Page"
}

sample.jade文件里:

doctype html
html
  head
    meta(charset='#{charset}')
  body
    h1.titleClass#titleID #{title}

执行命令:jade -P -w sample.jade -O sample.json后Jade文件里的变量被自动替换。编译出来的sample.html:

<!DOCTYPE html>
<html>
  <head>
    <meta charset="UTF-8">
  </head>
  <body>
    <h1 id="titleID" class="titleClass">My First Jade Page</h1>
  </body>
</html>

语句

  • if-else
  • unless
  • case-when
  • for-in
  • each-in
  • while
- var author = 'Jack';
if author
  p 作者:#{author}
else
  p 无作者

//编译出来的结果
<p>作者:Jack</p>

Jade还支持unless语句,它是if-else的反向,写法都一样,用的不多就不举例了。
Jade里的case-when语句就是JavaScript里的switch-case语句(不知为何…)

- var authors = ['Jack', 'Bill'];case authors[0]
  when 'Jack'
    p 作者是Jack
  when 'Bill'
    p 作者是Bill
  default
    p 无作者

//编译出来的结果
<p>作者是Jack</p>

循环遍历用for-in(注意上面的if-else,case-when语句前不用像变量那样加上-横杠,但for的前面要加上-横杠。如果漏写-横杠,会被解析为标签):

- var person = {name:'Jack', gender: 'Male'}
- for (var prop in person)
  p= person[prop]

//编译出来的结果
<p>Jack</p>
<p>Male</p>
循环遍历也可以用each-in(each前的-横杠加不加均可):- var employee = {name:'Jack', gender: 'male'}
- each value, key in person
  p #{key}: #{value}
- var language = ['Java', 'JavaScript', 'C++']
ul
  each item in language
    li #{item}

//编译出来的结果
<p>name: Jack</p>
<p>gender: male</p>
<ul>
  <li>Java</li>
  <li>JavaScript</li>
  <li>C++</li>
</ul>

循环遍历也可以用while(同样前面加不加-横杠均可):

- var n = 0
ul
  while n < 4
    li= n++

//编译出来的结果
<ul>
  <li>0</li>
  <li>1</li>
  <li>2</li>
  <li>3</li>
</ul>

Mixin

mixin personInfo(name, hobbies)
  p #{name}'s hobbies:
    ul.hobby
      each hobby in hobbies
        li= hobby
+personInfo('Jack', ['movie', 'music'])

//编译出来的结果
<p>Jack's hobbies:</p>
<ul class="hobby">
  <li>movie</li>
  <li>music</li>
</ul>

模板

Jade用block和extends来实现模板的继承

block真正的作用在于占位,供子文件继承,可以理解为传统OO语言里的虚函数。父文件里定义的block,子文件里用extends来继承并重写

例如每个文件的页头都一样,就body里内容不一样,可以写一个header.jade:

doctype html
html
  head
    meta(charset='#{charset}')
    block scripts
      script(src='jquery.js')
      script(src='underscore.js')
      script(src='backbone.js')
  body
    block content
      p please write content

每个页面的header都长这样。而body里定义了block content,这里block可以理解为一个占位符placeholder,需要继承它的文件重写block content。根据业务需求写页面主体部分,例如sample.jade改成这样:

extends header

block content
  h1.titleClass#titleID #{title}
  a(href='http://www.jackzxl.net', target='_blank') 我的主页
  ……

在sample.jade里,开头用extends表明和header.jade的继承关系。然后根据业务重写header.jade里的block content。

(执行jade -P -w sample.jade -O sample.json就能看到和之前一模一样的页面。引擎加载流程是:解析sample.jade,发现开头有extends,就去解析header.jade,将其编译成html。此时html里的body里是<p>please write content</p>。解析完header.jade就继续解析sample.jade,发现block content,于是会将定义在header.jade里的block content替换掉。最终输出的是正确的页面内容,而不是<p>please write content</p>。(但如果你执行的是jade -P -w header.jade -O sample.json会发现body里内容为<p>please write content</p>))

除继承外还可以用include包含。Include会将内容无脑全拷贝进去。例如上面的sample.jade第一行extends header改成include header。

与extends不同,include就是无脑将另一个文件里的内容直接拷贝进去,不像block + extends可以重写block。

注意:include包括extends如果省略后缀名,Jade默认该文件时.jade会进行编译。但如果另一个文件里写的是原生的html,需要写明后缀名为.html(例如include xx.html),明确告诉Jade不要编译。

注释

Jade里加上//就能添加注释,用双斜杠的注释会被输出到html源码里。

如果不想在html源码里输出注释,用//-,在双斜杠后加一横杠。

html里还可以写注释型的条件语句,常用于兼容IE。Jade里你同样可以写这些条件语句,例如将上面header.jade改成能识别IE89,应用不同的class:

doctype html
<!--[if IE 8]><html class='ie8'><![endif]-->
<!--[if IE 9]><html class='ie9'><![endif]-->
<!--[if !IE]><!--><html><!--<![endif]-->
head
  meta(charset='#{charset}')
  block scripts
    script(src='jquery.js')
    script(src='underscore.js')
    script(src='backbone.js')
body
  block content
  p please write content
</html>

上面因为有了条件语句,所以html标签用尖括号括了起来,因此最下面要手动加上来闭合标签。而且Jade是空格缩进敏感的,需要将原先的head和body包括里面内容,全往前缩进2个空格。

块注释

块注释也是支持的:

body
  //
    #content
      h1 Example

渲染为:

<body>
  <!--
  <div id="content">
    <h1>Example</h1>
  </div>
  -->
</body>

Jade 同样很好的支持了条件注释:

body
  //if IE
    a(href='http://www.mozilla.com/en-US/firefox/') Get Firefox

渲染为:

<body>
  <!--[if IE]>
    <a href="http://www.mozilla.com/en-US/firefox/">Get Firefox</a>
  <![endif]-->
</body>

过滤器

Jade同样兼容其他模块,例如写博客爱用的markdown,写css爱用的less,还有coffeeScript等。只要npm安装好后,用:冒号+模块名就能声明使用这些模块,例如:

:markdown
  ...
:less
  ...
:coffee
 ...
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 218,284评论 6 506
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,115评论 3 395
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 164,614评论 0 354
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,671评论 1 293
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,699评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,562评论 1 305
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,309评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,223评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,668评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,859评论 3 336
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,981评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,705评论 5 347
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,310评论 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,904评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,023评论 1 270
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,146评论 3 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,933评论 2 355

推荐阅读更多精彩内容

  • Express框架里内嵌了Jade模板引擎。正好项目里也要用到,本篇整理了下Jade的相关用法。 安装与执行 标签...
    张歆琳阅读 25,516评论 8 42
  • Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智...
    卡卡罗2017阅读 134,657评论 18 139
  • Jade语法归纳 把 Jade 编译为一个可供浏览器使用的单文件,只需要简单的执行: 如果你已经安装了 uglif...
    majun00阅读 521评论 0 1
  • 今天中午我一个人去食堂吃了想了几天的梅菜扣肉,咸淡适宜、肥瘦均匀,特别是外面那层肉皮,真的又糯又好吃。 忘了这是第...
    团团不是圆圆阅读 2,805评论 18 17
  • 不知道为什么最近总是莫名感伤,无故的掉眼泪,我没有真正经历过生死,所以我害怕,我害怕未知,我害身边突如其来的死亡消...
    属猪的狮子座阅读 795评论 0 0