演示链接:查看演示

dedecms模板原理,实现标签替换

文章介绍

 

 

<?php

require_once(dirname(__FILE__)."/../include/common.inc.php");

//1. 读入模板文件

$str = file_get_contents('test.html');

//2. 使用正则匹配出页面中所有的 arclist 标签

$re = '/{dede:arclist(.*)}(.*){\\/dede:arclist}/Us';

// 执行正则匹配

// 第一个参数:正则 

// 第二个参数:字符串

// 第三个参数:这个函数会把匹配到的结果放第三个参数的数组中

// 返回值:匹配到的个数

preg_match_all($re, $str, $a);

//3. 循环每一个匹配到的arclist标签进行处理 

foreach ($a[0] as $k => $v)

{

    /****************处理标签1.根据标签上的属性构造一个SQL语句 **************/

    // 取出标签相应的属性字符串并把属性转化成一个数组,如 row="10" channelid="17" addfields="pffz,pfrs,yuyan" orderby="id" orderway="desc"

    $attrArr = strToArray($a[1][$k]);

    // 根据构造构造SQL语句上的变量

    if(isset($attrArr['row']))

        $limit = $attrArr['row'];

    else

        $limit = 20;

    if(isset($attrArr['orderby']))

        $orderby = $attrArr['orderby'];

    else

        $orderby = 'id';

    if(isset($attrArr['orderway']))

        $orderway = $attrArr['orderway'];

    else

        $orderway = 'desc';

    // 连表的属性

    if(isset($attrArr['channelid']))

        $leftJoin = ' LEFT JOIN dede_addon17 b ON a.id=b.aid ';

    else

        $leftJoin = '';

    if(isset($attrArr['addfields']))

        $extraFields = ','.$attrArr['addfields'];

    else

        $extraFields = '';

    // 解析属性

    

    $sql = "SELECT a.*$extraFields

            FROM dede_archives a $leftJoin

             ORDER BY $orderby $orderway

             LIMIT $limit";

    $dsql->Execute('me', $sql);

    $html = '';

    // 每个arclist对应的多个数据

    while($row = $dsql->GetArray('me'))

    {

        // 重置模板字符串,不要在原模板上面进行替换

        $_tep = $a[2][$k];

        /**

        <li>

            <img src="[field:litpic/]" /><br />

             标题:[field:title/]<br />

             评分分值:[field:pffz    function="getSmallStar(@me)"/]<br />

             评分人数:[field:pfrs/]<br />

             语言:[field:yuyan/]

        </li>

    **/

        // 把字符串中的[field:xxxx/]替换成$row['xxxx']变量。

        $_re = '/\\[field:(\\w+)(\\s+function=("|\\')(\\w+)\\((.*)\\)\\3)?\\/\\]/U';

        preg_match_all($_re, $_tep, $_a);

        /**

array

  0 => 

    array

      0 => string '[field:litpic/]' (length=15)

      1 => string '[field:title/]' (length=14)

      2 => string '[field:pffz/]' (length=13)

      3 => string '[field:pfrs/]' (length=13)

      4 => string '[field:yuyan/]' (length=14)

  1 => 

    array

      0 => string 'litpic' (length=6)

      1 => string 'title' (length=5)

      2 => string 'pffz' (length=4)

      3 => string 'pfrs' (length=4)

      4 => string 'yuyan' (length=5)

     */

     // 再循环每一条 记录中的每个字段的值

        foreach($_a[0] as $_k => $_v)

        {

            if($_a[4][$_k] == '')

                // 把[field:xxx/]字符串替换成相应的$row[xxx]变量

                $_tep = str_replace($_v, $row[$_a[1][$_k]], $_tep);

            else

            {

                // 如果参数中有@me就把@me替换成当前这个字段的数据库中的值

                $_a[5][$_k] = str_replace('@me', $row[$_a[1][$_k]], $_a[5][$_k]);

                // 如果有函数就调用函数

                $funStr = '$_val='.$_a[4][$_k]."({$_a[5][$_k]});";

                eval($funStr);

                $_tep = str_replace($_v, $_val, $_tep);

            }

        }

        $html .= $_tep;

    }

    // 到这arclist标签就已经都解析成了相应的数据,把整个arclist标签替换成解析之后的数据,$html就是

arclist最终解析完成之后的HTML的字符串

    $str = str_replace($v, $html, $str);

    // 一个arclist就解析完成了

}

// 把解析好的字符串生成前台静态页

file_put_contents('./index.html', $str);

echo '解析成功!';

 

 

 

 

function strToArray($str)

{

    $str = trim($str);

    // 从属性字符串中匹配出每个属性,格式如:row="10" channelid="17" addfields="pffz,pfrs,yuyan" orderby="id" orderway="desc"

    $re = '/[a-z]+\\s*=\\s*("|\\').*\\1/U';

    $data = array();

    preg_match_all($re, $str, $a);

    foreach ($a[0] as $k => $v)

    {

        $_a = explode('=', $v);

        // 去掉属性值左右的引号,属性左右的引号是单引号还是双引号不能确定所以需要使用$a[1][$k]变量来代替,这个变量是正则中

的第一个括号的内容,匹配的就是引号

        $_a[1] = ltrim($_a[1], $a[1][$k]);

        $_a[1] = rtrim($_a[1], $a[1][$k]);

        $data[$_a[0]] = $_a[1];

    }

    return $data;

 

 

}

 

 

 

 

<?php

require_once(dirname(__FILE__)."/../include/common.inc.php");

//1. 读入模板文件

$str = file_get_contents('test.html');

//2. 使用正则匹配出页面中所有的 arclist 标签

$re = '/{dede:arclist(.*)}(.*){\\/dede:arclist}/Us';

// 执行正则匹配

// 第一个参数:正则 

// 第二个参数:字符串

// 第三个参数:这个函数会把匹配到的结果放第三个参数的数组中

// 返回值:匹配到的个数

preg_match_all($re, $str, $a);

//3. 循环每一个匹配到的arclist标签进行处理 

foreach ($a[0] as $k => $v)

{

    /****************处理标签1.根据标签上的属性构造一个SQL语句 **************/

    // 取出标签相应的属性字符串并把属性转化成一个数组,如 row="10" channelid="17" addfields="pffz,pfrs,yuyan" orderby="id" orderway="desc"

    $attrArr = strToArray($a[1][$k]);

    // 根据构造构造SQL语句上的变量

    if(isset($attrArr['row']))

        $limit = $attrArr['row'];

    else

        $limit = 20;

    if(isset($attrArr['orderby']))

        $orderby = $attrArr['orderby'];

    else

        $orderby = 'id';

    if(isset($attrArr['orderway']))

        $orderway = $attrArr['orderway'];

    else

        $orderway = 'desc';

    // 连表的属性

    if(isset($attrArr['channelid']))

        $leftJoin = ' LEFT JOIN dede_addon17 b ON a.id=b.aid ';

    else

        $leftJoin = '';

    if(isset($attrArr['addfields']))

        $extraFields = ','.$attrArr['addfields'];

    else

        $extraFields = '';

    // 解析属性

    

    $sql = "SELECT a.*$extraFields

            FROM dede_archives a $leftJoin

             ORDER BY $orderby $orderway

             LIMIT $limit";

    $dsql->Execute('me', $sql);

    $html = '';

    // 每个arclist对应的多个数据

    while($row = $dsql->GetArray('me'))

    {

        // 重置模板字符串,不要在原模板上面进行替换

        $_tep = $a[2][$k];

        /**

        <li>

            <img src="[field:litpic/]" /><br />

             标题:[field:title/]<br />

             评分分值:[field:pffz    function="getSmallStar(@me)"/]<br />

             评分人数:[field:pfrs/]<br />

             语言:[field:yuyan/]

        </li>

    **/

        // 把字符串中的[field:xxxx/]替换成$row['xxxx']变量。

        $_re = '/\\[field:(\\w+)(\\s+function=("|\\')(\\w+)\\((.*)\\)\\3)?\\/\\]/U';

        preg_match_all($_re, $_tep, $_a);

        /**

array

  0 => 

    array

      0 => string '[field:litpic/]' (length=15)

      1 => string '[field:title/]' (length=14)

      2 => string '[field:pffz/]' (length=13)

      3 => string '[field:pfrs/]' (length=13)

      4 => string '[field:yuyan/]' (length=14)

  1 => 

    array

      0 => string 'litpic' (length=6)

      1 => string 'title' (length=5)

      2 => string 'pffz' (length=4)

      3 => string 'pfrs' (length=4)

      4 => string 'yuyan' (length=5)

     */

     // 再循环每一条 记录中的每个字段的值

        foreach($_a[0] as $_k => $_v)

        {

            if($_a[4][$_k] == '')

                // 把[field:xxx/]字符串替换成相应的$row[xxx]变量

                $_tep = str_replace($_v, $row[$_a[1][$_k]], $_tep);

            else

            {

                // 如果参数中有@me就把@me替换成当前这个字段的数据库中的值

                $_a[5][$_k] = str_replace('@me', $row[$_a[1][$_k]], $_a[5][$_k]);

                // 如果有函数就调用函数

                $funStr = '$_val='.$_a[4][$_k]."({$_a[5][$_k]});";

                eval($funStr);

                $_tep = str_replace($_v, $_val, $_tep);

            }

        }

        $html .= $_tep;

    }

    // 到这arclist标签就已经都解析成了相应的数据,把整个arclist标签替换成解析之后的数据,$html就是

arclist最终解析完成之后的HTML的字符串

    $str = str_replace($v, $html, $str);

    // 一个arclist就解析完成了

}

// 把解析好的字符串生成前台静态页

file_put_contents('./index.html', $str);

echo '解析成功!';

 

 

 

 

function strToArray($str)

{

    $str = trim($str);

    // 从属性字符串中匹配出每个属性,格式如:row="10" channelid="17" addfields="pffz,pfrs,yuyan" orderby="id" orderway="desc"

    $re = '/[a-z]+\\s*=\\s*("|\\').*\\1/U';

    $data = array();

    preg_match_all($re, $str, $a);

    foreach ($a[0] as $k => $v)

    {

        $_a = explode('=', $v);

        // 去掉属性值左右的引号,属性左右的引号是单引号还是双引号不能确定所以需要使用$a[1][$k]变量来代替,这个变量是正则中

的第一个括号的内容,匹配的就是引号

        $_a[1] = ltrim($_a[1], $a[1][$k]);

        $_a[1] = rtrim($_a[1], $a[1][$k]);

        $data[$_a[0]] = $_a[1];

    }

    return $data;

 

 

}

 

 

<?php

require_once(dirname(__FILE__)."/../include/common.inc.php");

//1. 读入模板文件

$str = file_get_contents('test.html');

//2. 使用正则匹配出页面中所有的 arclist 标签

$re = '/{dede:arclist(.*)}(.*){\\/dede:arclist}/Us';

// 执行正则匹配

// 第一个参数:正则 

// 第二个参数:字符串

// 第三个参数:这个函数会把匹配到的结果放第三个参数的数组中

// 返回值:匹配到的个数

preg_match_all($re, $str, $a);

//3. 循环每一个匹配到的arclist标签进行处理 

foreach ($a[0] as $k => $v)

{

    /****************处理标签1.根据标签上的属性构造一个SQL语句 **************/

    // 取出标签相应的属性字符串并把属性转化成一个数组,如 row="10" channelid="17" addfields="pffz,pfrs,yuyan" orderby="id" orderway="desc"

    $attrArr = strToArray($a[1][$k]);

    // 根据构造构造SQL语句上的变量

    if(isset($attrArr['row']))

        $limit = $attrArr['row'];

    else

        $limit = 20;

    if(isset($attrArr['orderby']))

        $orderby = $attrArr['orderby'];

    else

        $orderby = 'id';

    if(isset($attrArr['orderway']))

        $orderway = $attrArr['orderway'];

    else

        $orderway = 'desc';

    // 连表的属性

    if(isset($attrArr['channelid']))

        $leftJoin = ' LEFT JOIN dede_addon17 b ON a.id=b.aid ';

    else

        $leftJoin = '';

    if(isset($attrArr['addfields']))

        $extraFields = ','.$attrArr['addfields'];

    else

        $extraFields = '';

    // 解析属性

    

    $sql = "SELECT a.*$extraFields

            FROM dede_archives a $leftJoin

             ORDER BY $orderby $orderway

             LIMIT $limit";

    $dsql->Execute('me', $sql);

    $html = '';

    // 每个arclist对应的多个数据

    while($row = $dsql->GetArray('me'))

    {

        // 重置模板字符串,不要在原模板上面进行替换

        $_tep = $a[2][$k];

        /**

        <li>

            <img src="[field:litpic/]" /><br />

             标题:[field:title/]<br />

             评分分值:[field:pffz    function="getSmallStar(@me)"/]<br />

             评分人数:[field:pfrs/]<br />

             语言:[field:yuyan/]

        </li>

    **/

        // 把字符串中的[field:xxxx/]替换成$row['xxxx']变量。

        $_re = '/\\[field:(\\w+)(\\s+function=("|\\')(\\w+)\\((.*)\\)\\3)?\\/\\]/U';

        preg_match_all($_re, $_tep, $_a);

 

    /**

array

  0 => 

    array

      0 => string '[field:litpic/]' (length=15)

      1 => string '[field:title/]' (length=14)

      2 => string '[field:pffz/]' (length=13)

      3 => string '[field:pfrs/]' (length=13)

      4 => string '[field:yuyan/]' (length=14)

  1 => 

    array

      0 => string 'litpic' (length=6)

      1 => string 'title' (length=5)

      2 => string 'pffz' (length=4)

      3 => string 'pfrs' (length=4)

      4 => string 'yuyan' (length=5)

     */

     // 再循环每一条 记录中的每个字段的值

        foreach($_a[0] as $_k => $_v)

        {

            if($_a[4][$_k] == '')

                // 把[field:xxx/]字符串替换成相应的$row[xxx]变量

                $_tep = str_replace($_v, $row[$_a[1][$_k]], $_tep);

            else

            {

                // 如果参数中有@me就把@me替换成当前这个字段的数据库中的值

                $_a[5][$_k] = str_replace('@me', $row[$_a[1][$_k]], $_a[5][$_k]);

                // 如果有函数就调用函数

                $funStr = '$_val='.$_a[4][$_k]."({$_a[5][$_k]});";

                eval($funStr);

                $_tep = str_replace($_v, $_val, $_tep);

            }

        }

        $html .= $_tep;

    }

    // 到这arclist标签就已经都解析成了相应的数据,把整个arclist标签替换成解析之后的数据,$html就是

arclist最终解析完成之后的HTML的字符串

    $str = str_replace($v, $html, $str);

    // 一个arclist就解析完成了

}

// 把解析好的字符串生成前台静态页

file_put_contents('./index.html', $str);

echo '解析成功!';

 

 

 

 

function strToArray($str)

{

    $str = trim($str);

    // 从属性字符串中匹配出每个属性,格式如:row="10" channelid="17" addfields="pffz,pfrs,yuyan" orderby="id" orderway="desc"

    $re = '/[a-z]+\\s*=\\s*("|\\').*\\1/U';

    $data = array();

    preg_match_all($re, $str, $a);

    foreach ($a[0] as $k => $v)

    {

        $_a = explode('=', $v);

        // 去掉属性值左右的引号,属性左右的引号是单引号还是双引号不能确定所以需要使用$a[1][$k]变量来代替,这个变量是正则中

的第一个括号的内容,匹配的就是引号

        $_a[1] = ltrim($_a[1], $a[1][$k]);

        $_a[1] = rtrim($_a[1], $a[1][$k]);

        $data[$_a[0]] = $_a[1];

    }

    return $data;

 

 

}
 

THE END
喜欢就支持一下吧
点赞0 分享