Any site without navigation is useless. Liferay provides great support for the site’s navigation. Liferay’s Navigation portlet allows navigation through public and private pages created in the particular site. Navigation consists of the main menus, which we use to customize and configure. Even it allows developers to extend and customize the default product navigation to fulfill their requirements.

There are two main ways to define and customize site navigation:

  • In the Site’s theme
  • Using Navigation Module

Even these two ways of defining site navigation can be used simultaneously.

ADDING A NAVIGATION MENU APP

  1. Go to the welcome page
  2. Click the Add button (+) on the upper right and expand the Applications  Content Management category in the menu
  3. Drag a Navigation application on the page
  4. You can change the look and feel of the same from the configuration

PROBLEM IN LIFERAY’S DEFAULT NAVIGATION MENU

Let’s say, we have a page structure in our site as follow :

  1. Home
  2. Documentation
    • Document 1
    • Document 2
  3. Services
    • Product
      • Product 1
        • Features
      • Product 2
        • Features
Liferay default provides only 2 level navigation. For above 2 level of Page structure, liferay default does not provide navigation as shown in the figure before the solution.
Defult Page structure
To get the solution of above problem, we need to create a new ADT (Application Display Template) for navigation. Below is the attached snippet of the ADT to show 4 level navigation.

4-Level Navigation-ADT

For 4 level navigation we need to check if the entries has browsable children then we need to add another ul tag for the same and need to iterate the list of the entries . If we have 3 level page structure then we need total 3 ul tags and if we have 4 level page structure then total 4 UL tags should be added to fulfil our requirement. If the Page structure level increases, then we need to check if the page has browsable children then that many times UL tags has to be added and iteration has to be done. Please find the below code snippet.

Code Snippet:

  <#if showChildren>
    <ul aria-expanded="false" class="level-1 child-menu dropdown-menu" role="menu">
        <#list navItem.getBrowsableChildren() as childNavigationItem>
            <#assign hasThirdChildren = (displayDepth != 1) &#038;&#038; childNavigationItem.hasBrowsableChildren() /> 
            <#assign
                nav_child_attr_selected = ""
                nav_child_css_class = "lfr-nav-item "
                nav_child_caret = ""
                nav_item_second_child_class = ""
                nav_child_link_css_class = ""
                nav_child_attr_has_popup = ""
            />
            <#if hasThirdChildren>
                <#assign nav_item_second_child_class = "dropdown dropdown-submenu" />
                <#assign nav_child_attr_has_popup = "aria-haspopup='true'" />
                <#assign nav_child_caret = '<span class="lfr-nav-child-toggle"><i class="icon-caret-right"></i></span>' />
                <#assign
                    nav_child_css_class = "${nav_child_css_class} dropdown"
                    nav_child_link_css_class = "dropdown-toggle"
                />
                <#list childNavigationItem.getBrowsableChildren() as level3Child>
                    <#if level3Child.isSelected()>
                        <#assign
                            nav_item_css_selected_class="selected active"
                        />
                    </#if>
                    <#list level3Child.getBrowsableChildren() as level4Child>
                        <#if level4Child.isSelected()>
                            <#assign
                                nav_item_css_selected_class="selected active"
                            />
                        </#if>
                    </#list>
                </#list>
            </#if>
            <#if childNavigationItem.isSelected()>
                <#assign
                    nav_child_attr_selected = "aria-selected='true'"
                    nav_child_css_class = "${nav_child_css_class} active selected"
                />
            </#if>
            <li class="${nav_child_css_class} ${nav_item_second_child_class} ${nav_item_css_selected_class} " id="layout_${childNavigationItem.getLayoutId()}" ${nav_child_attr_selected} role="presentation">
            <#assign
                    nav_item_css_selected_class = ""
                />
                <span>${childNavigationItem.getName()}
                    <@liferay_theme["layout-icon"] layout=childNavigationItem.getLayout() /> ${nav_child_caret}</span>
                
                <#if hasThirdChildren>
                    <ul aria-expanded="false" class="level-2 child-menu dropdown-menu" role="menu">
                        <#list childNavigationItem.getBrowsableChildren() as level3Child>
                            <#assign hasFourthChildren = (displayDepth != 1) &#038;&#038; level3Child.hasBrowsableChildren() />
                            <#assign
                                nav_third_child_caret = ""
                                nav_item_third_child_class = ""
                                nav_third_link_css_class = ""
                                nav_third_attr_has_popup = ""
                                nav_third_child_css_class = ""
                                nav_third_css_selected_class = ""
                            />
                            <#if hasFourthChildren>
                                <#assign nav_item_third_child_class = "dropdown dropdown-submenu" />
                                <#assign nav_third_attr_has_popup = "aria-haspopup='true'" />
                                <#assign nav_third_child_caret = '<span class="lfr-nav-child-toggle"><i class="icon-caret-right"></i></span>' />
                                <#assign
                                    nav_third_child_css_class = "${nav_third_child_css_class} dropdown"
                                    nav_third_link_css_class = "dropdown-toggle"
                                />
                                <#list level3Child.getBrowsableChildren() as level4child >
                                    <#if level4child.isSelected()>
                                        <#assign
                                            nav_third_css_selected_class="selected active"
                                        />
                                    </#if>
                                </#list>
                            </#if>
                            <#assign
                                third_level_child_attr_selected = ""
                                third_level_child_css_class = "lfr-nav-item "
                            />
                            <#if level3Child.isSelected()>
                                <#assign
                                    third_level_child_attr_selected = "aria-selected='true'"
                                    third_level_child_css_class = "${third_level_child_css_class} active selected"                          
                                />
                            </#if>
                            <li class="${third_level_child_css_class} ${nav_item_third_child_class} ${nav_third_css_selected_class}" id="layout_${level3Child.getLayoutId()}" ${third_level_child_attr_selected} role="presentation" >
                            <#assign
                                nav_third_css_selected_class = ""
                            />
                            <a labelledby="layout_${level3Child.getLayoutId()}" href="${level3Child.getURL()}" role="menuitem" class="${nav_third_link_css_class} broken_link">
                                <span>${level3Child.getName()}
                                    <@liferay_theme["layout-icon"] layout=level3Child.getLayout() /> ${nav_third_child_caret}
                                </span>
                            </a>
                            <#if hasFourthChildren>
                                %3�ul aria-expanded="false" class="level-2 child-menu dropdown-menu" role="menu">
                                    <#list level3Child.getBrowsableChildren() as level4children>
                                        <#assign
                                            fourth_level_child_attr_selected = ""
                                            fourth_level_child_css_class = "lfr-nav-item "
                                        />
                                        <#if level4children.isSelected()>
                                            <#assign
                                                fourth_level_child_attr_selected = "aria-selected='true'"
                                                fourth_level_child_css_class = "${fourth_level_child_css_class} active selected"                            
                                            />
                                        </#if>
                                        <li class="${fourth_level_child_css_class}" id="layout_${level4children.getLayoutId()}" ${fourth_level_child_attr_selected} role="presentation">
                                            <a aria-labelledby="layout_${level4children.getLayoutId()}" href="${level4children.getURL()}" ${level4children.getTarget()} role="menuitem">${level4children.getName()}</a>
                                        </li>
                                    </#list>
                                </ul>
                            </#if>
                            </li>
                        </#list>
                    </ul>
                </#if>
            </li>
        </#list>
    </ul>
</#if>

In the above snippet, main conditions which we need to check if the page has third children by using displayDepth and hasBrowsableChildren. If it has third children, then again iteration needs to be done as shown in the above snippet for 3rd level child to display its page name. Again, we need to check if the page has fourth children by same above mentioned step. If it has, then again looping is to be done as shown in the above snippet for 4th level child to display its page name. 

Your content goes here. Edit or remove this text inline or in the module Content settings. You can also style every aspect of this content in the module Design settings and even apply custom CSS to this text in the module Advanced settings.

he above snippet is till 4 level navigation, if we need to add 5th level of page in the navigation then again, we need to check if the page has fifth children by same above mentioned steps. If it has, then again looping is to be done for 5th level child to display its page name. And it goes on.

Closure : A Site can have N number of page level structure and each should be displayed in the navigation menu for user to traverse the site. So after reading this blog, you will be able to have each and every page in your navigation. Was worrying for more than 2 level of page structure for navigation in your site? Now no need to worry.

This blog has been written by our Jr. Consultant Jinal Thakrar

Cloud Cost Management Logo Web
Hadoop to Snowflake New Web
capptixAI-case-study
lendingAI-logo_opt
CustomerAI_Logo_700x300 copy
sales-ai-logo-500x200