天空之城

您当前位置>>首页>>PHP学习>>PHP其它>>一个非常简单的PHP模板引擎

一个非常简单的PHP模板引擎

来源:天空之城 - My Site   时间:2014-04-04 19:29:07   编辑:administrator   阅读数:439

[导读]自己写的一个非常简单的模板引擎,这么多的注释现在看看还是比较清楚的,要不然很多以前自己写的代码乍一看想\\\"这是谁写的?\\\"再一看,这家伙到底想干嘛?这种感觉~~~~

MyTpl.rar简单的实现

<?php

class MyTpl {
    
    /*
     * 构造方法,创建对象时初始化成员属性
     * 参数template_dir:指定存放模板文件的位置目录
     * 参数compile_dir:指定存放变异后的模板文件位置
     */
    function __construct($template_dir='./templates/',$compile_dir='./templates_c/'){
        //将./templates/目录作为模板存放目录
        $this->template_dir=rtrim($template_dir,'/').'/';
        //初始化解析后的模板存放目录 
        $this->compile_dir=rtrim($compile_dir,'/').'/';
        //为成员属性tpl_vars赋值为空数组
        $this->tpl_vars=array();
    }
    
    /*
     * assign方法用来将值分配给模板中对应的变量
     * 参数tpl_val:需要一个字符串参数,要和模板中的变量名对应
     * 参数value:需要一个标量类型的值,用来分配给模板中变量的值
     */
    function assign($tpl_var,$value=null){
        //如果第一个参数$tpl_var不是一个空字符串
        if($tpl_var != ''){
            //将第二个参数提供的值添加到数组tpl_var中
            $this->tpl_vars[$tpl_var] = $value;
        }
    }
    
    /*
     * display方法加载指定目录下的模板文件,并将解析后的内容存放到另一个指定目录下的文件中
     * 参数fileNmae:提供模板文件的文件名
     */
    function display($fileName){
        //到指定的目录下寻找模版文件
        $tplFile=$this->template_dir.$fileName;
        //如果需要处理的模板文件不存在,返回false
        if(!file_exists($tplFile)){
            exit('模板文件'.$fileName.'不存在,请到模板目录下检查是否存在该模板文件');
            //return false;
        }
        //获取编译过的模板文件,该文件中的内容都是被替换过的
        $comFileName=$this->compile_dir."com_".basename($tplFile).'.php';
        //判断替换后的文件是否存在或是存在但有改动,都需要重新创建
        if(!file_exists($fileName) || filemtime($comFileName) < filetime($tplFile)){
            //调用内部替换模板方法
            $repContent=$this->tpl_replace(file_get_contents($tplFile));
        }
        //打开一个用来保存编译过的文件
        $handle=fopen($comFileName, 'w+');
        //向文件中写入内容
        fwrite($handle, $repContent);
        //关闭打开的文件
        fclose($handle);
        //echo $repContent;
        require_once($comFileName);
    }
    
    /*
     * tpl_replace方法,使用正则表达式将模板文件'<{ }>'中的语句替换为对应的值或PHP代码
     * 参数content:提供从模板文件中读入的全部内容字符
     */
    private function tpl_replace($content){
        //匹配模板中各种标识符的正则表达式的模式数组
        $pattern=array(
            //匹配模板中变量
            '/<\{\s*\$([a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*)\s*\}>/i',
            //匹配模板中if标识符
            '/<\{\s*if\s*(.+?)\s*\}>(.+?)<\{\s*\/if\s*\}>/ies',
            //匹配模板中elseif标识符
            '/<\{\s*else\s*if\s*(.+?)\s*\}>/ies',
            //匹配else标识符
            '/<\{\s*else\s*\}>/is',
            //用来匹配模板中的loop标识符,用来遍历数组中的值
            '/<\{\s*loop\s+\$(\S+)\s+\$([a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*)\s*\}>(.+?)<\{\s*\/loop\s*\}>/is',
            //用来匹配模板中的loop标识符,用来遍历数组中的键和值
            '/<\{\s*loop\s+\$(\S+)\s+\$([a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*)\s*=>\s*\$(\S+)\s*\}>(.+?)<\{\s*\/loop \s*\}>/is',
            //匹配include标识符
            '/<\{\s*include\s+[\"\']?(.+?)[\"\']?\s*\}>/ie'
        );
        //替换从模板中使用正则表达式匹配到的字符串属猪
        $replacement=array(
            //替换模板中的变量
            '<?php echo $this->tpl_vars["${1}"]; ?>',
            //替换模板中if字符串
            '$this->stripvtags(\'<?php if(${1}) { ?>\',\'${2}<?php } ?>\')',
            //替换unelseif字符串
            '$this->stripvtags(\'<?php } elseif(${1}) { ?>\',"")',
            //替换else字符串
            '<?php } else { ?>',
            //替换模板中loop标识符为foreach格式
            '<?php foreach($this->tpl_vars["${1}"] as $this->tpl_vars["${2}"]) { ?>${3}<?php } ?>',    
            '<?php foreach($this->tpl_vars["${1}"] as $this->tpl_vars["${2}"] => $this->tpl_vars["${3}"]) { ?>${4}<?php } ?>', 
            //替换include字符串
            'file_get_contents($this->template_dir."${1}")'
        );
        //使用正则替换函数处理
        $repContent=preg_replace($pattern,$replacement,$content);
        //$repContent=preg_replace('/<{\$([a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*)\s*}>/i','2',$content);
        //如果还有要替换的标识符,递归调用自己再次替换(主要用与调用其他模板时,其他模板中的标识符的替换)
        if(preg_match('/<\{([^(\}>)]{1,})\}>/',$repContent)){
            $repContent=$this->tpl_replace($repContent);
        }
        //返回替换后的字符串
        return $repContent;
        //return $content;
    }
    
    /*
     * stripvtags方法用来将条件语句中使用的变量替换为对应的值
     * 参数expr:提供模板中条件语句的开始标记
     * 参数statement:提供模板中条件语句的结束标记
     */
    private function stripvtags($expr,$statement=''){
        //匹配变量的正则
        $var_pattern='/\s*\$([a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*)\s*/is';
        //将变量替换为值
        $expr = preg_replace($var_pattern, '$this->tpl_vars["${1}"]', $expr);
        //将开始标记中的引号转义替换
        $expr = str_replace("\\\"", "\"", $expr);
        //替换语句体和结束标记中的也好
        $statement = str_replace("\\\"", "\"", $statement);
        //将处理后的条件语句相连后返回
        return $expr.$statement;
    }
    
}

一个非常简单的PHP模板引擎
原文地址:

上一篇:php备份恢复mysql数据库
下一篇:小记一二三

    just do it
    天空之城天空之城