PHP项目ThinkPHP视图与模板引擎

wen PHP项目 4

本文目录导读:

PHP项目ThinkPHP视图与模板引擎

  1. 视图基础概念
  2. 模板引擎配置
  3. 模板渲染方法
  4. 模板语法详解
  5. 模板继承
  6. 模板引入与加载
  7. 模板引擎高级特性
  8. 模板安全与性能
  9. 完整示例

在ThinkPHP框架中,视图与模板引擎是MVC架构中非常重要的组成部分,下面我来详细介绍ThinkPHP的视图与模板引擎机制。

视图基础概念

视图的主要职责

  • 展示数据
  • 分离业务逻辑与表现层
  • 支持模板继承与复用

模板引擎配置

config/view.php中配置:

return [
    // 模板引擎类型使用Think
    'type'         => 'Think',
    // 默认模板渲染规则
    'default_theme' => '',
    // 模板目录名
    'view_dir_name' => 'view',
    // 模板后缀
    'view_suffix'  => 'html',
    // 模板常量
    'tpl_begin'    => '{',
    'tpl_end'      => '}',
    // 模板替换
    'tpl_replace'  => [
        '__ADMIN__' => '/static/admin',
        '__PUBLIC__' => '/static',
    ],
    // 模板缓存
    'tpl_cache'    => true,
    // 模板编译缓存
    'tpl_deny_php' => false,
];

模板渲染方法

控制器中渲染模板

namespace app\controller;
use think\facade\View;
class User
{
    // 使用View类
    public function index()
    {
        View::assign('name', '张三');
        View::assign('age', 25);
        return View::fetch();
    }
    // 使用fetch方法
    public function detail()
    {
        // 分配单个变量
        $this->assign('user', ['name' => '李四', 'age' => 30]);
        // 批量分配
        $this->assign([
            'title' => '用户详情',
            'data'  => $data
        ]);
        // 渲染指定模板
        return $this->fetch('user/detail');
    }
    // 使用view助手函数
    public function profile()
    {
        return view('profile', [
            'name' => '王五',
            'email' => 'wangwu@example.com'
        ]);
    }
}

模板文件命名规范

view/
├── index/           # 控制器目录
│   ├── index.html   # 对应index方法
│   ├── about.html   # 对应about方法
└── user/
    ├── index.html
    └── detail.html

模板语法详解

变量输出

<!-- 普通变量 -->
{$name}
{$user.name}
{$user['name']}
<!-- 默认值 -->
{$name|default='未命名'}
{$email|default='暂无邮箱'}
<!-- 运算符 -->
{$a + $b}
{$a * $b}
{$a > $b ? '大于' : '小于'}
<!-- 函数调用 -->
{:time()}
{:strtoupper($name)}
{:date('Y-m-d', $time)}

表达式与运算

<!-- 算术运算 -->
{$score + 10}
{$price * 0.8}
<!-- 比较运算 -->
{$age >= 18 ? '成年' : '未成年'}
<!-- 逻辑运算 -->
{$flag && $status}
{$flag || $status}
<!-- 三元运算 -->
{$condition ? '真' : '假'}

循环标签

<!-- foreach 循环 -->
{foreach $list as $key=>$value}
    <tr>
        <td>{$key}</td>
        <td>{$value.name}</td>
        <td>{$value.price}</td>
    </tr>
{/foreach}
<!-- volist 循环(ThinkPHP特有) -->
{volist name="list" id="item"}
    <li>{$item.title}</li>
{/volist}
<!-- 循环控制 -->
{foreach $list as $item}
    {if $item@first}第一个{/if}
    {if $item@last}最后一个{/if}
    {if $item@iteration % 2}偶数行{/if}
{/foreach}

分支判断

<!-- if 判断 -->
{if $status == 1}
    启用中
{elseif $status == 0}
    已禁用
{else}
    状态未知
{/if}
<!-- switch 判断 -->
{switch $type}
    {case value="1"}类型一{/case}
    {case value="2|3"}类型二或三{/case}
    {default/}其他类型
{/switch}
<!-- 条件判断 -->
{if condition="($name == 'admin') AND ($age > 20)"}
    管理员且年龄大于20
{/if}

模板继承

基础模板(layout.html)

<!-- application/view/layout.html -->
<!DOCTYPE html>
<html>
<head>{block name="title"}默认标题{/block}</title>
</head>
<body>
    <div class="header">
        网站头部
    </div>
    <div class="content">
        {block name="content"}默认内容{/block}
    </div>
    <div class="footer">
        网站底部
    </div>
</body>
</html>

子模板继承

<!-- 子模板 -->
{extend name="layout"}
{block name="title"}用户列表{/block}
{block name="content"}
    <table>
        <tr>
            <th>ID</th>
            <th>用户名</th>
        </tr>
        {foreach $users as $user}
        <tr>
            <td>{$user.id}</td>
            <td>{$user.username}</td>
        </tr>
        {/foreach}
    </table>
{/block}

模板引入与加载

<!-- 引入外部模板 -->
{include file="public/header" /}
{include file="public/footer" /}
<!-- 引入时传递参数 -->
{include file="public/nav" title="导航" /}
<!-- 加载静态资源 -->
{css href="/static/css/style.css" /}
{js href="/static/js/main.js" /}
<!-- 图片输出 -->
<img src="__STATIC__/images/logo.png">

模板引擎高级特性

模板助手函数

// 控制器中
return view('index', [
    'time' => time(),
    'html' => '<b>加粗文本</b>'
]);
<!-- 模板中使用函数 -->
{:date('Y-m-d', $time)}
{:strip_tags($html)}
{:mb_substr($content, 0, 100)}
<!-- 变量修饰符 -->
{$content|nl2br}
{$date|date='Y年m月d日'}
<!-- 防御XSS -->
{$content|htmlspecialchars}
{$content|htmlentities}

模板布局

<!-- 定义布局 -->
{layout name="layout" /}
<!-- 使用布局 -->
{layout name="layout" replace="[__CONTENT__]"}

模板缓存控制

<!-- 禁用缓存 -->
{cache name="key" expires="0"}  
    动态内容
{/cache}
<!-- 多级缓存 -->
{cache name="user_$id"}  
    {foreach $users as $user}
        {$user.name}
    {/foreach}
{/cache}

模板安全与性能

安全防护

// 开启HTML过滤
'default_filter' => 'htmlspecialchars',
// 禁止PHP标签
'tpl_deny_php' => true,
// 模板编译时自动过滤
'auto_escape' => true,

性能优化

// 开启模板缓存
'tpl_cache' => true,
// 设置缓存时间
'tpl_cache_time' => 3600,
// 模板编译目录
'view_compile' => runtime_path() . 'temp/',

完整示例

控制器

namespace app\controller;
use think\facade\View;
class Product
{
    public function list()
    {
        $products = [
            ['id' => 1, 'name' => '手机', 'price' => 3000],
            ['id' => 2, 'name' => '电脑', 'price' => 5999],
            ['id' => 3, 'name' => '平板', 'price' => 2500],
        ];
        View::assign([
            'products' => $products,
            'title' => '产品列表',
            'user' => ['is_admin' => 1]
        ]);
        return View::fetch('list');
    }
}

模板文件(view/product/list.html)

{extend name="layout"}
{block name="title"}{$title}{/block}
{block name="content"}
<div class="product-list">
    {if $user.is_admin}
    <div class="admin-toolbar">
        <a href="{:url('product/add')}">新增产品</a>
    </div>
    {/if}
    <table>
        <tr>
            <th>ID</th>
            <th>产品名称</th>
            <th>价格</th>
            <th>操作</th>
        </tr>
        {foreach $products as $product}
        <tr>
            <td>{$product.id}</td>
            <td>{$product.name}</td>
            <td>¥{$product.price|number_format=2}</td>
            <td>
                <a href="{:url('product/edit', ['id' => $product.id])}">编辑</a>
                <a href="{:url('product/delete', ['id' => $product.id])}" 
                   onclick="return confirm('确定删除?')">删除</a>
            </td>
        </tr>
        {/foreach}
    </table>
</div>
{/block}

通过这些示例可以看出,ThinkPHP的模板引擎提供了强大而灵活的功能,能够满足各种复杂的页面渲染需求,记得根据实际项目选择合适的语法和功能来使用。

抱歉,评论功能暂时关闭!