Jade是Node.js的一个模板引擎,他借鉴了Haml,语法和Haml相似,支持空格缩进。
一行开头的任何文件都会被默认解释成HTML标签,Jade的主要优势是为HTML元素同时渲染闭合和开始标签,
标签后的文本和空格会被解释成内联HTML,也就是元素的文本内容。如:
Body div h1 Practical Node.js p The only book most people will ever need. div footer © Apress上面的模板会输出:
<body> <div> <h1>Practical Node.js</h1> <p>The only book most people will ever need.</p> </div> <div> <footer>© Apress</footer> </div> </body>传给Jade模板的数据称为locals。要输出一个变量的值,使用等号=。 Jade代码:
h1= title p= body (locals): { title: "Express.js Guide", body: "The Comprehensive Book on Express.js" }输出的HTML:
<h1>Express.js Guide</h1> <p>The Comprehensive Book on Express.js</p>属性紧跟在标签的名字之后,用括号括起来,格式是name=value。多个属性之间用逗号分割。 如:
div(id="content", class="main") a(href="http://expressjsguide.com", title="Express.js Guide", target="_blank") Express.js Guide form(action="/login") button(type="submit", value="保存") div(class="hero-unit") Lean Node.js!会变成:
<div id="content" class="main"> <a href="http://expressjsguide.com" title="Express.js Guide" target="_blank">Express.js Guide</a> <form action="/login"> <button type="submit" value="保存"></button> </form> <div class="hero-unit">Learn Node.js</div> </div>有时,一个属性的值必须是动态的,在这种情况下,只需要使用该变量的名字。符号|允许我们在新的一行里写HTML节点的内容,换句话说,就是有符号|的那行会变成文本内容。 如:
a(href=url, data-active=isActive) label input(type="checkbox", checked=isChecked) | yes / no给上面的模板提供数据:
{ url: "/logout", isActive: true, isChecked: false }模板和数据一起会输出如下:
<a href="/logout" data-active="data-active"></a> <label> <input type="checkbox" />yes / no </label>注意:值是false的属性在输出HTML代码时会被忽略;而当没有传值时,会被赋值为true 如:
input(type="radio", checked) input(type="radio", checked=true) input(type="radio", checked=false) <input type="radio" checked="checked" /> <input type="radio" checked="checked" /> <input type="radio" />为了方便起见,可以直接在标签名之后写类和ID。比如,我们给一个段落使用类lead和center,给一个div使用ID side-bar和类pull-right(再次使用符号|创建文本内容):
div#content p.lead.center | webapplog: where code lives #side-bar.pull-right span.contact.span4 a(href="/contact">Contact us翻译成:
<div id="content"> <p class="lead center"> webapplog: where code lives <div id="side-bar" class="pull-right"></div> <span class="contact span4"> <a href="/contact">Contact us</a> </span> </p> </div>注意:如果没有写标签名,则默认就是div标签
通过符号|可以输出原始文本
有时,开发人员要在HTML的script 或 style标签里写内容块。这时,可以使用点号. 比如,可以这样写前端JavaScript:
script. console.log('Hello Jade!') setTimeout(function(){ window.location.href='http://rpjs.co' }, 200) console.log('Good bye!')翻译成:
<script> console.log('Hello Jade!') setTimeout(function(){ window.location.href='http://rpjs.co' }, 200) console.log('Good bye!') </script>与上面例子相反,如果要在模板编译时使用JavaScript代码, 即,要在Jade中写可以操作输出的可以执行JavaScript代码,可以使用符号-、=或!=。 这在要输出HTML元素和注入JavaScript时是很有用的,很显然,处理这种操作要小心,要避免跨站脚本(XSS)攻击, 如:
- var arr= ['<a>','<b>','<c>'] ul - for(var i=0; i<arr.length; i++) li span=i span!="unescaped: " + arr[i] + "vs." span= "escaped: " + arr[i]会生成这个:
<ul> <li><span>0</span><span>unescaped: <a> vs. </span><span>escaped: <a></span></li> <li><span>1</span><span>unescaped: <b> vs. </span><span>escaped: <b></span></li> <li><span>2</span><span>unescaped: <c> vs. </span><span>escaped: <c></span></li> </ul>提示:Jade和Handlebars的一个主要区别是:Jade允许在代码里写几乎所有的JavaScript; 而Handlebars则限制开发人员只能使用少量的内置和自定义的helpers。
想输出注释:用JavaScript的注释形式// 不想输出注释:则使用//- 如:
// content goes here p Node.js is a non-blocking I/O for scalable apps. //- @todo change this to a class p(id="footer") Copyright 2015 深情小建输出:
<!-- content goes here--> <p> Node.js is a non-blocking I/O for scalable apps.</p> <p id="footer">Copyright 2015 深情小建</p>给if语句加个前缀-,就可以写标准的JavaScript代码了。 也可以使用一种极简的不需要前缀、不需要括号的替代写法 如:
- var user = {} - user.admin = Math.random() > 0.5 if user.admin button(class="launch") Launch Spacecraft else button(class="login") Log in除了if外,还有unless,他相当于不或者!
与if语句相似,Jade里的迭代可以只简单地写each, 如:
- var languages = ['php', 'node', 'java', 'ruby', 'c++'] div each value, index in languages p= index + ". " + value输出的HTML如下
<div> <p>0. php</p> <p>1. node</p> <p>2. java</p> <p>3. ruby</p> <p>4. c++</p> </div>同样的写法也适用于是对象的时候:
- var languages = {'php': -1, 'node': 2, 'java': 3, 'ruby': 6, 'c++': 1} div each value, key in languages p= key + ": " + value上面的Jade被编译后,输出HTML
<div> <p>php: -1</p> <p>node: 2</p> <p>java: 3</p> <p>ruby: 6</p> <p>c++: 1</p> </div>当有一个文本块需要用另外一种语言写时,就会用到过滤器。比如:Markdown的过滤器的写法如下:
p :markdown # Practical Node.js [This book](http://expressjsguide.com) really helps to grasp many components needed for modern-day web development.注意:要想使用Markdown的过滤器,需要安装Markdown模块,以及marked和Markdown NPM包。不需要其他配置,只要在项目的本地文件夹node_modules下安装他们即可。
Jade中读取变量的值是通过#{name}来实现的。 如:
- var title = "Express.js Guide" p Read the #{title} in PDF, MOBI and EPUB在模板编译时变量的值就会被处理,因此,不要在可执行JavaScript(-)里使用它。
mixin是带参数,并产生一些HTML的函数。声明的语法是mixin name(param, param2, …),用法是+name(data) 如:
mixin row(items) tr each item, index in items td= item mixin table(tableData) table each row, index in tableData +row(row) - var node = [{name: "深情小建"}, {name: "刘德华"},{name: "孙悟空"}] +table(node) - var js= [{name: "那英"}, {name: "哈林"},{name: "王峰"}] +table(js)上面的模板和数据生成的HTML代码如下:
<table> <tr> <td>深情小建</td> </tr> <tr> <td>刘德华</td> </tr> <tr> <td>孙悟空</td> </tr> </table> <table> <tr> <td>那英</td> </tr> <tr> <td>哈林</td> </tr> <tr> <td>王峰</td> </tr> </table>include是把逻辑提取到单独文件里的一种方式,旨在让多个文件重用他, include是一种自顶向下的方法, 格式:include /path/filename。 如:include ./includes/header 注:不用给模板名字和路径加双引号或单引号 下面的例子会从父目录开始查找: include ../includes/footer 但是,没有办法在文件名和文件路径里使用变量,因为includes/partials是在编译时处理的,而不是在执行时。
extend是一种自底向上的方法(和include相反) 格式:extend filename 和 block blockname 如: 在文件file_a里:
block header p some default text block content p Loading ... block footer p copyright在文件file_b里:
extend file_a block header p very specific text block content .main-content