问题
I have an unordered list exported by a CMS and need to identify <li>
elements that have the class .sub and wrap them in a <ul>
.
I have tried the wrapAll()
method but that finds all <li class="sub">
elements and wraps them in one <ul>
. I need it to maintain seperate groupings.
The exported code is as follows:
<ul>
<li></li>
<li></li>
<li></li>
<li class="sub"></li>
<li class="sub"></li>
<li class="sub"></li>
<li></li>
<li></li>
<li class="sub"></li>
<li class="sub"></li>
<li class="sub"></li>
<li></li>
</ul>
I need it to be:
<ul>
<li></li>
<li></li>
<li></li>
<ul>
<li class="sub"></li>
<li class="sub"></li>
<li class="sub"></li>
</ul>
<li></li>
<li></li>
<li></li>
<ul>
<li class="sub"></li>
<li class="sub"></li>
<li class="sub"></li>
</ul>
<li></li>
<li></li>
</ul>
Any help would be greatly appreciated.
回答1:
- Use .each to walk through all
.sub
elements. - Ignore elements whose parent has class
wrapped
, using hasClass() - Use nextUntil(:not(.sub)) to select all consecutive sub elements (include itself using .andSelf()).
The given first parameter means: Stop looking forward when the element does not match.sub
. - wrapAll
Demo: http://jsfiddle.net/8MVKu/
For completeness, I have wrapped the set of <li>
elements in <li><ul>...</ul></li>
instead of a plain <ul>
.
Code:
$('.sub').each(function() {
if ($(this.parentNode).hasClass('wrapped')) return;
$(this).nextUntil(':not(.sub)').andSelf().wrapAll('<li><ul class="wrapped">');
});
$('ul.wrapped').removeClass('wrapped'); // Remove temporary dummy
回答2:
I would like to expand on Rob W's already awesome solution, providing a way to eliminate the temporary wrap class:
$(document).ready(function() {
$('li.sub').filter(':not(li.sub + li.sub)').each(function() {
$(this).nextUntil(':not(li.sub)').andSelf().wrapAll('<li><ul>');
});
});
http://jsfiddle.net/m8yW3/
Edit: The filter isn't even needed:
$('li.sub:not(li.sub + li.sub)').each(function() {
$(this).nextUntil(':not(li.sub)').andSelf().wrapAll('<li><ul>');
});
回答3:
I believe what you should have is this jQuery:
$('li.sub').wrap('<li><ul>');
This will properly wrap your <li>
elements in a new <ul>
tag while wrapped them within <li>
tags. The output of your example would then be:
<ul>
<li></li>
<li></li>
<li></li>
<li><ul><li class="sub"></li></ul></li>
<li><ul><li class="sub"></li></ul></li>
<li><ul><li class="sub"></li></ul></li>
<li></li>
<li></li>
<li><ul><li class="sub"></li></ul></li>
<li><ul><li class="sub"></li></ul></li>
<li><ul><li class="sub"></li></ul></li>
<li></li>
</ul>
来源:https://stackoverflow.com/questions/9022601/wrapping-consecutive-list-items-in-separate-groups-using-jquery