Magento2 add a cms page link to menu

Magento2 add a cms page link to menu

.
Magento2 add a cms page link to menu or add a link to the menu, Magento2 add a cms page link to the menu.

Most of the times, need to add cms page links or static link to the menu.T

So, today I am writing this blog for add a cms page link to the menu at magento2.In this case, i am using Magento plugins and use before method.

We have used class Magento\Theme\Block\Html\Topmenu  as the menu is rendered from this class and use before plugin.

and use before plugin on _getHtml()

Magento2 add a cms page link to menu
Magento2 add a cms page link to menu

First, create a module.

Second: create di.xml where we will define the plugin.

app\code\{VendorName}\{ModuleName}\etc\di.xml

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
    <type name="Magento\Theme\Block\Html\Topmenu">
        <plugin name="add_cms_menu" type="{VendorName}{ModuleName}\Plugin\Topmenu" sortOrder="1" />
    </type>
</config>

3.Now create the plugin class where we will add a cms page link to the menu.

File Path: app\code\{VendorName}\{ModuleName}\Plugin\Topmenu.php

<?php 
namespace {VendorName}\{ModuleName}\Plugin;
use Magento\Framework\Data\Tree\NodeFactory;
class Topmenu
{
    protected $nodeFactory;
    protected $_storeManager;
    protected $_pageFactory;
    protected $_urlBuilder;
 
    public function __construct(
        NodeFactory $nodeFactory,
        \Magento\Cms\Model\PageFactory $pageFactory,
        \Magento\Store\Model\StoreManagerInterface $storeManager,
        \Magento\Framework\UrlInterface $urlBuilder
    ) {
        $this->nodeFactory = $nodeFactory;
        $this->_pageFactory = $pageFactory;
        $this->_storeManager = $storeManager;
        $this->_urlBuilder = $urlBuilder;
    }
    public function beforeGetHtml(
        \Magento\Theme\Block\Html\Topmenu $subject,
        $outermostClass = '',
        $childrenWrapClass = '',
        $limit = 0
    ) {
        /* Showing  Cms page About us at menu */
        $page = $this->getCmspage('about-us');
        if($page == null){
            return;
        }
 
 
        $node = $this->nodeFactory->create(
            [
                'data' => [
                    'name' => $page->getTitle(),
                    'id' => $page->getIdentifier(),
                    'url' =>  $this->_urlBuilder->getUrl(null, ['_direct' => $page->getIdentifier()]),
                    'has_active' => false,
                    'is_active' => false // (expression to determine if menu item is selected or not)
                ],
                'idField' => 'id',
                'tree' => $subject->getMenu()->getTree()
            ]
        );
        $subject->getMenu()->addChild($node);
    }
    protected function getCmspage($identifier){
 
        $page = $this->_pageFactory->create();
        $pageId = $page->checkIdentifier($identifier, $this->_storeManager->getStore()->getId());
 
        if (!$pageId) {
            return null;
        }
        $page->setStoreId($this->_storeManager->getStore()->getId());
        if (!$page->load($pageId)) {
            return null;
        }
 
        if (!$page->getId()) {
            return null;
        }
 
        return $page;
    }
 
}

In this way, you can Magento2 an add custom link to menu or navigation.

<?php 
namespace {VendorName}{ModuleName}\Plugin;
use Magento\Framework\Data\Tree\NodeFactory;
 
class Topmenu
{
    protected $nodeFactory;
    protected $_storeManager;
    protected $_pageFactory;
 protected $_urlBuilder;
 
    public function __construct(
        NodeFactory $nodeFactory,
 \Magento\Cms\Model\PageFactory $pageFactory,
 \Magento\Store\Model\StoreManagerInterface $storeManager,
 \Magento\Framework\UrlInterface $urlBuilder
    ) {
        $this->nodeFactory = $nodeFactory;
 $this->_pageFactory = $pageFactory;
        $this->_storeManager = $storeManager;
 $this->_urlBuilder = $urlBuilder;
    }
 
    public function beforeGetHtml(
        \Magento\Theme\Block\Html\Topmenu $subject,
        $outermostClass = '',
        $childrenWrapClass = '',
        $limit = 0
    ) {
 // Add contact us page in menu
 
       $node = $this->nodeFactory->create(
            [
                'data' => [
                    'name' => __('CONTACT US'),
                    'id' => 'contactus',
                    'url' => $this->_urlBuilder->getUrl(null, ['_direct' =>'contact']),
                    'has_active' => false,
                     'is_active' => false
                     ],
                 'idField' => 'id',
                 'tree' => $subject->getMenu()->getTree()
            ]
        );
        $subject->getMenu()->addChild($node);
    }
 
 
}

This module should have below files:

app/code/{VendorName}/{ModuleName}/etc/module.xml
app/code/{VendorName}/{ModuleName}/composer.json
app/code/{VendorName}/{ModuleName}/registration.json

In this example, I have added contact us page AT the menu.

Hope this blog will help the people

Related posts: