简体   繁体   中英

How to wrap groups of li tags inside ul

I have a navigation menu that contains a bunch of li tags and some of them having this class "sub-item" and I want to group those li tags inside a ul so my navigation which is like this :

<ul class='main-menu'>
    <li><a href="#">Home</a></li>
    <li><a href="#">Pages</a></li>
    <li class='sub-item'><a href="#">_Contact Us</a></li>
    <li class='sub-item'><a href="#">_Community</a></li>
    <li class='sub-item'><a href="#">_About Me</a></li>
    <li class='sub-item'><a href="#">_Blog</a></li>

    <li><a href="#">DropDown </a></li>
    <li class='sub-item'><a href="#">_Sub Menu 1</a></li>
    <li class='sub-item'><a href="#">_Sub Menu 2</a></li>
    <li class='sub-item'><a href="#">_Sub Menu 3</a></li>
    <li class='sub-item'><a href="#">_Sub Menu 4</a></li>
    <li><a href="#">Sign Out</a></li>
</ul>

Will become like this :

<ul id='main-menu'>
    <li><a href="#">Home</a></li>

    <li><a href="#">Pages</a></li>
    <ul class="sub-menu">
      <li class='sub-item'><a href="#">_Contact Us</a></li>
      <li class='sub-item'><a href="#">_Community</a></li>
      <li class='sub-item'><a href="#">_About Me</a></li>
      <li class='sub-item'><a href="#">_Blog</a></li>
    </ul>

    <li><a href="#">DropDown </a></li>
    <ul class="sub-menu">
      <li class='sub-item'><a href="#">_Sub Menu 1</a></li>
      <li class='sub-item'><a href="#">_Sub Menu 2</a></li>
      <li class='sub-item'><a href="#">_Sub Menu 3</a></li>
      <li class='sub-item'><a href="#">_Sub Menu 4</a></li>
    </ul>

    <li><a href="#">Sign Out</a></li>
</ul>

This is my attempt to do this but unfortunately it didn't worked :

$('.main-menu li a').each(function() {
  var $this = $(this),
    content = $this.text();

  if (content.indexOf('_') != -1) {
    $this.parent('li').addClass('sub-item');
  }

});
$('.sub-item').wrapAll('<ul class="sub-menu"></ul>'); 

Here is a JsFiddle demo : http://jsfiddle.net/hc05fhxr/1/

The desired output given in your question is invalid as li can't have ul as its content.

I possible alternate is to add the new ul as a descendant of the previous anchor

 $('li:not(.sub-item)').each(function() { var $li = $(this), $subs = $li.nextUntil(':not(.sub-item)'); if ($subs.length) { $('<ul />', { 'class': 'sub-menu' }).html($subs).appendTo($li); } }) 
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> <ul class='main-menu'> <li><a href="#">Home</a></li> <li><a href="#">Pages</a></li> <li class='sub-item'><a href="#">Contact Us</a></li> <li class='sub-item'><a href="#">Community</a></li> <li class='sub-item'><a href="#">About Me</a></li> <li class='sub-item'><a href="#">Blog</a></li> <li><a href="#">DropDown </a></li> <li class='sub-item'><a href="#">Sub Menu 1</a></li> <li class='sub-item'><a href="#">Sub Menu 2</a></li> <li class='sub-item'><a href="#">Sub Menu 3</a></li> <li class='sub-item'><a href="#">Sub Menu 4</a></li> <li><a href="#">Sign Out</a></li> </ul> 

You should use a combination prev() and after()

$('.main-menu li').each(function(index, el) {
  var el = $(el);

    if (!el.hasClass("sub-item"))    {
        el.after($("<ul></ul>"));
    } else {
        el.prev("ul").append(el);
    }
});
$('.main-menu ul:empty').remove()

Here is your fiddle updated: http://jsfiddle.net/hc05fhxr/3/

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM