《Php笔记3.5》ThinkPHP 模板(下)——标签,布局

模板作为 MVC 中 View 的高级应用,提供了丰富的视图渲染功能,对于项目实战来说,掌握上部分讲解的变量输出、函数和模板替换规则的知识是远远不够的,我们可以利用 ThinkPHP 内置的标签,甚至自定义标签库来简化模板,通过模板布局和继承机制,打造目录结构直观、便于维护的视图层,模板知识是开发中大型应用的基础,在后续的实战课程中会大量使用本课程的知识

 

ThinkPHP 模板:模板标签

本课时讲解 ThinkPHP 模板内置标签的用法,以及如何关闭局部模板标签的解析,达到原样输出的目的。

 

volist标签,empty标签,compare标签,lt等比较标签,if/else标签,模板替换

数据获取,function.php:

 1 /*
 2  * 获取球星测试数据
 3  * @return array
 4  */
 5 function get_user_friends(){
 6     $friends = array(
 7         array(
 8             'username' => '科比',
 9             'avatar' => '1.jpg',
10             'age' => 37,
11             'tags' => array('81分','总冠军','美如画')
12         ),
13         array(
14             'username' => '詹姆斯',
15             'avatar' => '2.jpg',
16             'age' => 30,
17             'tags' => array('控场','暴力','全面')
18         ),
19         array(
20             'username' => '库里',
21             'avatar' => '3.jpg',
22             'age' => 26,
23             'tags' => array('3分','运球','总冠军')
24         ),
25         array(
26             'username' => '莫里斯',
27             'avatar' => null,
28             'age' => 17,
29             'tags' => array('球员','后卫','NBA')
30         ),
31     );
32 
33     return $friends;
34 }

控制器 indexController.class.php:

$this->assign('friends', get_user_friends());

给头像图片设置一个目录在/Public/avatar,设置配置项config:

'TMPL_PARSE_STRING'    =>    array(
    '__AVATAR__'=>'/Uploads/avatar'
)

index.html 模板文件:

 1 <!-- 球星列表 -->
 2 <div class="panel panel-default">
 3     <div class="panel-heading">
 4         <h3 class="panel-title">球星列表</h3>
 5     </div>
 6     <ul class="list-group media-list">
 7         <!-- volist循环 -->
 8         <volist name="friends" id="friend" empty="没有球星数据">
 9             <li class="list-group-item media">
10                 <a class="pull-left" href="#">
11                     <empty name="friend['avatar']">
12                         <img src="__AVATAR__/default.jpg" width="100">
13                         <else/>
14                         <img src="__AVATAR__/{$friend['avatar']}" width="100"></empty>
15                 </a>
16                 <div class="media-body">
17                     <h4 class="media-heading">
18                         {$friend['username']}:{$friend['age']}岁
19                             <!--
20                                     eq      :   ==
21                                     neq     :   !=
22                                     gt      :   >
23                                egt     :   >=
24                                     lt      :  <
26                                     elt     :   <=
27                                     heq     :   ===
28                                     nheq    :   !==
29                                 -->
30 
31                             <!-- eq,判断年龄是否是30岁 -->
32                             <compare name="friend['age']" value="30" type="eq">
33                                 <span class="label label-warning">您正好30岁,真是猿粪啊!</span>
34                             </compare>
35 
36                             <!-- if else -->
37                             <!-- 如果年龄小于18岁 -->
38                             <if condition="$friend['age'] lt 18">
39                                 <span class="pull-right">因为未成年,所以不显示</span>
40                                 <else/>
41                                 <a href="#" class="pull-right btn btn-warning">这项操作需要满18岁</a>
42                             </if>
43                         </h4>
44 
45                         <p>
46                             <!-- 比较标签 -->
47 
48                             <!-- lt方式比较年龄 -->
49                             <lt name="friend['age']" value="18">未成年</lt>
50                             <!-- compare方式比较 -->
51                             <compare name="friend['age']" value="18" type="lt">
52                                 <span class="text-danger">注意,compare标签也表示:{$friend['username']}未成年!</span>
53                             </compare>
54                             <!-- egt方式比较年龄 -->
55                             <egt name="friend['age']" value="35">中年人</egt>
56                             <!-- between方式判断年龄区间 -->
57                             <between name="friend['age']" value="18,34">青年</between>
58                         </p>
59 
60                         <div>
61                             标签:
62                             <!-- Volist循环嵌套输出tags标签 -->
63                             <volist name="friend['tags']" id='tag'>
64                                 <span class="label label-success">{$tag}</span>
65                                 &nbsp;
66                             </volist>
67                         </div>
68                     </div>
69                 </li>
70             </volist>
71         </ul>
72     </div>

访问页面:

 

for标签,原生PHP标签,literal原样输出

 1 <!-- For循环 -->
 2 <div class="panel panel-default">
 3     <div class="panel-heading">
 4         <h3 class="panel-title">For标签循环输出</h3>
 5     </div>
 6     <div class="list-group">
 7         <for start="0" end="5" step="1">
 8             <a href="#" class="list-group-item">使用for标签循环了{$i+1}次</a>
 9         </for>
10     </div>
11 </div>
12 
13 <!-- PHP循环 -->
14 <div class="panel panel-default">
15     <div class="panel-heading">
16         <h3 class="panel-title">使用PHP标签实现php代码循环输出</h3>
17     </div>
18     <div class="list-group">
19         <php>
20             for($i=0; $i<5; $i++){
21                 echo '<a href="#" class="list-group-item">使用PHP标签循环了'.($i+1).'次</a>';
22             }
23         </php>
24     </div>
25 </div>
26 
27 <!-- literal原样输出 -->
28 <div class="panel panel-default">
29     <div class="panel-heading">
30         <h3 class="panel-title">原样输出</h3>
31     </div>
32     <div class="panel-body">
33         <blockquote>
34             <pre>
35                         <literal>我们可以使用{$user.user}的方式来输出用户名</literal>
36                     </pre>
37         </blockquote>
38     </div>
39 </div>

 

 

ThinkPHP模板:标签库

本课时讲解 ThinkPHP 自带的模板标签库以及标签库的加载方式,配置框架的内置标签库以及自定义标签库。

内置标签库解析文件位置:/ThinkPHP/Library/Think/Template/Cx.class.php

 

新增一个自定义标签库:

创建Application/Views/TagLib目录,新建Jike.class.php文件: (标签库类文件)

 1 <?php
 2 namespace Views\TagLib;
 3 use Think\Template\TagLib;
 4 
 5 /**
 6  *
 7  */
 8 class Jike extends TagLib
 9 {
10     
11     /**
12      * 定义标签列表
13      */
14     protected $tags = array(
15         'friends' => array(
16             'attr' => 'uid',
17             'close' => 1
18         )
19     );
20 
21     public function _friends($tag,$content)
22     {
23         $id=$tag['uid'];
24         $name=$tag['name'];
25         $empty=$tag['empty'];
26         $unique=rand(); 
27 
28         $parse_string='<?php ';
29         $parse_string.='$_FRIENDS_'.$unique.'=get_user_friends('.$id.');';
30         $parse_string.='if(empty($_FRIENDS_'.$unique.')){echo $empty;}';
31         $parse_string.='else';
32         $parse_string.='{';
33         $parse_string.='foreach ($_FRIENDS_' . $unique . ' as $key => $' . $name . ') {';
34         $parse_string.=' ?>';
35         $parse_string.=$content;
36         $parse_string.='<?php ';
37         $parse_string.='}';
38         $parse_string.='}';
39         $parse_string.=' ?>';
40 
41         return $parse_string;
42     }
43 }
44 ?>

补上里面的get_user_friends()方法(获取数据),function.php

 1 <?php
 2 
 3 /*
 4  * 获取球星测试数据
 5  * @return array
 6  */
 7 function get_user_friends($id=''){
 8     $friends = array(
 9         array(
10             'username' => '科比'.$id,
11             'avatar' => '1.jpg',
12             'age' => 37,
13             'tags' => array('81分','总冠军','美如画')
14         ),
15         array(
16             'username' => '詹姆斯'.$id,
17             'avatar' => '2.jpg',
18             'age' => 30,
19             'tags' => array('控场','暴力','全面')
20         ),
21         array(
22             'username' => '库里'.$id,
23             'avatar' => '3.jpg',
24             'age' => 26,
25             'tags' => array('3分','运球','总冠军')
26         ),
27         array(
28             'username' => '莫里斯'.$id,
29             'avatar' => null,
30             'age' => 17,
31             'tags' => array('球员','后卫','NBA')
32         ),
33     );
34 
35     return $friends;
36 }

 

加载标签库或预加载标签设置(TAGLIB_PRE_LOAD)

加载标签库,模板文件中:

<taglib name="Views\TagLib\Jike"/>

预加载标签设置,config中:

'TAGLIB_PRE_LOAD'=>'Views\TagLib\Jike',
//'TAGLIB_BUILD_IN'=>'Views\TagLib\Jike',  //配置内置标签库,标签就不用加前缀Jike:...

 

模板文件中使用标签

<div class="list-group">
    <Jike:friends name="jike_user" uid="2" empty="没有数据">
         <a href="#" class="list-group-item">{$jike_user['username']}</a> 
    </Jike:friends>
</div>

 

访问页面,输出结果:

 

标签在程序中是怎样一个实现原理呢?

我们查看缓存文件后,看到标签段代码已经被解析成了:

<div class="list-group">
    <?php $_FRIENDS_16864=get_user_friends(2);if(empty($_FRIENDS_16864)){echo $empty;}else{foreach ($_FRIENDS_16864 as $key => $jike_user) { ?><a href="#" class="list-group-item"><?php echo ($jike_user['username']); ?></a><?php }} ?>
</div>

我们看到,标签内容全部被解析成了php语句。

所以实现原理是:

1.标签解析标签段代码通过自定义标签库中的标签解析类,解析成

<?php $_FRIENDS_16864=get_user_friends(2);if(empty($_FRIENDS_16864)){echo $empty;}else{foreach ($_FRIENDS_16864 as $key => $jike_user) { ?><a href="#" class="list-group-item">{$jike_user['username']}</a><?php }} ?>

2.数据的获取和循环

都是在标签解析文件中实现,并且将参数的名称定义成标签里的tag['name'],这样就实现了标签输出内容名称jike_user自定义的功能。

3.界定符内代码解析成PHP

{$jike_user['username']}

最后通过Thinkphp的界定符解析,将标签内容解析成php代码

 

所以最终的原理就是把所有的标签解析成php语句,再通过php服务器,输出成html。

 

 

 

ThinkPHP模板:模板布局和继承

本课时讲解 ThinkPHP 模板的布局和继承,模板继承在实际项目中应用非常广泛,可以极大地提高开发效率,优化模板的结构。

 

暂时不是特别重要,也不难,暂略。马上开始学习模型数据库课程。

 

posted @ 2016-01-11 05:05  暖风叔叔  阅读(306)  评论(0编辑  收藏  举报