Laravel学习教程之View模块详解


Posted in PHP onSeptember 18, 2017

前言

本文主要是给大家介绍了关于Laravel中View模块的相关资料,分享出来供大家参考学习,下面话不多说了,来一起看看详细的介绍吧。

本文是基于Laravel 5.4版本的路由模块代码进行分析书写;

文件结构

View模块的文件格局及功能如下图所示:

Laravel学习教程之View模块详解

视图化呈现时的大概流程:

1、通过view()方法的调用,开始视图的呈现;

2、首先,查找视图文件;

(1)依次遍历路径,如果文件名带命名空间(也就是::之前的部分),则采用命名空间对应注册的路径数组,否则采用全局路径数组(在Illuminate\View\FileViewFinder类中的paths变量);

(2)结合当前路径,文件名,后缀名(默认顺序是blade.php、php、css),判断文件是否存在;

(3)如果文件不存在,报异常:对应的view文件不存在;如果文件存在,则根据后缀名调用对应的引擎进行解析;

3、如果是css后缀,采用file引擎,核心调用方法是file_get_contents;

4、如果是php后缀,采用php引擎,核心调用方法是

ob_start();
include $__path;
ob_get_clean();

5、如果是blade.php后缀,采用blade引擎;

这个引擎会主动作缓存处理,如果缓存文件未过期,则直接调用缓存文件,否则重新编译,并通过sha1生成缓存文件(位于storage/framework/views目录下);

Blade 引擎编译

Blade引擎对文件的编译,是通过大量的正则匹配和替换实现的;

protected $compilers = [ 
 'Comments', // 注释部分
 'Extensions', // 扩展部分
 'Statements', // 语句块 (@ 开头的指令)
 'Echos',  // 输出
];

protected function parseToken($token) {
 list($id, $content) = $token;
 
 if ($id == T_INLINE_HTML) {
  foreach ($this->compilers as $type) {
   $content = $this->{"compile{$type}"}($content);
  }
 }
}

在解析的过程中,Blade会先使用token_get_all函数获取视图文件中的被PHP解释器认为是HTML(T_INLINE_HTML)的部分,然后依次进行Comments、Extensions、Statements 和 Echos部分的正则替换;

注释部分

核心代码如下,将注释符号“{{-- --}}”包裹的代码替换为空字符串;

preg_replace("/{{--(.*?)--}}/s", '', $value);

扩展部分

通过extend方法向BladeCompiler添加自定义处理的回调函数,对模板内容进行自定义的文本匹配替换;

核心代码在Illuminate\View\BladeCompiler文件中,如下:

// 自定义的文本替换扩展 数组
protected $extensions = [];

protected function compileExtensions($value) {
 foreach ($this->extensions as $compiler) {
  $value = call_user_func($compiler, $value, $this);
 }
 
 return $value;
}

指令替换

这部分就是将类似@if这种框架自带的指令和通过directive方法注册的指令进行文本替换;

框架提供的指令有以下十部分:

  • View\Compilers\Concerns\CompilesAuthorizations: 权限检查
    指令包括:@can、@cannot、@elsecan、@elsecannot、@endcan、@endcannot
  • Concerns\CompilesComponents:与组件、插槽相关
    指令包括:@component、@endcomponent、@slot、@endslot
  • Concerns\CompilesConditionals:与判断语句相关
    指令包括:@if、@unless、@else、@elseif、@endif、@endunless、@isset、@endisset、@hassection
  • Concerns\CompilesIncludes:嵌入文件
    指令包括:@each、@include、@includeif、@includewhen
  • Concerns\CompilesInjections:服务注入
    指令包括:@inject
  • Concerns\CompilesLayouts:和布局相关
    指令包括:@extends、@section、@parent、@yield、@show、@append、@overwrite、@stop、@endsection
  • Concerns\CompilesLoops:与循环相关
    指令包括:@forelse、@empty、@endforelse、@endempty、@for、@foreach、@break、@continue、@endfor、@endforeach、@while、@endwhile
  • Concerns\CompilesRawPhp:与原生PHP语句相关
    指令包括:@php、 @endphp、 @unset
  • Concerns\CompilesStacks:和堆栈相关
    指令包括:@stack、@push、@endpush、@prepend、@endprepend
  • Concerns\CompilesTranslations:与本地化翻译相关
    指令包括:@lang、@endlang、@choice

Echo 替换

echo输出是针对{!! !!}、{{ }}、{{{ }}}三种括号进行正则替换;

  • {!! !!}输出未转义字符,用于输出原生带html标签的值;
  • {{ }}正常输出,支持三目运算符替换;
  • {{{ }}}输出转义字符,支持三目运算符替换;

三目运算符替换是指:{{ $a ?: "默认值" }} (或者 {{$a or "默认值"}}) 换成 {{ isset($a) ? $a : "默认值"}}

参考文章

Laravel 模板引擎(Blade)原理简析

Laravel 5.4 文档 前端 —— Blade模板

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作能带来一定的帮助,如果有疑问大家可以留言交流,谢谢大家对三水点靠木的支持。

PHP 相关文章推荐
PHP加速 eAccelerator配置和使用指南
Jun 05 PHP
PHP 源代码压缩小工具
Dec 22 PHP
PHP中单引号与双引号的区别分析
Aug 19 PHP
thinkphp循环结构用法实例
Nov 24 PHP
如何写php守护进程(Daemon)
Dec 30 PHP
php 使用curl模拟登录人人(校内)网的简单实例
Jun 06 PHP
Laravel学习教程之request validation的编写
Oct 25 PHP
PHPTree――php快速生成无限级分类
Mar 30 PHP
php如何把表单内容提交到数据库
Jul 08 PHP
Thinkphp5.0 框架使用模型Model添加、更新、删除数据操作详解
Oct 11 PHP
深入理解PHP+Mysql分布式事务与解决方案
Dec 03 PHP
一文搞懂PHP中的抽象类和接口
May 25 PHP
php制作圆形用户头像的实例_自定义封装类源代码
Sep 18 #PHP
PHP中使用jQuery+Ajax实现分页查询多功能操作(示例讲解)
Sep 17 #PHP
PHP实现深度优先搜索算法(DFS,Depth First Search)详解
Sep 16 #PHP
PHP实现广度优先搜索算法(BFS,Broad First Search)详解
Sep 16 #PHP
PHP实现的迪科斯彻(Dijkstra)最短路径算法实例
Sep 16 #PHP
PHP环形链表实现方法示例
Sep 15 #PHP
PHP实现的链式队列结构示例
Sep 15 #PHP
You might like
浅谈php安全性需要注意的几点事项
2014/07/17 PHP
PHP字符串word末字符实现大小写互换的方法
2014/11/10 PHP
php读取torrent种子文件内容的方法(测试可用)
2016/05/03 PHP
浅谈PHP array_search 和 in_array 函数效率问题
2019/10/15 PHP
input标签内容改变的触发事件介绍
2014/06/18 Javascript
BAT及各大互联网公司2014前端笔试面试题--JavaScript篇
2014/10/29 Javascript
JS实现为表格动态添加标题的方法
2015/03/31 Javascript
JavaScript中的anchor()方法使用详解
2015/06/08 Javascript
Javascript中Date类型和Math类型详解
2016/02/27 Javascript
JavaScript数据结构之优先队列与循环队列实例详解
2017/10/27 Javascript
vue实现某元素吸顶或固定位置显示(监听滚动事件)
2017/12/13 Javascript
详解React 服务端渲染方案完美的解决方案
2018/12/14 Javascript
微信小程序封装自定义弹窗的实现代码
2019/05/08 Javascript
Javascript通过控制类名更改样式
2019/05/24 Javascript
jQuery实现的移动端图片缩放功能组件示例
2020/05/01 jQuery
[09:37]DOTA2卡尔工作室 英雄介绍圣堂刺客篇
2013/06/13 DOTA
[51:53]完美世界DOTA2联赛循环赛 LBZS vs DM BO2第二场 11.01
2020/11/02 DOTA
python图像处理之镜像实现方法
2015/05/30 Python
python3设计模式之简单工厂模式
2017/10/17 Python
Python数据结构之哈夫曼树定义与使用方法示例
2018/04/22 Python
对django xadmin自定义菜单的实例详解
2019/01/03 Python
对python3.4 字符串转16进制的实例详解
2019/06/12 Python
Python PIL读取的图像发生自动旋转的实现方法
2019/07/05 Python
Python生成器实现简单"生产者消费者"模型代码实例
2020/03/27 Python
django执行原始查询sql,并返回Dict字典例子
2020/04/01 Python
基于python requests selenium爬取excel vba过程解析
2020/08/12 Python
Python用dilb提取照片上人脸的示例
2020/10/26 Python
PyQT5速成教程之Qt Designer介绍与入门
2020/11/02 Python
纠纷协议书
2014/04/16 职场文书
纪检干部对照检查材料
2014/08/22 职场文书
2014年作风建设工作总结
2014/10/29 职场文书
2015年团队工作总结范文
2015/05/04 职场文书
2019自荐信范文集锦!
2019/07/03 职场文书
MySQL如何使用使用Xtrabackup进行备份和恢复
2021/06/21 MySQL
Python可视化学习之seaborn调色盘
2022/02/24 Python
基于redis+lua进行限流的方法
2022/07/23 Redis