Copied to clipboard

Flag this post as spam?

This post will be reported to the moderators as potential spam to be looked at


  • Matt 228 posts 585 karma points
    5 days ago
    Matt
    0

    Hi,

    I'm trying to create a dynamic navigtaion menu as MegaNav isnt here for Umbraco8 yet.

    I've got the following code which works fine for a single menu with no drop downs.

    @inherits Umbraco.Web.Mvc.UmbracoViewPage
    
    
    
    <div data-collapse="medium" data-animation="default" data-duration="400" class="navbar w-nav">
    <div class="w-container">
    <nav role="navigation" class="navmenu w-nav-menu">
        <a href="/" class="navlink w-nav-link">Home</a>
    @{
        var selection = Umbraco.ContentAtRoot().FirstOrDefault()
        .Children()
        .Where(x => x.IsVisible());
    }
    
        @foreach (var item in selection)
        {
        <a href="@item.Url" class="navlink w-nav-link">@item.Name</a>
        }
    </nav>
            <div class="handburger w-nav-button">
              <div class="w-icon-nav-menu"></div>
            </div>
     </div>
    </div>
    

    However, I want to add some dropdowns to the menus for nodes with children using the following html code;

          <div data-hover="1" data-delay="0" class="w-dropdown">
            <div class="navlink w-dropdown-toggle">
              <div>What we do</div>
            </div>
            <nav class="w-dropdown-list"><a href="#" class="navlink w-dropdown-link">Drop Down link 1</a><a href="#" class="navlink w-dropdown-link">rop Down link 2</a><a href="#" class="navlink w-dropdown-link">rop Down link 3</a></nav>
          </div>
    

    Would anyone be able to help how I can add this to my code?

    Thanks

  • Kieron 152 posts 390 karma points
    5 days ago
    Kieron
    0

    Something like this any good?

     @foreach (var item in selection)
                {
                    if (item.Children().Count() == 0) {
                        <a href="@item.Url" class="navlink w-nav-link">@item.Name</a>
                    }
                    else if (item.Children().Count() >= 1) {
                        <div data-hover="1" data-delay="0" class="w-dropdown">
                        <div class="navlink w-dropdown-toggle">
                            <div>@item.Name</div>
                        </div>
                            @foreach (var child in item.Children().Where(c => c.IsVisible())) { 
                                <nav class="w-dropdown-list">
                                    <a href="@child.Url" class="navlink w-dropdown-link">@child.Name</a>
                                </nav>
                            }
                        </div>
                    }
                }
    

    Maybe it would be more efficient to do

    If children {
          // children
    }
    else {
          //no children link
    }
    
  • Jeffrey Veer 25 posts 219 karma points
    5 days ago
    Jeffrey Veer
    101

    Just to add on to the reply of Kieron, keep in mind that the suggested code contains a common pitfall (over-querying). A solution that solves this issue would be something like:

    @foreach (var item in selection)
    {
        var children = item.Children(c => c.IsVisible()).ToArray();
        if (children.Any())
        {
            <div data-hover="1" data-delay="0" class="w-dropdown">
                <div class="navlink w-dropdown-toggle">
                    <div>@item.Name</div>
                </div>
                @foreach (var child in children)
                {
                    <nav class="w-dropdown-list">
                        <a href="@child.Url" class="navlink w-dropdown-link">@child.Name</a>
                    </nav>
                }
            </div>
        }
        else
        {
            <a href="@item.Url" class="navlink w-nav-link">@item.Name</a>
        }
    }
    
  • Kieron 152 posts 390 karma points
    5 days ago
    Kieron
    1

    Yeah that looks much nicer. :)

  • Matt 228 posts 585 karma points
    5 days ago
    Matt
    0

    Thanks thats great and worked a treat!

    My only issue is it only shows 1 node in the drop down lists at a time? if I create more then 1 child under a node it will only show the latest 1?

    Thanks

  • Jeffrey Veer 25 posts 219 karma points
    5 days ago
    Jeffrey Veer
    0

    Hi Matt,

    Glad it worked! Can you share the code you currently have? I think it should work with the code above, but I might be missing something!

    Let me know and I will try to help you further :)

  • Matt 228 posts 585 karma points
    5 days ago
    Matt
    0

    Thanks my code is below

    @inherits Umbraco.Web.Mvc.UmbracoViewPage
    
    @{
        var selection = Umbraco.ContentAtRoot().FirstOrDefault()
        .Children()
        .Where(x => x.IsVisible());
    }
    
    <div data-collapse="medium" data-animation="default" data-duration="400" class="navbar w-nav">
    <div class="w-container">
    <nav role="navigation" class="navmenu w-nav-menu">
        <a href="/" class="navlink w-nav-link">Home</a>
    @foreach (var item in selection)
    {
        var children = item.Children(c => c.IsVisible()).ToArray();
        if (children.Any())
        {
            <div data-hover="1" data-delay="0" class="w-dropdown">
                <div class="navlink w-dropdown-toggle">
                    <div>@item.Name</div>
                </div>
                @foreach (var child in children)
                {
                    <nav class="w-dropdown-list">
                        <a href="@child.Url" class="navlink w-dropdown-link">@child.Name</a>
                    </nav>
                }
            </div>
        }
        else
        {
            <a href="@item.Url" class="navlink w-nav-link">@item.Name</a>
        }
    }
         </nav>
            <div class="handburger w-nav-button">
              <div class="w-icon-nav-menu"></div>
            </div>
     </div>
    </div> 
    
  • Jeffrey Veer 25 posts 219 karma points
    5 days ago
    Jeffrey Veer
    0

    Hmm, and it's only rendering the latest added child-page to the sub nodes of the pages under the root?

    A wild guess is that you have the umbracoNaviHide set to true? (IsVisible() filters those out)

    Another option might be that it is hidden by some CSS or JavaScript on the front-end? You might want to check the source code on your page, just to be entirely sure :)

  • Matt 228 posts 585 karma points
    5 days ago
    Matt
    0

    Yeap thats correct, if I create a new child under node "what we do" it would then hide the previous child created.

    I did think of the NaviHide, checked those and even tried removing the IsVisible statement but still the same issue.

    Hmm I'll try check the CSS/JS but cant see it being an issue as works out of Umbraco, strange.

  • Matt 228 posts 585 karma points
    5 days ago
    Matt
    1

    Got it working, I had to take the following class outside of my loop;

        <nav class="w-dropdown-list">
    
    </nav>
    

    Thanks :)

Please Sign in or register to post replies

Write your reply to:

Draft