At the beginning of the article, first of all, I want to say sorry to those who have been following me! Because it was originally planned to complete the first version of the PHP template engine immediately after the release of front-end framework 5.0. But I couldn't do it, and it took until New Year's Day of 2015 to complete it. I'm very ashamed of my serious procrastination, and I'm sorry again!
I have said before that the corresponding API usage instructions will be published simultaneously when publishing articles in the future, but I think this is not good enough and the blog platform is not very friendly to the processing and display of tables, resulting in the API not being perfectly presented, so I plan to Only API links are provided. You can directly access my official website through the link to read the manual. That kind of reading experience is the best. In the future, the published articles will update some usage instructions related to the API, and provide some small examples, so that while reading the API, everyone can also have a deeper understanding of the various usages and business logic ideas of the code through practical examples!
The following is the API manual and example demonstration link
【Example Demonstration】:http://www.shibuyi.net/demo/php/template_engine/prototype
【Official API User Manual】: http://www.shibuyi.net/api/php/template_engine/prototype
[Author’s personal official website]: http://www.shibuyi.net
The following is a tutorial on how to use the prototype version of the PHP template engine Prototype, which will be referred to as: template engine!
What? Don’t know what a template engine is? Some PHP novices may ask this question, so I will simply answer it. The template engine is actually a middleware technology of PHP, which makes traditional Web dynamic website programming easier. Why do you say this? Wasn't it easy before? That's because before the emergence of template engines, almost all Web server programmers completed their work through mixed code. The so-called mixed code means that a page contains both: PHP, HTML and even codes in other languages. Therefore, if the project gradually expands, the time cost of development and maintenance will be extremely high, and it will be error-prone, and the art and program will not work well together. If the artist does not understand the program at all, it is basically impossible to read the mixed file. The birth of the template engine solved this problem very well. It uses template engine technology to well separate the PHP business logic layer code and the presentation layer code HTML in the mixed file. Programmers can design programs with peace of mind, while artists can design interfaces with peace of mind. A special symbol of the template tag will be used for association, so that the template engine can smoothly compile the template file after reading it. There are already many quite mature template engines for PHP on the market, such as Smarty template engine, etc. Other web server languages also have their own corresponding template engines, or middleware technologies similar to template engines.
For a detailed introduction to the template engine, we recommend that you visit Baidu Encyclopedia: http://baike.baidu.com/view/4258079.htm
Before learning the template engine, you must first ensure that you have understood the OOP (Object-Oriented Programming) thinking of PHP, because template technology is described using OOP thinking. If you do not understand OOP, then this article is not suitable for you to read. Because the threshold is too high!
The first picture you see is the directory structure diagram of the template engine (the author is using the ZendStudio 7.2.1 integrated development environment):
1. caches is the template cache directory (if the template engine does not exist, it will be automatically generated for the first time);
2. classes is the core class library of the template engine;
3. compiles is the template compilation directory (if the template engine does not exist, it will be automatically generated for the first time);
4. constants is the template constant directory (if the template engine does not exist, it will be automatically generated for the first time);
5. includes configures the directory for the template;
6. templates is the template file directory (if the template engine does not exist, it will be automatically generated for the first time).
After understanding the directory of the template engine, let’s take a look at how to make it work. In the prototype version, the relevant initialization and configuration information of the template engine are completed in the includes/template.inc.php file (you can open the source code to check it out).
In fact, the configuration of the template engine is also called the initialization process. The first step of initialization is to configure the corresponding directory so that the template engine can correctly read and write the data in the directory (you can freely choose the configuration steps, no You must configure it according to my order, but it must be completed before instantiating the template engine, otherwise it will be invalid), and we assume that the configuration is in the same directory as the template engine. If it is not the same directory, the configuration of the root directory Need to pay attention to the adjustment.
1. The first step is to configure the root directory of the template engine. If not set, the absolute path to the root directory will be automatically generated.
Template :: <span>$rootPath</span> = <span>dirname</span>(<span>__FILE__</span>); <span>//</span><span> 相对与绝对路径均可,我们这里则采用绝对路径!如:"C:/wwwroot/prototype"</span>
2. 配置模板文件目录,这个目录是用来存放模板文件的,如果不设置则默认为:templates 目录。
<span>//</span><span> 这里则采用默认目录,大家根据自己的需求进行设置,建议不要写中文容易出错,目录名的前后加不加正反斜杠都无所谓,最终模板引擎内部会自动校正!</span> Template :: <span>$templateName</span> = '/templates/';
3. 配置编译文件目录,这是用来存在模板文件被解析后生成的编译文件,如果不设置则默认为:compiles 目录。
Template :: <span>$compileName</span> = '/compiles/'; <span>//</span><span> 和模板目录一样也采用默认目录。</span>
4. 配置缓存文件目录,这是在模板引擎开启缓存功能后,用来存在编译文件生成的缓存文件,如果不设置默认为:caches 目录。
Template :: <span>$cacheName</span> = '/caches/'; <span>//</span><span> 一样使用默认</span>
5. 配置模板常量目录,可能大家不太理解模板常量是用来干嘛的,和普通的PHP常量有什么区别吗?关于模板常量的解释,在接下来的运用在我们在详细探讨,这里就先跟我进行配置即可,如果不设置默认为:constants 目录。
Template :: <span>$constantName</span> = '/constants/'; <span>//</span><span> 使用默认</span>
6. 到第六步为止,目录的配置就全部完成了,大家不用担心目录不存在的问题,也不用手动去创建,模板引擎内部会自动帮我们完成。那么接下来就是设置模板常量的文件名称,如果不设置则默认为:default.xml 文件。
<span>//</span><span> 我们也采用默认,但大家要注意的是这里必须采用 .xml 为扩展名,因为常量文件是以 XML 标记描述的,如果不是 .xml 结尾,那么可能会导致模板引擎在处理常量时出现异常情况!</span> Template :: <span>$constantFile</span> = 'default.xml';
7. 设置缓存开关,缓存默认情况下是被关闭的,只有我们去设置他,才会开启。
<span>//</span><span> 大家注意,这里我写的是一个布尔值,其实这里可以填写任意值,最终都会被隐式转换为布尔值,写 0 或 1 都可以,我直接写布尔值是为了方便大家的理解!</span> Template :: <span>$cacheSwitch</span> = <span>true</span>;
8. 至此模板引擎的配置基本上就已经全部完成了,还是很简单的。现在我们只需要实例化出模板引擎对象,就可以真正的运行模板引擎了。
<span>$tpl</span> = <span>new</span> Template(); <span>//</span><span> 实例化出模板引擎,从这一步开始之前的配置全部生效,模板引擎实例化时不需要传递任何参数。</span>
9. 在实例化出模板引擎对象以后,我们就可以开始对其进行操作,那么对谁进行操作呢?当然是模板文件了,首先我们要先创建模板文件。在模板文件目录中进行创建。模板文件其实是纯 HTML 代码文件,扩展名可以自定义,而我们约定俗成,都已 .tpl 为扩展名。假设我们已经创建了一个模板文件名为:index.tpl,因为和我们的 php 业务逻辑文件 index.php 同名,这也是按照惯例约定俗成,因为 index.php 文件调用 index.tpl 模板,见名知意。
10. 在创建了模板文件之后,我们就可以在业务文件(之前的配置也都是在 index.php 中执行的)中进行对模板文件的加载以及注入模板变量,关于模板变量和其他的模板标识符(又统称模板标记)将在接下来的步骤中逐一讲解。
<span>//</span><span> 注入变量的格式有两种,大家注意看 API 手册的说明,数组格式与传统的键值对格式均可以,我们两种都使用一下。</span> <span>$tpl</span> -> assign('title', '头衔'); <span>//</span><span> 首先是传统键值对格式</span> <span>$tpl</span> -> assign(<span>array</span>('title' => '头衔', 'name' => '名称')); <span>//</span><span> 数组格式明显要更加好用一些,因为在注入多个变量时,就可以不用写多个注入语句,一句话就搞定了。 // 如果出现了两个一模一样的变量名称,那么其后会将之前的给替换掉。以下代码,最终 language 变量的值为:英文。</span> <span>$tpl</span> -> assign(<span>array</span>('language' => '中文', 'language' => '英文'<span>)); </span><span>//</span><span> 接下来是加载模板文件,直接写模板名称即可,模板引擎会自动锁定到模板文件目录。</span> <span>$tpl</span> -> display('index.tpl');
11. 至此对模板引擎的操作就结束了,接下来我们将熟悉一下模板文件中的各个模板标记的使用方法,他们都是用来做什么的。在原型版中模板标记一共有 9 种,分别为:1. 模板变量、2. 模板常量、3. 单行模板注释、4. 多行模板注释、5. include 文件加载、6. template 模板文件加载、7. source 源模板文件加载(较为特殊)、8. if 分歧语句、9. foreach 循环语句。那么我们首先解释一下模板变量吧。
<span><</span><span>div </span><span>id</span><span>="main"</span><span>></span> <span><!--</span><span> 刚刚我们注入了 title 变量,那么模板在模板文件中就可以对其进行调用了,调用方法就是保持同名,按着这样的格式抒写即可{$模板变量名称}</span><span>--></span> <span><!--</span><span> 模板变量的命名规范与 PHP 普通变量一模一样,首位不能为数字,且区分大小写,注意保证格式的正确性,如果错误模板引擎将不会对其进行解析 </span><span>--></span> <span><</span><span>a </span><span>href</span><span>="###"</span><span>></span>{$title}<span></</span><span>a</span><span>></span> <span><!--</span><span> 正确的格式,被正确解析 </span><span>--></span> <span><</span><span>a </span><span>href</span><span>="###"</span><span>></span>{$123}<span></</span><span>a</span><span>></span> <span><!--</span><span> 错误的格式,无法解析 </span><span>--></span> <span></</span><span>div</span><span>></span>
12. 下面是模板常量的使用,模板常量和 PHP 常量虽然名字上都叫他常量,其实本质上并非一回事。模板常量其实看以看做是伪常量,而并非真正的常量,他是通过对 XML 标记的处理,来保持一组特定不变的值,这些值需要手动的添加到常量文件中。(手动添加其实不太方便,笔者会在其后的版本迭代中,加入自动添加的功能)
首先我们需要在模板常量文件中手动添加模板常量,代码如下:
<span><?</span><span>xml version="1.0" coding="utf-8" </span><span>?></span> <span><</span><span>root</span><span>></span> <span><!--</span><span> 必须在 root 根标记中间进行添加,而且一个标记字母都不能出错,注意区分大小写,如果不慎写错,模板引擎将无法对其进行获取 </span><span>--></span> <span><</span><span>constant</span><span>></span> <span><</span><span>key</span><span>></span>WEBNAME<span></</span><span>key</span><span>></span> <span><!--</span><span> 这里填写常量名称注意字母必须全部大写,第一位不能为数字,格式与 PHP 定义常量一样 </span><span>--></span> <span><</span><span>value</span><span>></span>网站标题<span></</span><span>value</span><span>></span> <span><!--</span><span> 值可以为空 </span><span>--></span> <span></</span><span>constant</span><span>></span> <span><</span><span>constant</span><span>></span> <span><</span><span>key</span><span>></span>123abc<span></</span><span>key</span><span>></span> <span><!--</span><span> 错误的常量名 </span><span>--></span> <span><</span><span>value</span><span>></</span><span>value</span><span>></span> <span><!--</span><span> 空值 </span><span>--></span> <span></</span><span>constant</span><span>></span> <span></</span><span>root</span><span>></span>
配置好常量后,接下来就是在模板文件中进行调用,代码如下:
<span><!--</span><span> 模板常量的调用和变量类似,只是取消了 $ 符号,另外常量名要保持一致 </span><span>--></span> <span><</span><span>title</span><span>></span>{WEBANME}<span></</span><span>title</span><span>></span> <span><!--</span><span> 正确的名称,将被正确解析 </span><span>--></span> <span><</span><span>p</span><span>></span>{NAME}<span></</span><span>p</span><span>></span> <span><!--</span><span> 虽然格式正确,但刚才没有进行 NAME 常量的配置,因此最终解析后会返回一个空值 </span><span>--></span> <span><</span><span>p</span><span>></span>{abc123}<span></</span><span>p</span><span>></span> <span><!--</span><span> 错误的名称,无法解析 </span><span>--></span>
13. 下面是模板的注释符,有两种:一种为单行,一种为多行。多用于对模板文件代码的注解,可以让美工配合设计界面的时候了解代码的实际含义。
<span><!--</span><span> 大家可以把模板注释放到 HTML 注释中,这样美工在设置模板页面的时候会更加一目了然。</span><span>--></span> <span><!--</span><span> 单行注释的格式是:{@}内容可写可不写,但不写也就没有意义了 </span><span>--></span><span> {@ 普通的单行注释} </span><span><!--</span><span> 正确的格式 </span><span>--></span> <span><!--</span><span> {@ HTML 代码中的单行注释} </span><span>--></span> <span><!--</span><span> 正确的格式 </span><span>--></span><span> {@ 换行的 单行注释} </span><span><!--</span><span> 格式错误,单行注释无法换行,模板引擎无法解析 </span><span>--></span> <span><!--</span><span> 多行注释的格式是:{#}...{/#}一头一尾要呼应,内容也可以不写 </span><span>--></span><span> {#}这是多行行注释,注意首位呼应!{/#} </span><span><!--</span><span> 正确的格式 </span><span>--></span><span> {#}这是多行行注释, 我换行了!{/#} </span><span><!--</span><span> 正确的格式 </span><span>--></span><span> {#} 没有写结尾符号 </span><span><!--</span><span> 错误的格式,模板引擎无法解析 </span><span>--></span>
14. 模板加载标识符,加载方式分为三类,别分为:include 对普通文件的直接加载;template 对模板文件进行编译后加载;source 对模板文件进行编译后直接输出编译文件的路径(此方法较为特殊且并不完美,需要在特定的场合中使用,比如:框架页面的调用)
首先是对普通文件的加载调用,代码如下:
<span><!--</span><span> 注意抒写格式,被直接加载的文件多半是 php 文件,且文件必须要存在,不存在的文件,模板引擎将会给出一个错误提示,并且终止代码的执行 </span><span>--></span> <span><!--</span><span> 文件名前后的引号,单双引号都可以,但必须保持一致,不能一单一双,否则模板引擎将不会对其解析 </span><span>--></span><span> {include path = "test.php"} </span><span><!--</span><span> 正确的格式,将被解析 </span><span>--></span><span> {include path = 'abc.php"} </span><span><!--</span><span> 错误的格式,无法被解析 </span><span>--></span> <span><!--</span><span> 如果出现了同一个文件被加载了两次,那么模板引擎只会对其加载第一次后,自动忽略其后的加载 </span><span>--></span><span> {include path = "123.php"} </span><span><!--</span><span> 第一次被加载成功 </span><span>--></span><span> {include path = "123.php"} </span><span><!--</span><span> 与上一个文件同属一个文件,将无法被再次加载,而被自动忽略 </span><span>--></span>
下面是对模板文件的编译加载,代码如下:
<span><!--</span><span> 格式与 include 方式基本一样,就不重复阐述了,不一样的是 include 是需要给出具体的路径地址,而 template 则只需要给出模板名称即可,模板引擎会自动找到该模板文件 </span><span>--></span><span> {template path = 'test.tpl'} </span><span><!--</span><span> 正确的格式,将会被编译后加载 </span><span>--></span>
最后就是模板文件的编译地址的输出,该功能较特殊,即使不理解也没关系,该方法有严重的 BUG 尚未处理完毕,因此并不完美,且使用的概率也极低,这里只做简单的介绍。在其后的版本迭代中,是否会保留并完善,尚在定夺,代码如下:
<span><!--</span><span> 这里我们将使用 iframe 框架页面,来调用 source 加载方法,调用格式与前两种雷同,就不在阐述 </span><span>--></span> <span><!--</span><span> 这样使用其实就可以了,但又严重的 BUG 出现,原因是所有在 frame.tpl 中注入的模板标记被解析后,将无法找到源头,也就是说 php 将无法对其正确处理,并且因为无法找到源头,而会报错,该 BUG 的解决方案还在研究中,这里仅提供给大家思考 </span><span>--></span> <span><</span><span>iframe </span><span>src</span><span>="{source path = 'frame.tpl'}"</span><span>></</span><span>iframe</span><span>></span>
15. 接下来是经常会被用到的 if 分歧语句,他和 php 的 if 语句很类似,但功能上却很简单,且不支持多重判断以及嵌套判断,但我会在其后的版本迭代中让其功能逐步强大。
<span><!--</span><span> if 语句的格式其实和多行注释一样,一定要注意首位呼应,但大小写无所谓都能够支持和 PHP 原生的 if 语句是一样的。 </span><span>--></span><span> {if $action} </span><span><!--</span><span> 只要被注入的 {$action} 变量的值为 true,或隐式转换后为 true,那么 if 语句中的代码将被显示 </span><span>--></span> <span><</span><span>p</span><span>></span>界面1<span></</span><span>p</span><span>></span><span> {/if} {if !$action} </span><span><!--</span><span> 加入了逻辑非的判断,只要为 false 则被显示 </span><span>--></span> <span><</span><span>p</span><span>></span>界面2<span></</span><span>p</span><span>></span><span> {/if} {if $action} </span><span><!--</span><span> 双层判断的时候,为 true 时显示界面1,为 false 时显示界面2 </span><span>--></span> <span><</span><span>p</span><span>></span>界面1<span></</span><span>p</span><span>></span><span> {else} </span><span><</span><span>p</span><span>></span>界面2<span></</span><span>p</span><span>></span><span> {/if} {if $action} </span><span><!--</span><span> 错误的格式,没有结尾,不会被模板引擎解析 </span><span>--></span>
16. 终于到了最后的也是复杂的 foreach 循环语句的调用了,其功能和 PHP 一样,只是格式上稍有改动。
<span><!--</span><span> 注意在调用 foreach 和 if 一样要收尾呼应,而且如果变量不是数组格式,那么 php 将会自动报出一个错误 </span><span>--></span> <span><!--</span><span> 其中 $array 就是被注入的模板变量,注意要是数组格式;而 key 和 value 则是对于的数组中的键值对,必须写,否则格式不正确,将无法被模板引擎解析 </span><span>--></span><span> {foreach $array(key, value)} </span><span><</span><span>p</span><span>></span>{%key} ... {%value}<span></</span><span>p</span><span>></span> <span><!--</span><span> 注意 key 和 value 可以自定义,但一定要同名调用,否则无法被解析 </span><span>--></span><span> {/foreach} {foreach $userList(id, username)} </span><span><</span><span>p</span><span>></span>{%id} ... {%username}<span></</span><span>p</span><span>></span> <span><!--</span><span> 自定义的 key 和 value,格式正确 </span><span>--></span> <span><</span><span>p</span><span>></span>{%password}<span></</span><span>p</span><span>></span> <span><!--</span><span> 错误的格式,并没有被定义,因此无法被解析 </span><span>--></span><span> {/foreach}</span>
好了,写到这里我也可以长长的舒口气,模板引擎原型版的教导到此就结束了。虽然教导文章已经很详细了,但建议大家配合 API 手册和实例代码进行参照阅读,这样效果会更好更便于理解和掌握。当然因为是文章,所以即使你描述的再详细,文字也是抽象的,需要大家多动手,而对于动手能力较差的新手们,这篇教导文章则起不到多大的作用,可能反而会被弄得一头雾水,甚至最终对此厌恶,所以我有想过如果以后有可能,在版本迭代更新到一定程度后,我会针对性的出一套系列教导视频,那样的话就不会像文字这样抽象,新手也能够很快的学习。
如果你是从头看到尾,那么我真心感谢您的阅览,我想你应该有什么话要想说,请一定要在下面留言告诉我,有问题也请及时留言,谢谢各位的支持~!