How to find the next element which has an ID attribute using jQuery
Solution 1
Try :
var nextSectionWithId = $(this).closest("section").nextAll("section[id]:first");
or
var nextSectionWithId = $(this).closest("section").nextAll("section[id]").filter(':first');
You cannot use next because next will look for a match only in the next element. So you can instead use nextAll combined with :first in the selector.
Update
You can use the first() method in jquery to fetch the first element in the collection as well which seems like a faster option.
var nextSectionWithId = $(this).closest("section").nextAll("section[id]").first();
Probably could be this reason:
Because :first is a jQuery extension and not part of the CSS specification, queries using :first cannot take advantage of the performance boost provided by the native DOM querySelectorAll() method. To achieve the best performance when using :first to select elements, first select the elements using a pure CSS selector, then use .filter(":first").
Coutesy @T.J. Crowder
Solution 2
Use .nextAll()
var nextSectionWithId = $(this).closest("section").nextAll("section[id]")[0].id;
var nextSectionWithId = $(this).closest("section").nextAll("section[id]").eq(0).attr('id');
var nextSectionWithId = $(this).closest("section").nextAll("section[id]").attr('id');
Digbyswift
.Net Developer based in Leeds, UK. I work mostly with MVC, Azure, NHibernate, Umbraco, ElasticSearch, Javascript, Lucene, EF and all that shabang. I'm also a black belt in karate.
Updated on June 22, 2022Comments
-
Digbyswift almost 2 years
When I click on a link, I need to find the next
<section>
that has an ID attribute and return its ID.So given the following markup and javascript, I would expect clicking on the link to write "section_3" to the console.
<section id="section_1"> <a href="#" class="findNext">Find</a> </section> <section></section> <section id="section_3"></section> <section id="section_4"></section>
and
$('a.findNext').click(function() { var nextSectionWithId = $(this).closest("section").next("section[id]"); if (nextSectionWithId) { var sectionId = nextSectionWithId.attr('id'); console.log(sectionId) } });
But this doesn't work. I have set the code up here in jsFiddle.
Any ideas why this is not working?
-
Kevin B over 10 years.next doesn't search through all following siblings, it only look at the immediate next one. it's in the api docs.
-
marcellscarlett over 10 yearsIf a selector is provided, it retrieves the next sibling only if it matches that selector. Your next section doesn't have an id.
-
Digbyswift over 10 yearsExcellent, I obviously misinterpreted it to mean "the next one to match the criteria" not "the next if it meets the criteria".
-
T.J. Crowder over 10 years@Digbyswift: You're not the first, by far, to have made that assumption.
-
-
PSL over 10 yearsI did not downvote, but reason could be that OP wants to find only the next element with the condition, not all of them.
attr('id')
works because it considers only the first element in the collection. -
Liam over 10 yearsnextAll returns a list not an individual element. You also need the :first selector
-
Liam over 10 yearsThat's better :) That said, it did seem to work, but the updated answer makes more sense.
-
Liam over 10 years@T.J.Crowder, You found it? Isn't that your question :) Good to know!!
-
T.J. Crowder over 10 yearsOf course, the updated answer will throw an exception if there aren't any following siblings with
id
s, whereas.nextAll("section[id]").attr("id")
will return theid
of the first such sibling (if any) orundefined
if none, rather than throwing. It's one of the few use-cases where using.attr("id")
can actually make sense (unlike the common horror$(this).attr("id")
one sees far too often :-) ). -
T.J. Crowder over 10 years@Liam: Yes, it is. :-) I meant "I found" as in "I learned" (in this case, from Nick [and experimentation]).
-
Tushar Gupta - curioustushar over 10 years@T.J.Crowder Check the updated the answer used
.eq(0)
. Ty for telling me that :) -
T.J. Crowder over 10 years@TusharGupta: There's zero reason to use
.eq(0)
if you're usingattr
as a getter. Whenattr
(orprop
, orcss
, ortext
, orhtml
, ...) is used as a getter, it always looks only at the first element in the set. I don't know what the answer originally looked like, but if someone downvoted it for doing.nextAll(...).attr("id")
, that was their bad, not yours. -
PSL over 10 years@T.J.Crowder Yeah probably let me add that as well... in the answer... :) Thanks!!
-
Tushar Gupta - curioustushar over 10 years@T.J.Crowder hahhah my 1st answer was that only but i got Down-vote on that .
-
T.J. Crowder over 10 years@TusharGupta: But note that the OP didn't say they wanted the value of the
id
. They said they wanted to find the section (to me that means the element, not theid
value). So.nextAll("section[id]").first()
or.nextAll("section[id]:first')
as in PSL's answer. -
Tushar Gupta - curioustushar over 10 years@T.J.Crowder Yes Sir . :)