PHP模版引擎 – Twig

在网站开发过程中模版引擎是必不可少的,PHP中用的最多的当属Smarty了。目前公司系统也是用的Smarty,如果要新增一个页面只需把网站的头、尾和左侧公共部分通过Smarty的include方式引入进来,然后主体部分写内容即可,用起来也是相当方便。这也是一种比较通用的做法。但维护一段时间后发现有些凌乱了:

1. 公共部分内容越加越多了,不需要用的js、css在一些页面也被强制引进来了

2.新页面的css只能写在网页的body内,看起来总让人不爽。

3.左侧、头部、尾部若有特殊显示,操作起来不方便,只能在公共地方去做判断了。

当然这些页面问题在设计的时候可以通过合理的拆分网页来实现,当然最重要的还在于开发人员,在好的系统也经不起开发人员的折腾,一个项目经过多次转手后,接下来的维护人员那是相当痛苦的。不扯远了, 现在要说的是另一种模版开发思路。

在PHP中CLASS用过很多次了,有一个很有用的特性那就是继承,子类继承父类后可以直接调用父类的方法,也可以对父类的方法进行重写,同样PHP的模版引擎Twig也实现了这一点,模版的书写方式可以更方便。

Twig是开源框架Symfony2的默认模版引擎,主页是http://twig.sensiolabs.org/ 当前版本为Stable: 1.12.1 ,其他模版引擎能做的它都能做,这里主要整理下使用Twig的BLOCK方式编写模版页面。

以一个常见的排版为例,有三个链接,分别是首页、关于、联系三个页面,然后头部共用,尾部共用,中间部分分成左右两部分,左边共用,右边显示具体内容,貌似很多后台都是这种布局。
先看看首页 twig_index.php , 和Smarty差不多,初始化设置,然后设置变量并显示。


1

2

3

4

5

6

7

8

9

10

11

12

<?php

require ‘./Twig-1.12.1/lib/Twig/Autoloader.php‘;

Twig_Autoloader::register();

$loader = new Twig_Loader_Filesystem(‘./view/twig/templates‘);

$twig = new Twig_Environment($loader, array(

    ‘cache‘ => ‘./view/twig/templates_c‘,

    ‘auto_reload‘ => true

));

$twig->display(‘index.html‘, array(‘name‘ => ‘Bobby‘));

?>

其他页面的PHP内容除了模版名称不一样外,其他内容完全一样,所以后面的PHP页面就不写了。
那接下来的主要工作就是写模版了,既然支持继承,那应该有一个父类,其他页面来继承这个类。base.html就是模版的父类,其内容如下:


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

{# /view/twig/templates/base.html #}

<!DOCTYPE html>

<html>

<head>

<title>{% block title %}Home{% endblock %} - Twig</title>

<style type="text/css">

{% block stylesheet %}

#header, #main, #footer{width:600px; margin:0px auto; border:1px solid #333;}

#main{border:0px;}

#header { height:120px;margin-bottom:10px;}

#footer{ height:80px;clear:both;margin-top:10px;}

#header h1{margin-left:20px;}

#header span{margin-left:20px;}

#leftsider{width:125px; float:left; border:1px solid #333; height:200px;

padding-top:10px;}

#leftsider span{width:100%; height:30px; line-height:30px; clear:both;

padding-left:15px; display:block;}

#rightsider{width:460px; float:right; border:1px solid #333; height:250px;}

.clear{clear:both;}

{% endblock %}

</style>

</head>

<body>

    <div id="header">

        <h1>Twig Template Test</h1>

        <span><a href="twig_index.php">Home</a></span>

        <span><a href="twig_about.php">About</a></span>

        <span><a href="twig_contact.php">Contact</a></span>

    </div>

    <div id="main">

        <div id="leftsider">

            {% block leftsider %}

            <span>系统模块1</span>

            <span>系统模块2</span>

            {% endblock %}

        </div>

        <div id="rightsider">

            {% block rightsider %}Hello {{name}}{% endblock %}

        </div>

    </div>

    <div class="clear"></div>

    <div id="footer">

        {% block footer %}<h1>Twig Footer</h1>{% endblock %}

    </div>

</body>

</html>

基本的页面框架没太多说的,主要看看中间有5个block - {% block blockname%}{% endblock %}  每个BLOCK代表一个块, 这里的块可以理解成PHP父类中的一个方法。

基本的html框架搭好后,index.html该如何来写呢?首先该继承base页面,然后再考虑是否要重写base页面的内容,先只做继承看看效果。


1

2

{# /view/twig/templates/index.html #}

{% extends "base.html" %}

第一行为注释部分,可以省去,第二行表示index.html继承base.html, 未重写的情况下将直接使用base.html中的内容进行显示,也就是该页面将看到如下效果:

效果比较简单,但是很神奇,index.html只是继承了base.html,没写其他内容呢?对,不用写了,在未重写父类方法时。子类是可以直接调用父类方法的。

那接着看看about, 假设about页面和index页面除了右边区域不同外,其他部分完全相同,也就是只需要重写rightsider这个BLOCK:


1

2

3

4

{# /view/twig/templates/about.html #}

{% extends "base.html" %}

{% block title %}About{% endblock %}

{% block rightsider %} {% include ‘about_content.html‘ %} {% endblock %}

标题的内容改成了 About, rightsider的内容从about_content.html文件中读取,其他部分保留原有。也就是除了Hello Bobby的内容不同外,其他部分与首页都是相同的,是不是觉得很方便了?

再来看一下Contact页面怎么写?我么需要在leftsider里增加一个菜单,以及rightsider里显示其他block的内容。看看下面:


1

2

3

4

5

{# /view/twig/templates/contact.html #}

{% extends "base.html" %}

{% block title %}Contact{% endblock %}

{% block leftsider %}{{ parent() }}<span>系统模块3</span>{% endblock %}

{% block rightsider %} {{ block(‘footer‘) }} {% endblock %}

调用parent即可显示基类的内容,通过block(‘footer‘)则可获取footer中的Twig Footer内容。所以图片效果如下:

很神奇吧!这种排版方式值得一试,等待机会中...
使用block后子页面不可以按照html的方式在任意地方加html, 也就是在block外写任何内容都会报错,所以需要base里去合理的设置block,block设置的越多就越灵活。具体的还得到实际项目中去尝试。

至于Twig的具体语法有时间在整理下,不过这种写模版的方式确实很让人喜欢,好像Smarty3也支持该功能了,有时间也看看。

看到Twig后联想到了 lesscss, 动态样式语言,主页http://www.lesscss.net 有兴趣的朋友可以看看。

--EOF--

时间: 2024-10-12 19:52:32

PHP模版引擎 – Twig的相关文章

Symfony2模版引擎使用说明手册

一.基本使用 {{ demo }}输出一个demo变量; {{% func %}}通常是包含一个twig函数例如 for; 举个for循环的例子: {{% for i in 0..10 %}} <em>{{ i }}</em> {{% endfor %}} 当然也可以打印对象,例: {{% for user in users %}} <span>user.username</span> {{% endfor %}} 注:users是从控制器中传来的对象参数

如何在前端模版引擎开发中避免使用eval函数

前段时间,想着自己写一个简单的模版引擎,便于自己平时开发demo时使用.于是根据自己对模版引擎的理解,定义自己的模版格式,然后,根据自己定义的格式,编写处理函数,将模版标签中的字符串,解析成可执行的字符串,然后再用eval函数执行该可执行的字符串. 然后问题就出现了!eval等价于evil! 为什么呢?各大js权威书籍上都不提倡使用eval.下面我详细的解释一下为什么不提倡. 首先,大家需要知道,js并不是一门解释型语言.它和其他大家熟知的编程语言(c,java,c++)一样,是编译型语言.但是

前端数据模版引擎的总结

模板的工作原理可以简单地分成两个步骤:模板解析(翻译)和数据渲染.这两个步骤可分别部署在前端或后端来执行.如果放在后端执行,则是像Smarty,FreeMarker这样的后端模板引擎,而如果放在前端来执行,则是我们要探讨的前端模板. FreeMarker是一个模板引擎,一个基于模板生成文本输出的通用工具,使用纯Java编写,模板用servlet提供的数据动态地生成 HTML,模板语言是强大的直观的,编译器速度快,输出接近静态HTML页面的速度.这里不再对后端模版进行描述. 前端模版提高了前端开发

Express模版引擎hbs备忘

最近几天折腾了下express,想找个合适的模版引擎,下面是一些折腾过程的备忘 选择标准 选择一门模版语言时,可能会考虑的几点 语法友好(micro tmpl那种语法真是够了) 支持模版嵌套(子模版的概念) 支持模版继承(extend) 前后端共用 有容错处理(最好定位到具体出错位置) 支持预编译(性能好) 注意到hbs,似乎满足大部分的需求:https://github.com/donpark/hbs getting started demo地址:https://github.com/chyi

Spring整合Velocity模版引擎

1. 首先通过pom.xml自动加载velocity扩展包到工程: 1 <dependency> 2 <groupId>velocity</groupId> 3 <artifactId>velocity</artifactId> 4 <version>1.5</version> 5 </dependency> 2. 然后在自动装载bean的xml里边添加如下配置: 1 <bean id="vel

【转】T4模版引擎之基础入门

额,T4好陌生的名字,和NuGet一样很悲催,不为世人所熟知,却又在背后默默无闻的奉献着,直到现在我们项目组的人除了我之外,其它人还是对其豪无兴趣,基本上是连看一眼都懒得看,可怜的娃啊... T4(Text Template Transformation Toolkit)是微软官方在VisualStudio 2008中开始使用的代码生成引擎.在 Visual Studio 中,“T4 文本模板”是由一些文本块和控制逻辑组成的混合模板,它可以生成文本文件. 在 Visual C# 或 Visual

laravel 模版引擎使用

laravel 模版引擎以 @标签 开头,以 @end标签 结尾,常用有 foreach foreachelse if for while等 1)foreach 和 foreachelse 差不到,区别就是 foreachelse 还有一个@empty 分支,当循环的变量为空时执行 @foreach ($obj as $key=>$value) {{--循环体--}} @endforeach @foreachelse ($obj as $key=>$value) {{--循环体--}} @em

Java模版引擎velocity的使用

前言 关于velocity与SpringMVC的配置请参考前一篇文章,此处不再介绍.velocity作为Java模版引擎的主要目的是为了允许任何人使用简单而强大的模板语言来引用定义在Java代码中的对象.在velocity文件中可以给该页面指定模版布局,从而节省了大量的时间去写通用的模版布局.可以定义变量,与Java方法进行交互. 定义一个layout模版 在上一篇文章中提到了配置默认模版,当然也可以不使用默认模版即在要用到的页面的最上端写上 #set($layout='layout/yourl

使用模版引擎填充重复dom元素

引入arttemplate,定义newajax发送跨域请求获得数据,将获得的数据用定义的格式渲染 <!DOCTYPE html><html lang="en"><head> <meta charset="UTF-8"> <title>Title</title> <script src="js/jquery.js"></script> <scrip