Передача данных из макета в блок-контроллер с помощью setData
Я пытаюсь установить переменную в моем файле local.xml для моего настраиваемого блока:
<layout>
<!-- ... -->
<page_homepage>
<!-- ... -->
<reference name="root">
<!-- ... -->
<block type="core/template" name="home_page_sections" template="page/homepage/sections.phtml">
<block type="layout/carousel" name="featured_carousel">
<action method="setData">
<name>filter_attribute</name>
<value>is_featured_product</value>
</action>
</block>
</block>
</reference>
</page_homepage>
</layout>
Но я не получаю данные на другом конце моего контроллера:
class Foo_Layout_Block_Carousel extends Mage_Core_Block_Template
{
public function __construct()
{
parent::__construct();
$filterAttribute = $this->getFilterAttribute(); // Nothing
$filterAttribute = $this->getData('filter_attribute'); // Nada
// Alright, fine, what DO I have?!
var_dump($this->getData()); // array(0) {} ... Argh!
}
}
Из всех моих поисков я обнаружил, что это действительно должно сработать, но, поскольку это не так, у меня такое чувство, что я пропускаю что-то очевидное. Вот моя конфигурация модуля макета (я использую один модуль для определения главной страницы и любых других блоков, которые мне нужны для сайта):
<?xml version="1.0"?>
<config>
<modules>
<Foo_Layout>
<version>0.1.0</version>
</Foo_Layout>
</modules>
<global>
<page>
<layouts>
<foo_homepage translate="label">
<label>Homepage</label>
<template>page/homepage.phtml</template>
<layout_handle>page_homepage</layout_handle>
</foo_homepage>
</layouts>
</page>
<blocks>
<layout>
<class>Foo_Layout_Block</class>
</layout>
</blocks>
</global>
</config>
Ответы
Ответ 1
Когда код рендеринга макета встречает этот
<block type="layout/carousel" name="featured_carousel">
Он немедленно создает экземпляр блока. Это означает, что метод __construct
в блоке до вызывается метод setData
. Таким образом, во время построения данные не были установлены, поэтому ваши вызовы var_dump
возвращают пустой массив.
Кроме того, сразу после создания блок добавляется в макет
#File: app/code/core/Mage/Core/Model/Layout.php
...
$block->setLayout($this);
...
Когда это происходит, вызывается метод _prepareLayout
.
#File: app/code/core/Mage/Core/Block/Abstract.php
public function setLayout(Mage_Core_Model_Layout $layout)
{
$this->_layout = $layout;
Mage::dispatchEvent('core_block_abstract_prepare_layout_before', array('block' => $this));
$this->_prepareLayout();
Mage::dispatchEvent('core_block_abstract_prepare_layout_after', array('block' => $this));
return $this;
}
Итак, это означает, что любые данные, установленные в вашем обновлении макета xml, еще недоступны, даже в _prepareLayout
. После того, как система будет создана, блок перейдет к следующему XML node.
<action method="setData">
<name>filter_attribute</name>
<value>is_featured_product</value>
</action>
и вызывает метод setData
. Теперь ваш блок имеет свой набор данных.
Попробуйте определить метод _beforeToHtml
на вашем блоке и проверить там данные. (Предполагая, что ваш блок визуализируется)
Ответ 2
Я думаю, что определение блока неверно. Можете ли вы попробовать
<block type="layout/carousel"name="featured_carousel" attribute=value>
и в phtml получить значение с помощью $this- > getAttribute()
Вы можете увидеть следующий пример:
class Elblogdeselo_Blocksparams_Block_Test extends Mage_Core_Block_Abstract{
protected function _toHtml(){
//$nombre=$this->getNombre();
$nombre=$this->getData('nombre');
$html=$html." ".$this->getData('nuevo_parametro');
return $html;
}
}
И в определении в бэкэнде я положил в свою домашнюю CMS
{{block type="blocksparams/test" name="bloque_con_parametros" nuevo_parametro="nuevo" nombre="david" template="blocksparams/test.phtml"}}
другой пример, который я нашел в расширении:
protected function _construct(){
parent::_construct();
$this->setData('customer', Mage::getSingleton('customer/session')->getCustomer());
$this->addData(Mage::getModel('model/model'));
}
Ответ 3
Передать переменные из макета в блок:
<action method="setData">
<name>variablename</name>
<value>10</value>
</action>
Получить значение переменной в блоке из макета:
$variableName = $this->getVariablename();
$variableName = $this->getData('variablename');