Since the getElementsByTagName() function is new (DOM-1?) I wanted another more reliable method to get a reference to an element based on its tag name/id.
Edit- Without using a framework, since I need to cut down on size; so 10-20K for a framework is unacceptable. I just need the JS code that can fetch an element
Since the getElementsByTagName() function is new (DOM-1?) I wanted another more reliable method to get a reference to an element based on its tag name/id.
Edit- Without using a framework, since I need to cut down on size; so 10-20K for a framework is unacceptable. I just need the JS code that can fetch an element
Share Improve this question edited May 4, 2009 at 14:41 TStamper 30.4k10 gold badges68 silver badges73 bronze badges asked May 4, 2009 at 14:36 Robin RodricksRobin Rodricks 114k146 gold badges414 silver badges617 bronze badges 4- Done properly the 20k or so for jquery is only downloaded once. – cletus Commented May 4, 2009 at 14:43
- 4 getElementsByTagName() is indeed DOM level 1. It has support going back to IE5, Opera 7, and all versions of Mozilla and Safari. What browser are you worried about? NN3? ;) Ref: w3.org/TR/REC-DOM-Level-1/… – JPot Commented May 4, 2009 at 14:46
- @Jeremy: seriously, are you by any chance aiming for an older browser(s) that does not have support for getElementsByTagName()? – JPot Commented May 4, 2009 at 14:52
- There's also getElementById(), but the browsers that support it already support getElementsByTagName(). – Powerlord Commented May 4, 2009 at 14:57
5 Answers
Reset to default 15getElementsByTagName is not new. It is supported since IE5, FF1 and Opera 7 according to w3schools
[edit] Thanks for pointing this out. It was indeed supported since Opera 7.
As mentioned, getElementsByTagName is not new...
I think you're going to get about 10 references to jQuery.
Returns all the paragraph elements:
$('p').length
If 19kb is too big, and you just want to do element selection, something like sizzle works well, at about 4kb. The only thing I would note is that you're probably going to end up needing something that's in jQuery anyway.
http://sizzlejs.com/
Queries are very similar:
Sizzle("li");
19kb is a really small one-time price to pay for the power of jQuery.
If all you want to do is select elements, it may be smart to just use the sizzle selector engine and not a full blown library. I would go with the full library, but, going with a selector engine might be useful in limited circumstances.
Sizzle is the CSS selector engine that powers jQuery.
http://sizzlejs.com/
Or prototype, etc. You'll need to use one of these javascript glue libraries to achieve this. All of them will call this function if it exists, but fake it otherwise.
Here is an implementation based on the jQuery 1.12.4 implementation. It uses getElementsByTagName if available. If not, it uses querySelectorAll if available. If not, it falls back on recursively traversal. jQuery 1.12.4 supports older browsers, such as IE6, according to themselves.
function getElementsByTagName( node, tagName ) {
if (tagName == '*') {
tagName = undefined;
}
var merge = function( first, second ) {
var len = +second.length,
j = 0,
i = first.length;
while ( j < len ) {
first[ i++ ] = second[ j++ ];
}
// Support: IE<9
// Workaround casting of .length to NaN on otherwise arraylike objects (e.g., NodeLists)
if ( len !== len ) {
while ( second[ j ] !== undefined ) {
first[ i++ ] = second[ j++ ];
}
}
first.length = i;
return first;
},
nodeName = function( elem, name ) {
return elem.nodeName && elem.nodeName.toLowerCase() === name.toLowerCase();
},
elems, elem,
i = 0,
context = node,
tag = tagName,
found = typeof context.getElementsByTagName !== "undefined" ?
context.getElementsByTagName( tag || "*" ) :
typeof context.querySelectorAll !== "undefined" ?
context.querySelectorAll( tag || "*" ) :
undefined;
if ( !found ) {
for ( found = [], elems = context.childNodes || context;
( elem = elems[ i ] ) != null;
i++
) {
if ( !tag || nodeName( elem, tag ) ) {
found.push( elem );
} else {
merge( found, getElementsByTagName( elem, tag ) );
}
}
}
return found;
/* return tag === undefined || tag && nodeName( context, tag ) ?
merge( [ context ], found ) :
found;*/
}
I took the getAll() internal function of jQuery 1.12.4 and copied in the two helper functions it needs (jQuery.nodeName and jQuery.merge). I also made sure you can call it with "*" as tagName by adding a few lines in the top of the function. Finally, at the end of the function I commented out some functionality, which adds current node to result (if it matches), and simply returns the found nodes.
Be aware that the function in some cases returns an HTMLCollection, and in other circumstances returns an Array. Also beware that when "*" is passed as tagname, output differs depending on browser: The Element.prototype.getElementsByTagName does not return TextNodes, but the recursive traversal does.
Alternatively, you could use picoQuery. picoQuery is an implementation of jQuery, where you can select which methods you need in an online builder. in this case, you need no methods, as selection is part of core, and the build is only 1kb gzipped. picoQuery is written for modern browsers, but falls back to jQuery 1.12.4 for older browsers.