zoukankan      html  css  js  c++  java
  • doT学习(一)之语法

    简介

    创建搜索最快和简洁的JavaScript模板函数,强调V8和nodejs下的性能,它在nodejs和浏览器上都显示了很好的性能。

    dot.js速度快,体积小,没有依赖关系,源js代码只有140行

    特性

    • 无依赖

    • 极其快速

    • 自定义定界符 (custom delimiters)

    • 运行时求值 (runtime evaluation)

    • 运行时插值 (runtime interpolation)

    • 编译时求值 (compile-time evaluation)

    • 支持局部模板

    • 支持条件语句

    • 数组迭代器

    • 编码

    • 控制空白字符 - 全去或保留

    • 流媒体友好

    • 轻逻辑或者重逻辑,由你决定

    doT.js详细使用介绍

    安装方法

    • 用于浏览器引入

         javascript 文件:

        <script type="text/javascript" src="doT.js"></script>

         自代码中使用

       <script type="text/x-dot-template"></script>

    • 用于 Node.js

      如果你打算在 Node.js 中使用 doT,可以通过 npm 安装 doT

        npm install dot

        在代码中使用require('dot')

    调用方式

    doT渲染模板分为2个阶段,这一点从它的使用方法中也能看出来:

    // 1. 编译模板函数
    var tempFn = doT.template("<h1>Here is a sample template {{=it.foo}}</h1>");
    // 2. 渲染模板函数
    var resultText = tempFn({foo: 'with doT'});

    这一点是与其他主流的模板引擎不同的。 在compile阶段,可以依赖其他模板文件,缓存模板等操作。还可以传入参数,通过条件判断生成模板内容。 在页面载入或是服务器启动时,根据一些环境变量或其他条件预先编译模板,可以进

    一步提高模板渲染是的效率。

    doT.template方法的第2个参数为配置项,第3个参数为编译时可接收的参数,参数在模板中被默认存储在def对象下,具体用法在{{#}}语法中介绍。

    doT.template方法返回值为function类型:tempFn,tempFn接收的参数是模板渲染时可传入的数据(与前面编译时的数据不是同一份数据)。该数据在模板中被默认存储在it对象下具体用法在{{}}和{{=}}等语法中都会介绍。

    doT.templateSettings - 默认编译设置

    可以通过改变编译设置自定义 doT。这是默认设置:

    doT.templateSettings = {
      evaluate:    /{{([sS]+?)}}/g,
      interpolate: /{{=([sS]+?)}}/g,
      encode:      /{{!([sS]+?)}}/g,
      use:         /{{#([sS]+?)}}/g,
      define:      /{{##s*([w.$]+)s*(:|=)([sS]+?)#}}/g,
      conditional: /{{?(?)?s*([sS]*?)s*}}/g,
      iterate:     /{{~s*(?:}}|([sS]+?)s*:s*([w$]+)s*(?::s*([w$]+))?s*}})/g,
      varname: 'it',
      strip: true,
      append: true,
      selfcontained: false
    };

    如果你想用自己的定界符,可以修改 doT.templateSettings 中的正则表达式。

    这是默认的定界符列表:

    • {{= }} 用于插值

    • {{ }} 用于求值

    • {{~ }} 数组迭代

    • {{? }} 条件语句

    • {{! }} 用于编码求值

    • {{# }} 用于编译时求值/引入和局部模板

    • {{## #}} 用于编译时定义

    其他说明

    • varname : 模板数据引用变量名

         默认情况,模板中的数据必须用 'it' 作为引用。修改设置中的 'varname',可以改变默认的变量名。 例如,你可以把 'varname' 设置成 "foo, bar",就可以传2个数据实例,通过 foo 和 bar 与模板建立关联。

    • strip : 控制空白字符, true:全部去掉空格; false:保留空格
    • append : 性能优化设置

            通过它调整性能,根据使用的 javascript 引擎和模板的大小,append 设置成 false,可能会产生更好的效果。

    • selfcontained:依赖设置

        如果 'selfcontained' 为 true,doT 将毫无依赖的产生函数。通常,doT 都是无依赖的,除非用到编码时,encodeHTML 会被加入。 如果 'selfcontained' 为 true,模板需要编码,encodeHTML 方法将被引入生成模板的函数中。

    doT.template - 模板编译函数

    调用此函数把你的模板编译成一个方法。

    function(tmpl, c, def)

    • tmpl - 模板正文

    • c - 自定义编译设置,如果为 null,用到 doT.templateSettings

    • def - 编译时求值的数据(与前面编译时的数据不是同一份数据)

    默认,产生的方法有一个参数 - data - 命名为 'it' 。修改 doT.templateSettings.varname,可以改变参数的名字和个数。

    实例

    插值(evaluation)

    用法:{{= }},输出表达式,{{= }} 将其中的内容直接输出到html中。其中可以是在{{ }}中定义的变量、通过函数传入在it中的变量、也可以是全局变量、甚至可以是一个立即执行的function的返回结果。 可以简单的理解为可以获取特定作

    用于下变量的单行js语句

    // 模板字符串:
    {{
      it.a = 1;
      a = 2;
    }}
    {{= it.a}} it.a = 1
    {{= a}} a = 2
    {{= window}} window = [object Window]
    {{= (function(){return 123})()}} function(){return 123})() = 123

    创建模板,默认情况下,模板中的数据用it作为引用,可修改配置中的varname来改变变量名;

    <script type="text/x-dot-template" id="testTpl">
        <div>{{= it.msg }}</div>
        <div>{{= it.code }}</div>
    </script>

    使用:

    var message = {
        msg: 'Hello world.',
        code: 200
    };
    //使用doT.template(tplText)函数,tplText为模板文本
    var tpl = doT.template($("#testTpl").text()); //某些浏览器可能会取不到模板内容,可用$("#testTpl").html()
    //传入数据获取html
    var html = tpl(message);
    console.log(html); 

    结果输出:

    <div class="msg">Hello world.</div> <div class="code">200</div> 

    求值(evaluate)

    用法:{{ }},可在表达式中使用js脚本,代码片段,{{ }} 的用法非常灵活,里面可以直接写js语句。定义的变量可以直接在{{= }}中调用。也可以调用通过tempFn传入的数据(数据默认放在it对象内)。

    // 模板字符串:
    {{
       var a = 1;
       it.a = a + 1;
    }}
    
    {{= a}} //  a 输出 1
    {{= it.a}}  // it.a 输出 2

    也可以定义函数。并在其他的{{}} 区块内调用:

    // 模板字符串:
    {{
     function fn() {
       return 123
     }
    }}
    
    {{= fn()}} //  fn 输出 123
    
    也可以直接运行匿名函数
    {{
      (function() {
        it.b = 123
      })();
    }}
    
    {{= it.b}} // it.b通过直接执行的匿名函数赋值为123

    {{}}中的代码块随时可以被打断,插入dom片段等html内容:

    // 模板字符串:
    {{
      var a = 3;
      if(a > 2) {
    }}
      a的值大于2
    {{
      } else {
    }}
      a的值小于2
    {{
     }
    }}

    此外,{{}}中也可以直接调用全局对象下的函数或变量。可以以此特点实现比较复杂的功能(通过专用的命名空间给doT模板提供一些过滤器等特色的支持等)。

    注意:如果在tempFn函数的调用中不传参数或者传入的是undefined等空对象,则doT不会实例化it对象。此时在{{}}中赋值的it对象的值,{{=}}中无法拿到(js的值引用问题)。

    创建模板: 

    <script type="text/x-dot-template" id="testTpl2">
        {{ if (it.status == true) { }}
            <div class="success">操作成功</div>
        {{ } else { }}
            <div class="error">操作错误</div>
        {{ } }}
    </script>

    使用:

    var result = {
        status: true,
        error: ''
    };
    var tpl = doT.template($("#testTpl2").text());
    var html = tpl(result);
    console.log(html);

    结果输出:

    <div class="success">操作成功</div>  

    条件语句(conditional)

    用法:{{? }},{{?}}标签必须成对出现,起始标签中写入判断条件,并以另外一个{{?}}标签为结束。该标签和下面的{{~}}是{{if for}}的语法糖。

    如上面的:

    // 模板字符串:
    {{
      var a = 3;
      if(a > 2) {
    }}
      a的值大于2
    {{
      } else {
    }}
      a的值小于2
    {{
     }
    }}

    可以用本标签简写为:

    // 模板字符串:
    {{
      var a = 3;
    }}
    {{? a>2}}
      a的值大于2
    {{?? true}}
      a的值小于2
    {{?}}

    在上个 求值(evaluate) 例子中的模板恰好是条件判断,我们可以用{{? }}改写模板以达到一样的效果:

    <script type="text/x-dot-template" id="testTpl2">
        {{? it.status == true }}
            <div class="success">操作成功</div>
        {{?? }}
            <div class="error">操作错误</div>
        {{? }}
    </script>

    使用方法参考求值(evaluate)例子,最后输出html是一样的。

    数组迭代(iterate)

    用法:{{~ }},循环,{{~}}标签必须成对出现,起始标签中写入对数组遍历的变量赋值:{{~it.array :value:index}},并以另外一个{{~}}标签为结束。

    创建模板:

    <script type="text/x-dot-template" id="testTpl3">
        {{~ it.list:item:index }}
            <tr>
                <td>{{= index + 1 }}</td>
                <td>{{= item.name }}</td>
                <td>{{= item.email }}</td>
            </tr>
        {{~ }}
    </script>

    使用:

    var data = {
        status: true,
        msg: 'success',
        list: [{
            id: 1,
            name: 'zhangsan',
            email: 'zhangsan@lwhweb.com'
        }, {
            id: 2,
            name: 'lisi',
            email: 'lisi@lwhweb.com'
        }]
    };
    var tpl = doT.template($("#testTpl3").html());
    var html = tpl(data);
    console.log(html);

    结果输出:

    <tr> <td>1</td> <td>zhangsan</td> <td>zhangsan@lwhweb.com</td> </tr>  <tr> <td>2</td> <td>lisi</td> <td>lisi@lwhweb.com</td> </tr>

    编码插值

    用法:{{!  }} encode 转义,{{! }} 会将其中的内容中特定字符进行转义,如:{{! location.href}}

    // 数据源
    {"uri":"http://jq22.com/?keywords=Yoga"}
    
    // 区域
    <div id="encode"></div>
    
    // 模版
    <script id="encodetmpl" type="text/x-dot-template">
        Visit {{!it.uri}} {{!it.html}}
    </script>
    
    // 调用方式
    var dataEncode = {"uri":"http://jq22.com/?keywords=Yoga","html":"<div style='background: #f00; height: 30px; line-height: 30px;'>html元素</div>"};
    var EncodeText = doT.template($("#encodetmpl").text());
    $("#encode").html(EncodeText(dataEncode));

    编译时变量定义

    用法:{{## #}}

    {{## #}}有两种赋值方式:使用=赋值和使用:赋值。二者的区别是,=赋值时,右侧是一个js的表达式。可以是函数定义、真值判断、字符串等等,:赋值时,紧跟:之后的所有内容,都被当做静态模板直接赋值给变量:

    // 模板字符串:
    {{##
      def.array = [1,2,3,4]
    #}}
    {{#def.array[0]}} 的值是 1
    
    {{##
      def.array2:[1,2,3,4]
    #}}
    {{#def.array2[0]}} 的值是 [  // array2是字符串的:”[1,2,3,4]”,所以第0位是 [ 

    编译时载入代码片段

    用法:{{# }}

    编译时载入代码片段、文件类似于宏编译,在compile阶段,将对应的变量或文件内容插入指定的位置传入的参数默认在对象def中。此外,通过{{## #}}定义的变量,也都是在def对象中的用法与{{}}基本一致,只是生效的阶段不同。

    编译时包含模板和编译时定义综合使用

    用法:{{# }}{{## #}}

    创建模板:

    <script type="text/x-dot-template" id="testHeaderTpl">
               <h2>标题:{{= it.title }}</h2>
    </script>
    
    <script type="text/x-dot-template" id="testPageTpl5">
        <h2>以下使用'testHeaderTpl'模板内容:</h2>
        {{#def.header }}
        {{= it.content }}
        {{#def.injectIntoHeader || '' }}
    </script>
    
    <script type="text/x-dot-template" id="testBodyTpl">
        <h2>工作内容:</h2>
        {{#def.body }}
        <h2>以下是编译时定义</h2>
        {{##def.injectIntoHeader:
            <div>截止时间:{{= it.dealine }} </div>
        #}}
    </script>

    使用:

    var work = {
        title: '完善项目一需求提取',
        content: '请研发部争取在月底前提取项目一需求',
        dealine: '2017-11-25 23:00'
    };
    var def = {
        header: $('#testHeaderTpl').text(),
        body: $('#testPageTpl5').text()
    };
    var tpl = doT.template($("#testBodyTpl").html(), null, def);
    var html = tpl(work);
    console.log(html);

    结果输出:

    <h2>工作内容:</h2>  <h2>以下使用'testHeaderTpl'模板内容:</h2>  <h2>标题:完善项目一需求提取</h2>  请研发部争取在月底前提取项目一需求  <div>截止时间:2017-11-25 23:00 </div>   <h2>以下是编译时定义</h2> 

    额外

    1、浏览器执行到

    <script id="encodetmpl" type="text/x-dot-template">
        ......
    </script>

       不会解析,因为浏览器“不认识它”,这个是在我们调用模版函数的时候才渲染执行的

    2、dot模版会被编译成函数

    3、根据前面所有的介绍我们可以知道,dot模版渲染分为两个阶段,编译和渲染,因此它的用法也要分为两个层面,一个是编译一个是渲染

       编译时使用dot.template(参数1,参数2,参数3),着重说参数3,参数3接受编译时传入的参数,默认存储在def对象中, 并且{{##  # }}、{{# }}在编译时使用,{{##  # }}定义的变量存储在def中

       渲染时使用dot.template()返回的函数,假如是temp(参数4),参数4接受渲染时传入的参数,默认存储在it对象中,并且{{= }}、{{ }}、{{? }}、{{~ }}、{{! }}在渲染时使用,{{ }}定义的变量存储在it中

    参考

    Github地址:https://github.com/olado/doT 

    精巧快速的 JavaScript 模板引擎,Node.js 和浏览器同样适用。

    doT 模板

     

     

  • 相关阅读:
    图形化代码阅读工具——Scitools Understand
    cocos studio UI 1.6.0.0 修改导出项目路径
    cocos2dx 中文路径编译错误记录
    利用特性区分查找方法,并通过反射调用方法
    WPF MVVM学习(二)
    wpf 控件模板、面板模板、数据模板
    blend 自定义控件
    wpf dataGrid样式
    blend 使用模板的几点说明
    WPF MVVM学习
  • 原文地址:https://www.cnblogs.com/kunmomo/p/11226890.html
Copyright © 2011-2022 走看看