In my recent exploration of jQuery, I came across the need to walk the DOM tree, depth-first.
After playing around in FireBug, I came up with an ad-hoc soltution that involves:
.offset() to figure out where my element positions were going fractional)The initial code I entered into FireBug for it looked like this:
// sets the first node var node = $('body'); // walks to the next element and spits it and it's offset out; // repeat as many times as you want (until the node is "[]" and the offset is "0, 0") [ node = (node.children(':first')[0]) ? node.children(':first') : ( (node.next()[0]) ? node.next() : node.closest(':not(:last-child)').next() ), node.offset() ];
And it worked! From my tests, it walks each node, as expected.
Then I got to thinking. This would be useful all over. I could… make it a jQuery-ized function! So I tried this:
jQuery.fn.walk = function() { var firstChild = this.children(':first'); if (firstChild[0]) { return firstChild; } else { var nextSibling = this.next() if (nextSibling[0]) return nextSibling; else return this.closest(':not(:last-child)').next(); } }
Then you just walk from the initial element node like this:
node = node.walk();
Once I had this working, I thought, “I can do better still”. After poking around on John Resig’s blog a bit, and playing with different ways of allowing an expression for an argument, I realized that this is either going to be really slow (by grabbing all the elements in the document and finding the next logical one) or really really slow (by using recursion in a fashion similarto above). It might be plausible with full XPath, but I just don’t know enough about Sizzle to make it work efficiently.
Perhaps someday, though! For now, it’s pretty easy to just put the walk in a loop until you get the element type you’re looking for. Best of luck and be sure to correct me if I’m doing this “the hard way”!
Definitely hand-crafted and maintained by Slippy Douglas. All questions/comments may be directed to him, whether he likes it or not.
Powered by Radiant CMS, running on Rails, running on Ruby Enterprise Edition, running on Phusion Passenger, running on Apache, running on Debian Linux, running on Love.
Part of the Slippy Douglas family of sites: SlippyD.com | ClutterApp | DeliTag | R•Node.net | Nectar Games | 6BITT.com
Copyright © 2003-2009, Slippy Douglas. All rights reserved, unless otherwise specified or conflicting, in which case:
“Copyright © the-appropriate-year, the-appropriate-copyright-holder.”