Php Zend Framework 2-包装$this->;满足于其他布局

Php Zend Framework 2-包装$this->;满足于其他布局,php,zend-framework2,Php,Zend Framework2,我正在尝试为特定模块的$this->内容创建包装 我拥有的是一个主布局(所有模块都将遵循此布局),它构建了带有页眉和页脚等的基本布局。这些布局在所有模块中保持不变 但是,我希望模块的主体内容具有自定义布局。即用于定制导航条等 因此,采用以下结构: module / ModuleName / view / layout / modulelayout.phtml / modulename / index / in

我正在尝试为特定模块的$this->内容创建包装

我拥有的是一个主布局(所有模块都将遵循此布局),它构建了带有页眉和页脚等的基本布局。这些布局在所有模块中保持不变

但是,我希望模块的主体内容具有自定义布局。即用于定制导航条等

因此,采用以下结构:

module
  / ModuleName
    / view
      / layout
        / modulelayout.phtml
      / modulename
        / index
          / index.phtml
view
  / layout
    / layout.phtml
/view/layout/layout.phtml:

<?= $this->doctype(); ?>
<html lang="en">
    <head>
      ...
    </head>
    <body>
        <header>...</header>

        <div id='body'>
            <?= $this->content; ?>
        </div>

           <footer>...</footer>
    </body>
</html>
<div>...</div>

<div>
    <?= $this->content; ?>
</div>
因此,我希望ModuleName内部的所有操作(显示的$this->内容)都使用modulelayout.phtml中的布局进行包装

我在控制器的调度事件上创建了一个侦听器,以捕获所有控制器操作的侦听器:

public function onBootstrap($e) {
    $app = $e->getApplication();
    $app->getEventManager()
        ->getSharedManager()
            ->attach('Zend\Mvc\Controller\AbstractActionController', 'dispatch', array($this, 'dispatchControllerStrategy'));
}
现在我需要知道如何保留基本布局,并将模块布局添加为包装?

public function dispatchControllerStrategy($e) {
    $controller = $e->getTarget();

    $layout = $controller->layout();

    $wrapper = new ViewModel();
    $wrapper->setTemplate('layout/modulelayout');

    $layout->addChild($wrapper, 'content');
}
^^^添加子布局似乎不会以任何方式包装$this->内容,并且子布局不会呈现。总而言之,我希望最终来源是这样的:

<!DOCTYPE html>
<html lang="en">
    <head>
      ...
    </head>
    <body>
        <header>...</header>

        <div id='body'>
            <div>...</div>

            <div>
              Hello World
              ...
            </div>
        </div>

           <footer>...</footer>
    </body>
</html>

...
...
...
你好,世界
...
...
谢谢

您是否尝试过此模块:

然后在模块配置文件中添加配置

array(
    'module_layouts' => array(
        'ModuleName' => 'layout/some-layout',
    ),
);
您是否尝试过此模块:

然后在模块配置文件中添加配置

array(
    'module_layouts' => array(
        'ModuleName' => 'layout/some-layout',
    ),
);

经过一番周折,我终于找到了解决办法。看来SLMThreestpview用户2257808的评论正是我想要开始的,但我的解决方案正好符合我的需要,所以我将在这里分享:

我不再担心尝试在控制器调度时修改布局,而是将注意力集中在带有事件\u渲染器\u POST事件的视图上:

->attach('Zend\View\View', \Zend\View\ViewEvent::EVENT_RENDERER_POST, array($this, 'renderViewStrategy'));
然后在渲染时修改模型:

private $renderdedOuterView = false;
public function renderViewStrategy($e) {
    if ($this->renderdedOuterView) {
        return;
    } else {
        $this->renderdedOuterView = true;
    }

    $layout = $e->getModel();

    $children = $layout->getChildren();
    $layout->clearChildren();

    $wrapper = new ViewModel();
    $wrapper->setTemplate('layout/modulelayout');
    $wrapper->addChild($children[0], 'content');

    $layout->addChild($wrapper, 'content');
}
我使用$renderOuterView只对主布局进行任何渲染修改

然后,对于主布局,我获取模型,并获取附加的子级,该子级将是当前操作的布局

然后,我清除该子级的主模板,并在其位置添加包装器。然后,作为包装器的子级,我为刚刚从主模板中删除的当前操作添加布局

我的问题可能不是最好的选择,但这个解决方案正好符合我试图解决的问题

更新

我想补充一点,我发现了另一个问题。 将调用每个模块的所有onbootstrap,无论它们是否为活动模块

这导致另一个模块获得此布局。更改首先添加了事件调度:

$evtMgr = $e->getApplication()->getEventManager();
$evtMgr->attach(MvcEvent::EVENT_DISPATCH, array($this, 'handleEventStrategy'));
然后在HandleEvents策略中,我检查以确保活动模块是正在调用的模块的引导。如果是,那么我附加事件_RENDER _POST并使用我定义的renderViewStrategy


如果活动模块不是具有“渲染视图”策略的模块,则“如果”条件将失败,并且没有其他模块将获得修改后的布局。

经过大量的混乱,我终于找到了解决方案。看来SLMThreestpview用户2257808的评论正是我想要开始的,但我的解决方案正好符合我的需要,所以我将在这里分享:

我不再担心尝试在控制器调度时修改布局,而是将注意力集中在带有事件\u渲染器\u POST事件的视图上:

->attach('Zend\View\View', \Zend\View\ViewEvent::EVENT_RENDERER_POST, array($this, 'renderViewStrategy'));
然后在渲染时修改模型:

private $renderdedOuterView = false;
public function renderViewStrategy($e) {
    if ($this->renderdedOuterView) {
        return;
    } else {
        $this->renderdedOuterView = true;
    }

    $layout = $e->getModel();

    $children = $layout->getChildren();
    $layout->clearChildren();

    $wrapper = new ViewModel();
    $wrapper->setTemplate('layout/modulelayout');
    $wrapper->addChild($children[0], 'content');

    $layout->addChild($wrapper, 'content');
}
我使用$renderOuterView只对主布局进行任何渲染修改

然后,对于主布局,我获取模型,并获取附加的子级,该子级将是当前操作的布局

然后,我清除该子级的主模板,并在其位置添加包装器。然后,作为包装器的子级,我为刚刚从主模板中删除的当前操作添加布局

我的问题可能不是最好的选择,但这个解决方案正好符合我试图解决的问题

更新

我想补充一点,我发现了另一个问题。 将调用每个模块的所有onbootstrap,无论它们是否为活动模块

这导致另一个模块获得此布局。更改首先添加了事件调度:

$evtMgr = $e->getApplication()->getEventManager();
$evtMgr->attach(MvcEvent::EVENT_DISPATCH, array($this, 'handleEventStrategy'));
然后在HandleEvents策略中,我检查以确保活动模块是正在调用的模块的引导。如果是,那么我附加事件_RENDER _POST并使用我定义的renderViewStrategy


如果活动模块不是具有“渲染视图”策略的模块,则“如果”条件将失败,并且没有其他模块将获得修改后的布局。

我想我离答案越来越近了。似乎我的动作视图是作为基本布局(布局/布局)的子级添加的,而不是作为包装器布局(布局/模块化布局)的子级添加的。因此,我需要弄清楚如何将动作布局附加到分派中的包装器布局(我不想在每个动作中返回一个新视图)。我想您正在寻找这个,我想我离我的答案越来越近了。似乎我的动作视图是作为基本布局(布局/布局)的子级添加的,而不是作为包装器布局(布局/模块化布局)的子级添加的。因此,我需要弄清楚如何将动作布局附加到分派内部的包装器布局(我不想在每个动作中返回一个新视图)。我想您正在寻找这个我已经看到了,但它所做的只是更改每个模块的主布局。我想保持主布局不变,并在$this->content的输出中添加一个布局包装器。我已经看到了它,但它所做的只是更改每个模块的主布局。我想保持主布局不变,并在$this->content的输出中添加一个布局包装器。