前端模板引擎

从零开始:跟着 Art-template 学习前端模板引擎 Art-template 是一款基于 JavaScript 的快速、简单且功能丰富的模板引擎。在 HTML 文件中使用标签定义模板,或者将模板存储在外部文件中,并通过标签引入。 阅读详情

前言

正常渲染拿到数据后渲染,三步走:格式化数据、编译模板、渲染数据
如下例
在这里插入图片描述

  <!DOCTYPE html>
  <html lang="en">

  <head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>小米商城</title>
  </head>
  <style>
    * {
      margin: 0;
      padding: 0;
    }

    body,
    html {
      background-color: whitesmoke;
      font-size: 12px;
    }

    ul {
      list-style: none;
    }

    li {
      display: inline-block;
      padding: 0 10px;
      background: white;
    }

    h3 {
      text-align: center;
    }

    p {
      text-align: center;
    }

    .title {
      font-size: 16px;
      font-weight: 400;
      color: #333;
      line-height: 42px;
    }

    .desc {
      color: #b0b0b0;
    }

    .price {
      color: #444;
      line-height: 58px;
    }

    span {
      color: red;
    }
  </style>

  <body>
    <ul id="product-list">
      <!-- <li>
        <img src="img/1.webp" alt="">
        <h3 class="title">小米10青春版5G</h3>
        <p class="desc">50倍潜望式驾驶员/轻薄5G手机</p>
        <p class="price"><span>2099</span>元起</p>
      </li>
      <li>
        <img src="img/2.webp" alt="">
        <h3 class="title">小米10</h3>
        <p class="desc">骁龙865/1亿预期相机</p>
        <p class="price"><span>3799</span>元起</p>
      </li>
      <li>
        <img src="img/3.webp" alt="">
        <h3 class="title">Redmi K30 Pro</h3>
        <p class="desc">双模5G,骁龙865,投放全面屏</p>
        <p class="price"><span>2699</span>元起</p>
      </li>
      <li>
        <img src="img/4.webp" alt="">
        <h3 class="title">Redmi K30 Pro准版</h3>
        <p class="desc">双模5G,骁龙865,投放全面屏</p>
        <p class="price"><span>3499</span>元起</p>
      </li> -->
    </ul>


    <script>

      const productData = {
        title: '小米手机',
        list: [
          {
            productImgUrl: 'img/1.webp',
            productCUID: '088722478239',
            productTitle: 'PTD16-小米10青春版5G',
            productDesc: '50倍潜望式驾驶员/轻薄5G手机',
            productPrice: 209000,
            productCount: 999
          }, {
            productImgUrl: 'img/2.webp',
            productCUID: '088789478639',
            productTitle: 'PTD16-小米10', //
            productDesc: '骁龙865/1亿预期相机',
            productPrice: 379000, //3790.50   一般不会直接传代小数的数字,因为前端的计算是有问题的,一般数据是乘百发送,或者发送字符串自己转换
            productCount: 999  
          }, {
            productImgUrl: 'img/3.webp',
            productCUID: '088789478339',
            productTitle: 'PTD16-Redmi K30 Pro',
            productDesc: '双模5G,骁龙865,投放全面屏',
            productPrice: 269900,
            productCount: 0
          }, {
            productImgUrl: 'img/4.webp',
            productCUID: '088789471239',
            productTitle: 'PTD16-Redmi K30 Pro准版',
            productDesc: '双模5G,骁龙865,投放全面屏',
            productPrice: 349900,
            productCount: 99
          }]
      };

      let oUl = document.querySelector('#product-list');

      class TempRender {
        constructor(data = {}, parentEle = '') {
          this.parentEle = document.querySelector(parentEle);
          this.originalData = data;
          this.list = this.formatData(this.originalData.list)
          this.templateHtml = this.getTemplate(this.data);
          this.renderHtml();
        }

          //格式化数据
        formatData(list = []) {
          if (list.length === 0) {
            return [];
          }
          list = list.map(({ productImgUrl, productTitle, productDesc, productPrice }) => {
            productPrice = productPrice / 100;
            productTitle = productTitle.replace(/PTD16-/gi, '');

            productImgUrl = productImgUrl ?? 'img/1.webp'; //?? 是||的进阶版,如果没有值的话设置初始值
            productTitle = productTitle ?? '暂无信息';
            productDesc = productDesc ?? '暂无信息';
            productPrice = productPrice ?? '暂无信息';
            return {
              productImgUrl,
              productTitle,
              productDesc,
              productPrice
            }
          })
          return list;
        }
        //编译模板
      getTemplate() {    
        let template = '';
        for (let i = 0, len = this.list.length; i < len; i++) {
          let item = this.list[i];
          template += ` 
              <li>
                <img src="${item?.productImgUrl }" alt="">
                <h3 class="title">${item?.productTitle}</h3>
                <p class="desc">${item?.productDesc}</p>
                <p class="price"><span>${item?.productPrice}</span>元起</p>
              </li>
            `;
        }
        return template;
      }
      // 渲染数据
        renderHtml() {
          this.parentEle.innerHTML += this.templateHtml;
        }
      }

      new TempRender(productData, '#product-list');
    </script>
  </body>

  </html>

在该业务流程中模板是写死的,变量结构都是写死的,复用性为0,想着把模板当参数传进来,为了效率就借助模板引擎

模板引擎的使用

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>小米商城</title>
</head>
<style>
  * {
    margin: 0;
    padding: 0;
  }

  body,
  html {
    background-color: whitesmoke;
    font-size: 12px;
  }

  ul {
    list-style: none;
  }

  li {
    display: inline-block;
    padding: 0 10px;
    background: white;
  }

  h3 {
    text-align: center;
  }

  p {
    text-align: center;
  }

  .title {
    font-size: 16px;
    font-weight: 400;
    color: #333;
    line-height: 42px;
  }

  .desc {
    color: #b0b0b0;
  }

  .price {
    color: #444;
    line-height: 58px;
  }

  span {
    color: red;
  }
</style>

<body>
  <ul id="product-list">

  </ul>
  <script src="js/template-web.js"></script>
  <script type="text/template" id="testTemp">
    <h1>{{title}}</h1>
    {{each list}}
    <li>
      {{set price = $value.productPrice}}
      <img src="{{$value.productImgUrl}}" alt="">
      <h3 class="title">{{$value.productTitle}} {{$index}}</h3>
      <p class="desc">{{$value.productDesc}}</p>
      <p class="price"><span>{{price}}</span>元起</p>

      <!-- <i style="color:red">{{$value.productCount == 0?'无货':'有货'}}</i> -->
      {{if $value.productCount == 0}}
      <i style="color:red">无货</i>
      {{/if}}
      {{if $value.productCount != 0}}
      <i style="color:green">有货</i>
      {{/if}}
    </li>
   {{/each}}
  </script>
  <script>

    const productData = {
      title: '小米手机',
      list: [
        {
          productImgUrl: 'img/1.webp',
          productCUID: '088722478239',
          productTitle: 'PTD16-小米10青春版5G',
          productDesc: '50倍潜望式驾驶员/轻薄5G手机',
          productPrice: 209000,
          productCount: 999
        }, {
          productImgUrl: 'img/2.webp',
          productCUID: '088789478639',
          productTitle: 'PTD16-小米10', //
          productDesc: '骁龙865/1亿预期相机',
          productPrice: 379000, //3790.50   一般不会直接传代小数的数字,因为前端的计算是有问题的
          productCount: 999  //一般数据是乘百发送,或者发送字符串自己转换
        }, {
          productImgUrl: 'img/3.webp',
          productCUID: '088789478339',
          productTitle: 'PTD16-Redmi K30 Pro',
          productDesc: '双模5G,骁龙865,投放全面屏',
          productPrice: 269900,
          productCount: 0
        }, {
          productImgUrl: 'img/4.webp',
          productCUID: '088789471239',
          productTitle: 'PTD16-Redmi K30 Pro准版',
          productDesc: '双模5G,骁龙865,投放全面屏',
          productPrice: 349900,
          productCount: 99
        }]
    };

    let oUl = document.querySelector('#product-list');

    let templateHtml = template('testTemp', formatData(productData));

    oUl.innerHTML = templateHtml;

    function formatData(data) {
      let list = data.list;
      data.list = list.map(({ productImgUrl, productTitle, productDesc, productPrice, productCount }) => {
        productPrice = productPrice / 100;
        productTitle = productTitle.replace(/PTD16-/gi, '');

        productImgUrl = productImgUrl || 'img/1.webp';
        productTitle = productTitle ?? '暂无信息';
        productDesc = productDesc || '暂无信息';
        productPrice = productPrice || '暂无信息';
        return {
          productImgUrl,
          productTitle,
          productDesc,
          productPrice,
          productCount
        }
      })
      return data;
    }
  </script>
</body>

</html>

常见模板工具

jade.js doT.js tpl.js art-template.js handlebars

模板引擎工具的主要用法,就是给数据给模板,然后返回结果.

学习模板引擎主要学习模板引擎的语法

art-template:号称是性能最快的模板引擎

地址: http://aui.github.io/art-template/

handlebars:

地址: https://handlebarsjs.com/

模板语法

模板引擎本质上是通过特定标识符号和语句嵌入HTML文本中 , 通过输入数据 的到 嵌套好数据的HTML文本内容用于生产页面 数据+模板 = 结构内容 , 其中模板语法为核心 下面用art-template语法演示

<ul class="clearfix">
    {{each target}}
        <li> 序号: {{$index}} 姓名 :{{$value.name}} 年龄: {{$value.age}}</li>
	{{/each}}
</ul>

渲染方法

模板工具会提供模板渲染方法, 调用传参 数据 与 模板 返回生成的结构内容结果字符串

 let html = template('testTemp', { target: [{ name: '赫赫', age: 11 }, { name: '豆丁', age: 6 }, { name: '西瓜', age: 5 }, { name: '莉莉莎', age: 8 }, { name: '杰克', age: 22 }, { name: '奥米拉', age: 3 }] })

document.body.innerHTML = html;

效果

在这里插入图片描述

在这里插入图片描述

原生模板实现

原理就是正则替换内容

原理步骤:

  1. 正则替换 规定标识符内容

    普通标签

    <%= %> 内容替换成变量的值

    <% %> 内容替换成js代码

  2. 动态生成渲染函数 new Function(函数字符串)

  3. 通过正则格式化模板内容

  4. 拼接返回格式化模板内容代码字符串

<!DOCTYPE html>
<html lang="zh-cn">

<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>商品</title>
</head>

<body>
  <script type="text/template" id="temp">
    <h2><%= data.title %></h2>
    <ul>
      <% for(let i=0; i < data.list.length; i++) { %>
        <li data-index=<%=i%>><%= data.list[i] %>
          <% if(data.list[i].length>3) {%>
            <%= '哈哈哈' %>
          <% } %> 
        </li>
      <% } %>
    </ul>
  </script>
  <script>
    function getTempScript(id) {
      let script = document.querySelector(`#${id}[type="text/template"]`); 
      return `${script.innerHTML}`
    }

    function compile(id) {
      let template = getTempScript(id);
      let evalExp = /<%=(.+?)%>/g,
        expr = /<%([\s\S]+?)%>/g;
      template = template.replace(evalExp, '`) \n echo($1) \n echo(`').replace(expr, '`) \n $1 \n echo(`');
      template = 'echo(`'+template +'`)';

      let funcStr = `
        let html = '';
        function echo(content) {
          html += content;
        }
        ${template}
        return html;
      `
      return funcStr;
    }

    let funStr = compile('temp');
    let comp1 = new Function('data',funStr);
    document.body.innerHTML += comp1({ title: '标题', list: ['糖醋鱼', '香辣蟹', '红烧排骨'] })
  </script>
</body>

</html>
HTML5 前端模板引擎的使用 前端模板引擎是现代Web开发中不可或缺的工具,它通过分离HTML结构和业务数据,极大地提高了开发效率和代码可维护性。本文旨在全面介绍HTML5环境下主流前端模板引擎的工作原理、使用方法和最佳实践。本文将首先介绍模板引擎的基本概念,然后深入分析几种主流模板引擎的技术细节,接着通过实际案例展示其应用,最后讨论性能优化和安全性等高级话题。模板引擎:一种将模板和数据结合生成最终HTML的工具数据绑定:将数据模型与视图自动同步的机制模板语法:模板引擎特有的标记语言,用于控制逻辑和插入数据发展趋势。 阅读详情

相关推荐

初识前端模板引擎jade

1.什么是模板引擎?(我的理解)模板引擎:为了使用户界面与业务数据(内容)分离而产生的,根据特定的规则生成特定文档,各个领域都可以有自己的模板引擎。 web模板引擎:最终生成的文档是HTML类型。 而这种规则有五花八门,各种各样的规则就是不同的模板引擎。 本文主要讲jade2.jade的安装(windows)jade是基于nodeJs的,所以首先要安装运行环境 nodeJs,包管理工具npm

xi_2130的博客 2078

前端模板引擎使用

前端模板引擎的使用

weixin_45268910的博客 1413

前端模板引擎Handlebars理解与举例 jQuery

Handlebars是一种流行的前端模板引擎,它提供了一种简洁而灵活的方式来生成HTML模板。它基于JavaScript语言,并与许多流行的JavaScript库和框架集成,其中包括jQuery。Handlebars的设计目标是将数据和模板分离,使开发人员能够更轻松地管理和更新页面内容。它通过使用占位符和表达式来定义模板,然后将数据填充到模板中生成最终的HTML输出。在本文中,我们将通过使用jQuery库来演示Handlebars的用法。首先,确保已经引入了jQuery和Handlebars的库文件。

WfTest的博客 445

template模板引擎学习

template引擎模板学习

FM11101001的博客 1427

HTML5 前端模板引擎的使用教程

本文旨在为前端开发者提供一份全面的HTML5模板引擎使用指南。我们将覆盖模板引擎的基本概念、工作原理、主流实现以及在实际项目中的应用技巧。本文不仅适合初学者快速入门,也为有经验的开发者提供深入的技术细节和最佳实践。文章首先介绍模板引擎的基本概念,然后深入探讨三种主流模板引擎的具体实现,接着通过实际项目演示它们的应用,最后讨论性能优化和未来发展趋势。模板引擎:一种将模板和数据结合生成最终HTML的技术数据绑定:将数据模型与视图元素关联的过程模板语法:模板引擎特有的标记语言,用于定义数据插入点和逻辑控制。

AI架构全栈开发实战笔记 966

实现简单的前端模板引擎

然而,通过上述的代码,我们可以理解模板引擎的基本工作原理,并可以根据需要进行扩展和改进。在前端开发中,模板引擎是一个常用的工具,它能够将数据和HTML模板结合起来,生成最终的HTML内容。现在,当我们运行这段代码时,模板引擎将会将占位符替换为实际的值,并将渲染后的HTML内容显示在页面上。首先,让我们定义一个简单的HTML模板,其中包含一些占位符,我们将在渲染过程中替换这些占位符。的元素的innerHTML,这是我们之前定义的HTML模板。以上这段HTML代码中,方括号中的内容即为我们的占位符。

IOWEL的博客 130

模板引擎?看这一篇就懂了,前端插件化开发指南

我可以将最近整理的前端面试题分享出来,其中包含HTML、CSS、JavaScript、服务端与网络、Vue、浏览器、数据结构与算法等等,还在持续整理更新中,希望大家都能找到心仪的工作。CodeChina开源项目:【大厂前端面试题解析+核心总结学习笔记+真实项目实战+最新讲解视频】)**

m0_61408947的博客 1054

实现数据渲染的简易前端模板引擎

在现代前端开发中,模板引擎(Template Engine)是一个不可或缺的工具,它负责将页面的结构(HTML)与数据(JavaScript对象)分离,提供了一种高效的模板渲染机制。模板引擎的作用不仅仅在于快速生成静态页面,它还能够帮助开发人员避免在JavaScript代码中进行复杂而繁琐的字符串操作,从而提高代码的可读性和可维护性。通过模板引擎,开发者能够将页面的展示逻辑与业务逻辑清晰地分离,这不仅简化了开发流程,还极大地增强了团队协作的效率。

weixin_31720909的博客 1076

前端数据模板引擎

前端数据模板引擎的总结 2016-09-02 前端大全 作者:jingwhale 链接:http://www.cnblogs.com/jingwhale/p/5811800.html 模板的工作原理可以简单地分成两个步骤:模板解析(翻译)和数据渲染。这两个步骤可分别部署在前端或后端来执行。如果放在后端执行,则是像Smarty,Fr

chanda_yang的博客 1804

从SIGGRAPH审稿人视角看:什么样的TOG论文更容易被接收?

本文从SIGGRAPH审稿人视角深入解析TOG论文的审稿标准与投稿策略,揭示如何提升论文接收概率。重点探讨创新性、技术深度、实验验证等核心评分维度,并提供写作技巧与审稿意见应对策略,帮助研究者优化ACM Transactions on Graphics投稿质量。

weixin_33721344的博客 108

DINOv2 基于自定义数据集进行图片分类预测

(前提是安装好pytorch)1. pip安装2. 下载dinov2提供的预训练模型,需要自行前往网站上查找dinov2模型进行下载。模型需要下载三个文件:下载完成后将上述三个文件放置在本地一个名为dinov2_base的文件夹中即可。

sinat_34770838的博客 6665

java 前端模板_前端模板引擎入门

模板引擎模板引擎 起到 数据和视图分离的作用, 模板对应视图, 关注如何展示数据, 在模板外头准备的数据, 关注那些数据可以被展示。后端模板引擎freemarker如下介绍, java后台的模板引擎, freemark介绍,其图能很好标明这种关系。Apache FreeMarker is a template engine: a Java library to generate text out...

weixin_29089057的博客 825

mongoDB 数据莫名其妙的没了

问题 之前没有接触过mongoDB,然后接手一个项目使用的是MongoDB,我就跟着网上的教程搭建一个MongoDB的服务,并运行起来。 一开始没有啥问题,成功的把服务与MongoDB都启动以来,运行也没有问题。但是过了几天,我再次打开时发现,以前的数据神奇的消失了。我还在想,是有什么定时清除的么,还是什么原因导致崩了然后数据就被清理了。 查找原因 第一次遇到我没有在意,重启了一下MongoDB,...

技术熊的博客小窝 1万+

html jquery 模板引擎,jquery template.js前端模板引擎

作为现代应用,ajax的大量使用,使得前端工程师们日常的开发少不了拼装模板,渲染模板在刚有web的时候,前端与后端的交互,非常直白,浏览器端发出URL,后端返回一张拼好了的HTML串。浏览器对其进行渲染。html中可能会混有一些php(或者php中混有一些html)。在服务端将数据与模板进行拼装,生成要返回浏览器端的html串。这与我们现在做一个普通网页没什么区别。只不过现在,我们更常使用模板技术...

weixin_27719109的博客 724

Vue3+Vite+Electron桌面应用开发:从零到打包的完整避坑指南

本文是一份详尽的Vue3+Vite+Electron桌面应用开发实战指南。文章从项目初始化、环境配置、主进程构建、Vite深度优化,到最终的打包配置与优化,系统性地讲解了使用现代前端技术栈开发跨平台桌面应用的完整流程,并重点分享了开发与打包过程中的常见“坑点”与解决方案,旨在帮助开发者高效构建稳定可交付的桌面端应用。

hh234的博客 107

5060TI显卡深度学习环境搭建:CUDA12.8与CUDNN9.8.0的完美搭配

本文详细介绍了在Win10系统下为5060TI显卡搭建深度学习环境的最佳实践,重点配置CUDA12.8与CUDNN9.8.0的完美组合。通过优化OpenCV编译选项和YOLOv5环境设置,显著提升模型训练和推理效率,帮助开发者充分发挥5060TI显卡的性能潜力。

weixin_29065791的博客 488

【前端进阶】10 掌握前端框架模板引擎的实现原理

模板引擎会根据AST对象生成最终片段和逻辑,在这个过程中会通过添加特殊标识(例如元素id、属性标记等)的方式来标记DOM节点,配合DOM元素选择方式、事件监听方式等,在需要更新的时候,可以快速定位到该DOM节点,并进行节点内容更新,从未实现页面内容的更新

G.E.M.千百度的博客 472

顶刊《会计研究》数据复现|最新上市公司数智化数据

本文基于Python文本分析方法构建了中国A股上市公司数智化指标(1991-2024),通过识别年报中的"机器学习""智能医疗"等关键词,量化企业数字化与智能化融合程度。研究发现数智化企业更倾向于非正式渠道的定性披露以规避风险,该指标为监管完善信披规则提供了参考。研究还揭示了数智化对企业信息披露策略的转变,并提出了未来研究方向,包括数智化对绿色创新、ESG表现等影响机制。数据覆盖非金融类上市公司,采用文本挖掘技术构建结构化指标,为相关领域研究提供了微观基础。

PPdata_Academy的博客 1487

如何选择 Web 前端模板引擎?

Web 模板就在那里模板引擎负责组装数据,以另外一种形式或外观展现数据。 浏览器中的页面是 Web 模板引擎最终的展现。无论你是否直接使用模板引擎,Web 模板一直都在,不在前端就在后端,它的出现甚至可以追溯到超文本标记语言 HTML 标准正式确立之前。服务器端的模板引擎我所知道最早的 Web 模板引擎是 PHP,它正式诞生于 1997 年,工作在服务器端。让我们看看 PHP 官方的 intro-...

jgh113的博客 1万+

[深入研究4G/5G/6G专题-31]: 5G NR开机流程5.2 - UE Attach流程(Registeration Request/Accept/Complete)

目录前言:前置条件:第1章 5G NR UE attach流程(从UE log的视角看)1.0 NAS消息解析器1.1 消息交互流程1.2 UE Registeration Request消息(AMF->基站->UE)1.3 AMF Registeration Accept消息(AMF->基站->UE)1.4 UE Register complete消息(UE->基站->AMF)第2章 UE Register...............

文火冰糖(王文兵)的博客 7万+

生成对抗网络(GAN)在数据增强中的应用【附核心实战代码】

生成对抗网络(GAN)由Ian Goodfellow等人在2014年提出。它包含两个主要的部分:生成器(Generator)和判别器(Discriminator)。生成器负责生成假数据,而判别器则用于区分输入的数据是真实的还是由生成器生成的。通过这种对抗过程,生成器不断优化自己,生成越来越真实的样本。最终,生成器生成的样本几乎无法被判别器区分与真实数据。

一键难忘的博客 3120

前端与后端的模板引擎

模板引擎 模板引擎 起到 数据和视图分离的作用, 模板对应视图, 关注如何展示数据, 在模板外头准备的数据, 关注那些数据可以被展示。 &nbsp; 后端模板引擎 freemarker 如下介绍,&nbsp; java后台的模板引擎, freemark介绍,其图能很好标明这种关系。 htt...

随风飘扬 4404

RU DOS版、EFI版32bit/64bit BIOS常用工具

DOS版、EFI版的RU工具,可用来查看IO、MEM、PCI、SMBIOS等资源。亲测在EFI SHELL下可用。

TopLevel:革新前端开发的模板引擎

TopLevel:革新前端开发的模板引擎 项目介绍 TopLevel 是一款创新的前端模板引擎,它允许开发者在 HTML、CSS 和 JavaScript 的顶层进行模板化处理。通过 TopLevel,开发者可以实现动态加载资源、条件渲染以及循环生成内容等功能,而无需等待页面加载后再进行 DOM 操作。TopLevel 的核心优势在于其能够在浏览器解析 HTML 之前,根据条件动态生成内容,从而提...

gitblog_00485的博客 1077

WINCC7.3破解文件

WINCC7.3硬件够破解文件,有需要的下载!WINCC7.3硬件够破解文件,有需要的下载!

Probability and Statistics - 4th edition

Probability and Statistics - 4th edition

上一篇: HTML + CSS编程规范
下一篇: 移动端适配
喵_美
博客等级 码龄11年 445粉丝 102原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值