php模板引擎技术简单实现


Posted in PHP onMarch 15, 2016

用了smarty,tp过后,也想了解了解其模板技术是怎么实现,于是写一个简单的模板类,大致就是读取模板文件->替换模板文件的内容->保存或者静态化 

tpl.class.php主要解析

assign 方法实现     

/**
     * 模板赋值操作
     * @param mixed $tpl_var 如果是字符串,就作为数组索引,如果是数组,就循环赋值
     * @param mixed $tpl_value 当$tpl_var为string时的值,默认为 null
     */
    public function assign($tpl_var,$tpl_value=null){
      if(is_array($tpl_var) && count($tpl_var) > 0){
        foreach ($tpl_var as $k => $v) {
          $this->tpl_vars[$k] = $v;
        }
      }elseif($tpl_var){
        $this->tpl_vars[$tpl_var] = $tpl_value;
      }
    }

fetch 方法实现

/**
      * 生成编译文件
      * @param string $tplFile 模板路径
      * @param string $comFile 编译路径
      * @return string
     */
    private function fetch($tplFile,$comFile){

      //判断编译文件是否需要重新生成(编译文件是否存在或者模板文件修改时间大于编译文件的修改时间)
      if(!file_exists($comFile) || filemtime($tplFile) > filemtime($comFile)){
        //编译,此处也可以使用ob_start()进行静态化
        $content = $this->tplReplace(file_get_contents($tplFile));
        file_put_contents($comFile, $content);
      }

    }

简单编译方法:按照规则进行正则替换

/**
     * 编译文件
     * @param string $content 待编译的内容
     * @return string
     */
    private function tplReplace($content){
      //转义左右定界符 正则表达式字符
      $left = preg_quote($this->left_delimiter,'/');
      $right = preg_quote($this->right_delimiter,'/');

      //简单模拟编译 变量
      $pattern = array(
          //例如{$test}
          '/'.$left.'\$([a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*)'.$right.'/i'
        );

      $replace = array(
          '<?php echo $this->tpl_vars[\'${1}\']; ?>'
        );

      //正则处理
      return preg_replace($pattern, $replace, $content);
    }

display = fetch+echo

/**
     * 输出内容
     * @param string $fileName 模板文件名
     */
    public function display($fileName){
      //模板路径
      $tplFile = $this->template_dir.'/'.$fileName;

      //判断模板是否存在
      if(!file_exists($tplFile)){
        $this->errorMessage = '模板文件不存在';
        return false;
      }

      //编译后的文件
      $comFile = $this->compile_dir.'/'.md5($fileName).'.php';

      $this->fetch($tplFile,$comFile);
      
 include $comFile;
    }

其他属性

//模板文件存放位置
    private $template_dir = 'templates'; 

    //编译文件存放位置
    private $compile_dir = 'compiles';

    //左定界符
    private $left_delimiter = '{';

    //右定界符 
    private $right_delimiter = '}'; 

    //内部临时变量,存储用户赋值
    private $tpl_vars = array();

    //错误信息
    private $errorMessage = '';

    /**
     * 修改类属性的值
     * @param array $configs 需要修改的相关属性及值
     * @return bool
     */
    public function setConfigs(array $configs){
      if(count($configs) > 0){
        foreach ($configs as $k => $v) {
          if(isset($this->$k))
            $this->$k = $v;
        }
        return true;
      }
      return false;
    }

测试

模板文件 testTpl.html

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>test_tpl_demo</title>
</head>
<body>
  {$name}:{$age}:{$message}
</body>
</html>
运行文件 test_tpl.php
<?php
  require 'Tpl.class.php';
  
  $tpl = new Tpl();
  $tplarr = array(
      'name'=>'waited',
      'age'=>'100'
    );
  $tpl->assign($tplarr);
  $tpl->assign('message','this is a demo');
  $tpl->display('testTpl.html');

?>

输出:waited:100:this is a demo

生成编译文件:972fa4d270e295005c36c1dbc7e6a56c.php

以上就是本文的全部内容,希望对大家的学习有所帮助。

PHP 相关文章推荐
动态网站web开发 PHP、ASP还是ASP.NET
Oct 09 PHP
Smarty安装配置方法
Apr 10 PHP
PHP 加密/解密函数 dencrypt(动态密文,带压缩功能,支持中文)
Jan 30 PHP
php上的memcache和memcached两个pecl库
Mar 29 PHP
PHP中防止SQL注入实现代码
Feb 19 PHP
php Calender(日历)代码分享
Jan 03 PHP
PHP中round()函数对浮点数进行四舍五入的方法
Nov 19 PHP
浅谈php中include文件变量作用域
Jun 18 PHP
关于php几种字符串连接的效率比较(详解)
Feb 22 PHP
PHP实现的AES加密、解密封装类与用法示例
Aug 02 PHP
Laravel timestamps 设置为unix时间戳的方法
Oct 11 PHP
laravel 解决后端无法获取到前端Post过来的值问题
Oct 22 PHP
9个比较实用的php代码片段
Mar 15 #PHP
Laravel使用Caching缓存数据减轻数据库查询压力的方法
Mar 15 #PHP
php图片添加文字水印实现代码
Mar 15 #PHP
PHP闭包函数传参及使用外部变量的方法
Mar 15 #PHP
Yii rules常用规则示例
Mar 15 #PHP
基于laravel制作APP接口(API)
Mar 15 #PHP
使用Composer安装Yii框架的方法
Mar 15 #PHP
You might like
PHP中的float类型使用说明
2010/07/27 PHP
php 传值赋值与引用赋值的区别
2010/12/29 PHP
PHP常用的排序和查找算法
2015/08/06 PHP
PHP7标量类型declare用法实例分析
2016/09/26 PHP
php成功操作redis cluster集群的实例教程
2019/01/13 PHP
ExtJS Grid使用SimpleStore、多选框的方法
2009/11/20 Javascript
jquery定时滑出可最小化的底部提示层特效代码
2013/10/02 Javascript
Jquery ajax执行顺序 返回自定义错误信息(实例讲解)
2013/11/06 Javascript
jquery操作HTML5 的data-*的用法实例分享
2014/08/17 Javascript
使用text方法获取Html元素文本信息示例
2014/09/01 Javascript
IE10中flexigrid无法显示数据的解决方法
2015/07/26 Javascript
jQuery中$.ajax()和$.getJson()同步处理详解
2015/08/12 Javascript
jQuery超简单选项卡完整实例
2015/09/26 Javascript
jquery实现列表上下移动功能
2016/02/25 Javascript
利用React-router+Webpack快速构建react程序
2016/10/27 Javascript
jquery 删除节点 添加节点 找兄弟节点的简单实现
2016/12/07 Javascript
Vue作用域插槽slot-scope实例代码
2018/09/05 Javascript
nestjs返回给前端数据格式的封装实现
2021/02/22 Javascript
用Python代码来绘制彭罗斯点阵的教程
2015/04/03 Python
Python简单实现TCP包发送十六进制数据的方法
2016/04/16 Python
python 巧用正则寻找字符串中的特定字符的位置方法
2018/05/02 Python
Python文本统计功能之西游记用字统计操作示例
2018/05/07 Python
mac下如何将python2.7改为python3
2018/07/13 Python
python实现微信防撤回神器
2019/04/29 Python
python3发送邮件需要经过代理服务器的示例代码
2019/07/25 Python
如何利用python web框架做文件流下载的实现示例
2020/06/02 Python
Python 内存管理机制全面分析
2021/01/16 Python
StubHub智利:购买和出售您的门票
2016/11/23 全球购物
蛋白质世界:Protein World
2017/11/23 全球购物
男女钓鱼靴和甲板鞋:XTRATUF
2021/01/09 全球购物
华为的Java面试题
2014/03/07 面试题
超市营业员岗位职责
2013/12/20 职场文书
办公室前台岗位职责
2014/01/04 职场文书
学校党委干部个人对照检查材料思想汇报
2014/10/09 职场文书
教你怎么用Python实现多路径迷宫
2021/04/29 Python
详细总结Python常见的安全问题
2021/05/21 Python