I have a list of elements (well, nested lists of elements, really) that the user can reorder (using jQuery sortable()
). A simplified view of the structure is something like:
<div class="contentList">
<div class="content" />
<div class="content">
<div class="contentListInner">
<div class="triggerContent" />
<div class="triggerContent" />
<div class="triggerContent" />
</div>
<div class="contentListInner">
<div class="triggerContent" />
<div class="triggerContent" />
<div class="triggerContent" />
</div>
</div>
<div class="content" />
<div class="contentListInner">
<div class="triggerContent" />
<div class="triggerContent" />
<div class="triggerContent" />
</div>
<div class="contentListInner">
<div class="triggerContent" />
<div class="triggerContent" />
<div class="triggerContent" />
</div>
<div class="content" />
<div class="content" />
</div>
Each .content
inside of .contentList
is sortable, and each .triggerContent
inside of .contentListInner
is also sortable (independently of the other sections). Each element within these sections is numbered according to its position in its own list. So to continue with the example above, the correct numbering is:
<div class="contentList">
<div class="content" /> <!-- 1 -->
<div class="content"> <!-- 2 -->
<div class="contentListInner">
<div class="triggerContent" /> <!-- 1 -->
<div class="triggerContent" /> <!-- 2 -->
<div class="triggerContent" /> <!-- 3 -->
</div>
<div class="contentListInner">
<div class="triggerContent" /> <!-- 1 -->
<div class="triggerContent" /> <!-- 2 -->
<div class="triggerContent" /> <!-- 3 -->
</div>
</div>
<div class="content" /> <!-- 3 -->
<div class="contentListInner">
<div class="triggerContent" /> <!-- 1 -->
<div class="triggerContent" /> <!-- 2 -->
<div class="triggerContent" /> <!-- 3 -->
</div>
<div class="contentListInner">
<div class="triggerContent" /> <!-- 1 -->
<div class="triggerContent" /> <!-- 2 -->
<div class="triggerContent" /> <!-- 3 -->
</div>
<div class="content" /> <!-- 4 -->
<div class="content" /> <!-- 5 -->
</div>
There's an additional complication, in that each .triggerContent
can contain a new repetition of the entire structure, beginning again from .contentList
. This nested content, however, is essentially spurious and should be ignored for all practical purposes.
Anyhow, to apply the numbering to the inner sections (and simultaneously ignore content in the aforementioned nested sections), I'm currently using the following code:
$(".contentListInner").each(function() {
var taskNum = 1;
$(this).find(".triggerContent .taskTitle .left .number").each(function() {
if ($(this).parents(".triggerContent").length == 1) {
//FIXME: filtering on parents() is *slow*; find a faster approach
$(this).text("Task " + taskNum);
taskNum++;
}
});
});
This works, but as the FIXME
notes I found that filtering using .parents()
is incredibly slow. If I don't filter on .parents()
, then what happens is that nested .triggerContent
instances affect the count, and the numbering is incorrect (numbers jump like 1, 8, 17, 32, etc.).
Can anyone suggest an alternate approach that will produce the same results without the performance hit?
1 Answer 1
Try using the children selector: http://api.jquery.com/children/.
This only retrieves the first set of nested items (one level down vs. find which goes all the way down). I'm not sure how you're nested exactly with your other classes, but it would be something like this.
$(".contentListInner").each(function() {
$(this).children(".triggerContent").each(function(index, element) {
$(element).text("Task " + (index + 1));
});
});
-
\$\begingroup\$ Thanks, I had to go through a couple sets of
children()
to get this to work with the actual page structure, but that still seems faster than filtering using the result ofparents()
. \$\endgroup\$aroth– aroth2013年02月20日 03:38:46 +00:00Commented Feb 20, 2013 at 3:38
Explore related questions
See similar questions with these tags.