yii2 ContentDecorator 和 block 挂件
在做网站的过程中,大部分的页面结构都是相似的。如都有相同的头部和底部。各个页面这样仅仅是中间的部分不同。
Yii中的布局文件就是用来实现这样的功能。如:
布局文件:@app/views/layouts/main.php
<!-- 前后的html 、head、body代码就省略了,只看最主要的部分 -->
<header>
</header>
<div class="wrap">
<div class="container">
<!-- $content变量的值 就是子页面渲染之后的代码。也就是说子页面中的内容将输出到这个地方-->
<?= $content ?>
</div>
</div>
<footer class="footer">
</footer>
后台action:
public function actionIndex()
{
$this->layout='@app/views/layouts/main.php';
return $this->render('index');
}
执行顺序为:
- 先想找index视图文件,
- 渲染index视图文件 作为变量$output
- 查找布局文件@app/views/layouts/main.php
- 如果找到,则把$output值作为变量$content传递到布局文件
- 把渲染后的布局文件作为结果返回
- 如果没有找到布局文件,直接把$output作为结果返回
上面这个布局就是一列布局的页面,现在我们再增加另外一个布局:页面显示2列,左侧显示主要的内容,右侧显示统计信息。这个时候怎么办,再写一个和上面基本完全一样的代码吗?
布局文件嵌套(小部件:ContentDecorator)
这个小部件就是专为此功能而生的。
它的功能就是把begin和end之间的内容作为变量$content的值,然后渲染指定的视图文件。
两列布局文件:@app/views/layouts/column_2.php
<!-- 先引用main.php布局文件, -->
<?php $this->beginContent('@app/views/layouts/main.php');?>
<div class="left_column">
<?= $content ?>
</div> <div class="right_column">
<!-- 在右侧共用的统一数据 -->
</div>
<?php $this->endContent();?>
把上面的action改为:
public function actionIndex()
{
$this->layout='@app/views/layouts/column_2.php';
return $this->render('index');
}
执行顺序为:
- 先把视图index渲染之后的结果作为变量 $content 传递到布局文件column_2中
- 再把布局文件column_2中的 beginContent 和 endContent 之间的内容作为变量 $content 传递到布局文件 @app/views/layouts/main.php 中
- 最后把main.php文件的结果输出。
注意: 在上面布局文件column_2中,在 beginContent 和
endContent
之外的内容是不会显示。
因此Yii中布局文件可以通过ContentDecorator小部件进行无限的嵌套。当然要小心点,不要弄成死循环了,如:ayout1引用layout2,layout2引用layout1文件
到现在你以为本文就结束了吗?终极技巧解密才刚刚开始!!!!!
多变量继承
先给你们看一个实例:
布局文件maiin:app/views/layouts/main.php
<header>
</header>
<div class="wrap">
<div class="container">
<?= $content ?>
</div>
</div>
<footer class="footer">
<div>
<?= $footer ?>
</div>
</footer>
可以看到,里面有两个变量: $content 和
$footer
。
布局文件columns_2:@app/views/layouts/columns_2.php
<?php AreaDecorator::begin(['viewFile'=>'@app/views/layouts/main.php'])?> <?php Block::begin(['id' =>'content']);?>
<div class="main_column">
<?= $mainData ?>
</div>
<div class="side_column">
<?= $sideData ?>
</div>
<?php Block::end();?> <?php Block::begin(['id' =>'footer']);?>
<div>footer data </div>
<?php Block::end();?> <?php AreaDecorator::end();?>
布局文件columns_2引用main,并通过 Block 的
id
指定main里面的两个变量的内容
布局文件columns_3:@app/views/layouts/columns_3.php
<?php AreaDecorator::begin(['viewFile'=>'@app/views/layouts/columns_2.php'])?> <?php Block::begin(['id' =>'mainData']);?>
<div class="main_column_left">
<div>main column left data</div>
</div>
<div class="main_column_right">
<div><?= $content ?></div>
</div>
<?php Block::end();?> <?php Block::begin(['id' =>'sideData']);?>
<div class="side_column">
side data
</div>
<?php Block::end();?> <?php AreaDecorator::end();?>
这个和上面的类似
action使用:
public function actionIndex()
{
$this->layout='@app/views/layouts/columns_3.php';
return $this->render('index');
}
在布局中可以定义多个点位符变量,然后在各个子布局中指定所使用的内容。
现在再也不用担心Yii布局里面只提供一个
$content
变量了
下面就是实现这个功能的小部件类
AreaDecorator小部件类:
class AreaDecorator extends Widget
{
public $viewFile; public $params = []; public $ids=[]; public function init()
{
if ($this->viewFile === null) {
throw new InvalidConfigException('ContentDecorator::viewFile must be set.');
}
ob_start();
ob_implicit_flush(false);
} public function run()
{
$params = $this->params;
$params['content'] = ob_get_clean(); $blocks = $this->view->blocks;
if(count($this->ids)>0)
{
foreach ($blocks as $id=>$block)
{
if(in_array($id,$this->ids))
{
$params[$id]=$block;
unset($this->view->blocks[$id]);
}
}
}
else
{
foreach ($blocks as $id=>$block)
{
$params[$id]=$block;
unset($this->view->blocks[$id]);
}
} echo $this->view->renderFile($this->viewFile, $params);
}
}
yii2 ContentDecorator 和 block 挂件的更多相关文章
- yii2源码学习笔记(十八)
View继承了component,用于渲染视图文件:yii2\base\View.php <?php /** * @link http://www.yiiframework.com/ * @co ...
- Yii2 事务操作
官网关于Yii2 事务的说明文档 http://www.yiiframework.com/doc-2.0/guide-db-active-record.html Working with Transa ...
- 解决Yii2 启用_csrf验证后POST数据仍提示“您提交的数据无法验证”
一 CSRF 概念 CSRF(Cross-site request forgery跨站请求伪造,也被称为“One Click Attack”或者Session Riding,通常缩写为CSRF或者XS ...
- PHP在yii2中封装SuperSlide 幻灯片编写自己的SuperSlideWidget的例子
因为近期给朋友公司做个门户网站,把荒置了6.7年的PHP又重新拾起,发现PHP这些年兴旺多了,很多新的东西看的不明不白,研究了几个框架ZendFramework.thinkphp.Symfony.yi ...
- [PHP]Yii2框架的坑
[PHP]Yii2框架的坑.md-/Users/zjh/Documents/我的文章/[PHP]Yii2框架的坑 html{font-family: sans-serif;-ms-text-size- ...
- yii2源码学习笔记(十九)
view剩余代码 /** * @return string|boolean the view file currently being rendered. False if no view file ...
- Yii2.0源码阅读-PHP如何与redis通信?
PHP与Redis可以通过socket进行通信,前提是PHP需要实现Redis的协议 RESP协议描述: 字符串 \r\n : 表示一个正确的状态信息,具体信息是'+'后面的字符(Simple Str ...
- PHP Yii2 composer环境安装
PHP Yii2 composer环境安装 composer 安装 任意目录执行: php -r "copy('https://install.phpcomposer.com/install ...
- Yii2的使用
yii2的下载安装 使用下载好的文件配置高级模板,在配置文件配置好数据库和gii 在common模板配置db: 在backend模板配置gii: 配置nginx服务器访问backend和fronten ...
随机推荐
- flume学习(三):flume将log4j日志数据写入到hdfs(转)
原文链接:flume学习(三):flume将log4j日志数据写入到hdfs 在第一篇文章中我们是将log4j的日志输出到了agent的日志文件当中.配置文件如下: tier1.sources=sou ...
- zedboard--基于zedboard的demo系统的boa服务器搭建(二十一)
zedboard提供的demo系统很迷你,但是也能移植嵌入式Web服务器的.这里就移植boa服务器. 1.下载Boa服务器源代码(安装好了交叉编译器) http://www.boa.org/,选择最后 ...
- 关于Javascript你可能不知道的事
NaN表示一个不能产生正常结果的运算结果.它不等于任何值,包括它自己.可以用isNaN(number)来检测. 同Java中的字符串一样,JS中的字符串是不可变的.也就是说一旦字符串被创建,就无法改变 ...
- python 安装whl文件
对于安装whl格式的文件,首先要安装wheel包 利用 pip install wheel或下载再安装: 下载地址: https://pypi.python.org/pypi/wheel 解压后安装: ...
- 关于DrawIndexedPrimitive函数的调用
函数的原型例如以下所看到的: HRESULT DrawIndexedPrimitive( [in] D3DPRIMITIVETYPE Type, [in] INT BaseVertexIndex, [ ...
- RDLC 动态列
很久没有写博客了,关于动态列,国内很少资料有介绍动态列的,所想写点心得给哥们 啥是动态列呢?通常我们用存储过程时有列转行和行转列的做法,那么在RDLC 怎么支持呢?其实很简单,就是利用了RDLC的 C ...
- Cocos2d-x 处理双击事件的两种方法
在cocos2d-x的开发过程中有些时候也是需要用到双击的事件处理,那么由于在cocos2d-x中没有实现对双击的事件的处理,那么我们就需要自己用代码实现. 下面介绍两种方式实现双击事件的处理. (一 ...
- 微信小程序 - 展开收缩列表
代码源自于:微信小程序示例官方 index.wxml <block wx:for-items="{{list}}" wx:key="{{item.id}}" ...
- jquery翻页
http://js.itivy.com/simplePagination.js/index.html#page-10 http://www.oschina.net/news/41941/7-html5 ...
- 算法笔记_032:最长回文串(Java)
目录 1 问题描述 2 解决方案 2.1 中心扩展法 2.2 Manacher算法 1 问题描述 给定一个字符串,求它的最长回文子串的长度. 2 解决方案 2.1 中心扩展法 此处,首先枚举出回文 ...