Magento _prepareLayout() 调用 5 次到多次

发布于 2024-09-25 01:54:23 字数 1768 浏览 4 评论 0原文

** 新编辑 **

所以我想做的是这个。

我希望在以下 url 的产品视图上添加由我的模块生成的新表单元素,

http://magento.example.com/catalog/product/view/id/46

最终这些元素将由我的模块中的相关表确定显示

我预计,如果我在模块中扩展 Mage_Catalog_Block_Product_View ,如下所示,我仅当他位于我的模块中的相关表中时,才能够在产品表单中创建一个包含此类表单字段的块,

因此我在

 app/design/frontend/default/default/templates/<module>/test.phtml

其中创建了一个 test.phtml 文件,正如您在我的 View.php 文件中看到的那样如下所述,我构建了该块并将其显示在产品视图中。

它确实出现了,但次数太多了 5 次。从下面的答案来看,这是正常的,因此回答了为什么它出现五次的问题,但留下了问题,因为这个计划不会

起作用**结束新编辑**,

在我的模块中 所以继续进行的正确方法是什么我调用 _prepareLayout() ,当我拉出页面时,它执行了 5 次,

这是我的代码 在

/app/code/local/Namespace/Module/Product/Veiw.php
class <Namespace>_<module>_Block_Product_View extends Mage_Catalog_Block_Product_View {
    protected function _toHtml() {
        return parent::_toHtml();
    }

    public function _prepareLayout() {
        $block = $this->getLayout()->createBlock(
            'Mage_Core_Block_Template',
            'my_block_name_here',
            array('template' => '<module>/test.phtml')
        );
        if ($block){
            $this->getLayout()->getBlock('content')->insert($block)->toHtml();
        }else{
            echo "no block";
        }
            return parent::_prepareLayout();
    }
}

注意: 我刚刚注意到这也取消了可用价格数量和添加到购物车按钮。这也是一个问题

编辑 首先我要感谢大家的回答。其次,我想为您提供更多背景信息,

选择在模块中执行此操作的原因是我不希望该块出现在每个产品上。我所拥有的是一个我称之为自定义选项的表格,其中包含产品的属性,例如头发颜色、高度、重量等,并且取决于附加到产品的属性集(如果有)将取决于 html 内容显示在页面上。 所以在一种情况下它可能会得到一个下拉菜单,而在另一种情况下它可能会得到一个输入框。另一个非常重要的部分是,必须进行设置,以便我可以将最终结果作为可以安装的模块给出,并且不用担心如果有人在那里升级 magento 则不会显示它,

这是否仍然有意义这一切都在 xml 文件中完成吗?

** New EDIT **

so what I'm trying to do is this.

I want the to add new form elements generated by my module on the product view of the following url

http://magento.example.com/catalog/product/view/id/46

ultimately these elements will be determined to show up by a related table in my module

I expected that if I extended Mage_Catalog_Block_Product_View in my module as shown below I would be able to create a block in the product form that would contain such form fields, only if he are in the related table in my module

so I created a test.phtml file in

 app/design/frontend/default/default/templates/<module>/test.phtml

then as you can see in my the View.php file described bellow I built the block and displayed it in the product view.

It did appear but 5 times too many. from the answers below this is normal so that answers the question as to why the it shows up five times but leaves the question what is the proper way to proceecd since this plan is not going to work

** End New Edit **

in my module I call _prepareLayout() and it does this 5 times when i pull up the page

here's my code
in

/app/code/local/Namespace/Module/Product/Veiw.php
class <Namespace>_<module>_Block_Product_View extends Mage_Catalog_Block_Product_View {
    protected function _toHtml() {
        return parent::_toHtml();
    }

    public function _prepareLayout() {
        $block = $this->getLayout()->createBlock(
            'Mage_Core_Block_Template',
            'my_block_name_here',
            array('template' => '<module>/test.phtml')
        );
        if ($block){
            $this->getLayout()->getBlock('content')->insert($block)->toHtml();
        }else{
            echo "no block";
        }
            return parent::_prepareLayout();
    }
}

NOTE:
I just noticed this also takes away the price availability qty and add to cart button. which is also a problem

EDIT
First I want to thank you all for your answers. Second i want to give you more context

the reason for choosing to do this in the module is that I don't want the block to show up on every product . What i have is a table of what I'll call custom options containing properties of the product sort of like hair color height weight etc and depending on what set of properties are attached to the product (if any) will depend on what html content will show up on the page.
so in one case it my get a drop down menu and in another case it may get an input box. the other very important piece is that this must be setup so that I can give the end result out as a module that can be installed and not worrry that it won't show up if someone upgrades there magento

that said does it still make sense to do this all in the xml file ?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

束缚m 2024-10-02 01:54:23

在我看来,您的代码正在覆盖核心 Magento 模块,以实现在布局 xml 配置中可以轻松完成的任务。我强烈推荐以下内容:

  1. 使用内置配置机制(例如布局 xml - 阅读 Alan 的优秀教程此处)而不是尽可能编写代码。
  2. 请不要覆盖核心代码
  3. 如果必须更改核心代码的行为,
  4. ;如果绝对必须覆盖,请使用观察者而不是重写/覆盖,始终调用 parent::whatever()

例如,如果您在主题中创建 .xml 布局文件 (app/design/frontend/default//layout),您可以使用以下代码:

<catalog_product_view>
    <reference name="content">
        <block type="module/block" name"my_block_name_here" template="module/test.phtml"/>
    </reference>
</catalog_product_view>

然后您需要在 phtml 中使用 getChildHtml('my_block_name_here'); 调用来定位块。

因此,除非 _prepareLayout 内部发生其他功能,否则无需覆盖核心,甚至无需覆盖默认的 catalog.xml

编辑(上面的小编辑)

所以现在在您的块中(我建议您将其称为Namespace_Module_Block_Product_Customattributes或类似的名称),您不会覆盖核心Product_View块,但是只是处理您的逻辑,以使用哪些 html 小部件来呈现您的自定义属性。将其余的层级价格、添加到购物车、其他通用产品块代码等留给 Magento 来计算。

如果您担心模块用户的升级路径,那么您绝对不应该覆盖核心代码。使用配置方法并非常有选择性地引入与系统“运行良好”的代码,而不是尝试通过覆盖来控制它。

It seems to me that your code is overriding a core Magento module in order to achieve what could be easily done in the layout xml configuration. I would strongly recommend the follwing:

  1. Use the built-in configuration mechanisms (e.g. layout xml - read Alan's excellent tutorial here) instead of writing code whenever possible.
  2. Don't override the core code
  3. if you must change the behaviour of the core code, use an Observer rather than Rewrite/Override
  4. if you absolutely must Override, always call parent::whatever()

For example, if you create a <module>.xml layout file in your theme (app/design/frontend/default/<theme>/layout), you could use the following code:

<catalog_product_view>
    <reference name="content">
        <block type="module/block" name"my_block_name_here" template="module/test.phtml"/>
    </reference>
</catalog_product_view>

You would then need to use a getChildHtml('my_block_name_here'); call within your phtml to position the block.

So unless there is other functionality happening inside your _prepareLayout, there's no need to override the core, or even to override the default catalog.xml.

EDIT (small edit above)

So now in your Block (I would recommend that you call it Namespace_Module_Block_Product_Customattributes or something like that), you are not overriding the core Product_View block, but merely processing your logic for what html widgets to use to render your custom attributes. Leave the rest of the tier prices, add to cart, other generic product block code, etc to Magento to work out.

If you are worried about the upgrade path for your module's users, you should definitely NOT be overriding core code. Use the configuration approach and very selectively introduce code that "plays nice" with the system rather than try to boss it around with overrides.

-小熊_ 2024-10-02 01:54:23

我查看了 CE 1.4.1 的库存 Magento 安装,未修改 _prepareLayout 方法在加载 URL 时被调用 六次

http://magento.example.com/catalog/product/view/id/46

,这是因为该类被实例化了六次。所以这是正确的行为。

至于消失的元素,我可以肯定地说,但是您对 _prepareLayout 的覆盖似乎并没有

  1. 做与 Mage_Catalog_Block_Product_View::_prepareLayout 相同的事情

  2. 调用parent::_prepareLayout();

当您覆盖 Magento 中的类时,您将用自己的类替换现有的类。如果您更改方法,您就要对运行旧代码负责。

目前尚不清楚你想在这里完成什么。您应该考虑将问题分解为更小的问题,然后发布一个(或多个)“我尝试了 X,预期是 Y,并得到了 Z”类型的问题。正如所写,没有人能够回答你的问题。

I took a look at a stock Magento install of CE 1.4.1, and unmodified the _prepareLayout method is called six times when loading the URL

http://magento.example.com/catalog/product/view/id/46

That's because the class is instantiated six times. So that's the correct behavior.

As for the vanishing element, I can'y say for sure, but your override to _prepareLayout doesn't appear to either

  1. Do the same things as Mage_Catalog_Block_Product_View::_prepareLayout

  2. Call parent::_prepareLayout();

When you override a class in a Magento you're replacing an existing class with your own. If you change a method, you're responsible for that old code being run.

It's not clear what you're trying to accomplish here. You should consider breaking your problem down into smaller problems, and then posting one (or more) "I tried X, expected Y, and got Z" type questions. As written no one's going to be able to answer your question.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文