Magento: Neu in Version 1.7: das Top Menü

Es gibt einen neuen Block in Magento 1.7 und jeder, der das Navigationsmenü in älteren Versionen überschrieben hat, wird seine Änderungen in der Magento 1.7 nicht mehr wiederfinden.

In Magento 1.6 war diese Klasse zuständig für die Navigationsaufbereitung:
Mage_Catalog_Block_Navigation
und der funktionierende Rewrite war dieser:

<global>
   <blocks>
       <catalog>
        <rewrite>
            <navigation>MeinNameSpace_MeinModul_Block_Navigation</navigation>
        </rewrite>
    </catalog>
    </blocks>
</global>

In der neuen Magento Version hat man sich also von dieser Klasse verabschiedet. Die Navigation ist nun in einem völlig neuen Block untergebracht: dem „Topmenu“ innerhalb des Page-Moduls.

In der page.xml wird man also auch fündig:

<block type="page/html_header" name="header" as="header">
    <block type="page/template_links" name="top.links" as="topLinks"/>
    <block type="page/switch" name="store_language" as="store_language" 
         template="page/switch/languages.phtml"/>
    <block type="core/text_list" name="top.menu" as="topMenu" translate="label">
        <label>Navigation Bar</label>
        <block type="page/html_topmenu" name="catalog.topnav" 
             template="page/html/topmenu.phtml"/>
    </block>
    <block type="page/html_wrapper" name="top.container" as="topContainer" translate="label">
        <label>Page Header</label>
        <action method="setElementClass"><value>top-container</value></action>
    </block>
</block>

Die neue Zuständigkeit für das Rendern der Navigation hat also die Klasse
Mage_Page_Block_Html_Topmenu
übernommen.

Und in dieser Klasse scheint es neue Events zu geben:
page_block_html_topmenu_gethtml_before
und
page_block_html_topmenu_gethtml_after
(welche bei Google noch 0 Treffer liefern, was ich hiermit ändern möchte!)

Der _after Event-Observer liefert das fertige Menu und den fertigen HTML-Code der Navigation.

Wie man mit dem _before Event das Menu beeinflusst, möchte ich kurz zeigen.

Erstmal Magento mitteilen, dass man diesen Event gerne nutzen möchte:

<frontend>
     <events>
            <page_block_html_topmenu_gethtml_before>
                <observers>
                    <meinnamespace_page_block_html_topmenu_gethtml_before>
                        <type>singleton</type>
                        <class>meinnamespace_meinmodulname/observer</class>
                        <method>topmenuGethtmlBefore</method>
                    </meinnamespace_page_block_html_topmenu_gethtml_before>
                </observers>
            </page_block_html_topmenu_gethtml_before>
        </events>
</frontend>

Dann die Observer-Klasse mit der observierenden Funktion anlegen:

class MeinNameSpace_MeinModul_Model_Observer { 
   public function topmenuGethtmlBefore (Varien_Event_Observer $observer) {
        /** @var $event Varien_Event */
        $event = $observer->getEvent();
        
        ....
   }
}

Was im Event-Objekt nun zur Verfügung steht, kann man in der Mage_Page_Block_Html_Topmenu Klasse erfahren:

public function getHtml($outermostClass = '', $childrenWrapClass = '')
{
    Mage::dispatchEvent('page_block_html_topmenu_gethtml_before', array(
        'menu' => $this->_menu
    ));

    $this->_menu->setOutermostClass($outermostClass);
    $this->_menu->setChildrenWrapClass($childrenWrapClass);

    $html = $this->_getHtml($this->_menu, $childrenWrapClass);

    Mage::dispatchEvent('page_block_html_topmenu_gethtml_after', array(
        'menu' => $this->_menu,
        'html' => $html
    ));

    return $html;
}

Nutzt man also den page_block_html_topmenu_gethtml_before Event, so steht einem mittels

/** @var $menu Varien_Data_Tree_Node */
$menu = $event->getMenu();

das Objekt zur Verfügung, das die Navigationselemente enthält.

(bei page_block_html_topmenu_gethtml_after stünde einem noch der generierte HMTL-String des Menüs zur Verfügung mittels: $html = $event->getHtml(); )

Nun kann man das Menü manipulieren.

Man kann beispielsweise den Namen eines Menüpunkts ändern:

public function topmenuGethtmlBefore (Varien_Event_Observer $observer) {
        /** @var $event Varien_Event */
        $event = $observer->getEvent();

        /** @var $menu Varien_Data_Tree_Node */
        $menu = $event->getMenu();

        /** @var $menuCollection Varien_Data_Tree_Node_Collection */
        $menuCollection = $menu->getChildren();

        /** @var $item Varien_Data_Tree_Node */
        foreach ($menuCollection as $item) {
            if ($item->getName() == 'Alter Name') { 
                $item->setName('Neuer Name');
            }
        }
    }
}

Oder man kann Menüpunkte entfernen, beispielsweise alle Unterkategorien einer Kategorie:

public function topmenuGethtmlBefore (Varien_Event_Observer $observer) {
        /** @var $event Varien_Event */
        $event = $observer->getEvent();

        /** @var $menu Varien_Data_Tree_Node */
        $menu = $event->getMenu();

        /** @var $menuCollection Varien_Data_Tree_Node_Collection */
        $menuCollection = $menu->getChildren();

        /** @var $item Varien_Data_Tree_Node */
        foreach ($menuCollection as $item) {
            if ($item->getName() == 'Alter Name') {
            
                $item->setName('Neuer Name');
                
                /** @var $childNode Varien_Data_Tree_Node */
                foreach ($item->getAllChildNodes() as $childNode) {
                    $item->removeChild($childNode);
                }
            }
        }
    }
}

Man kann natürlich hier auch Menüpunkte hinzufügen. Und verschieben. Und was sonst noch, muss ich noch herausfinden. Aber dafür ist Magento ja da.

Kontakt
E-Mail: office@neoshops.de
Tel.: +49 [0]151 7000 7107
Carmen Bremen
Magento Certified Developer
Magento Certified Solution Specialist
Magento Certified Frontend Developer
Magento Freelancer


Magento Certified Developer Magento Certified Solution Specialist Magento Certified Frontend Developer



Magento Stammtisch Köln
Magento Stammtisch KölnDer nächste Kölner Magento Stammtisch findet statt am 04. Oktober 2016. (Xing eintragen, ich sende eine Rund-E-Mail mit Details kurz vor dem Event!

Kontakt

Carmen Bremen.

In: Xing
In: Skype
In: Twitter
In: Google+
Per: Formular
Innermail: Office (t) neoshops.de
In Köln: In der Lößbörde 1, 50859 Köln
Per Handy: +49 [0]151- 7000 7107

Letzte Beiträge