# VBForums CodeBank > CodeBank - JavaScript >  [JavaScript] Sprint CSS3 Selector System & SpringJS Library

## minitech

Finally, I've implemented the relationship selectors  :Roll Eyes (Sarcastic):  It was much easier than expected, actually. I've rebuilt my whole system from the ground up... and I minified it as I was writing it!  :Big Grin:  That's right - the whitespace, the variable names, everything  :Big Grin:  So enjoy! I'm working on giving it a better structure and actually finishing the selector system, then attaching my other JS library, but I don't have time today. See you then.

You can copy the most recent and compressed version right here (5.77KB), or download the full (readable) version:

Newest release is Sprint 2.0, which improves performance and general code structure. It doesn't support nth-xxx selectors yet (I didn't have time) but I'm working on it. Minified (6.89KB) is available below the link.

*Sprint 2.0 Dev Download, 05/09/2011* [11.2KB]



```
if(![].indexOf)Array.prototype.indexOf=function(b,a){for(a=a||0;a<this.length;)if(this[a++]===b)return a-1;return-1};String.prototype.startsWith=function(b){return this.length>=b.length&&this.substring(0,b.length)===b};String.prototype.endsWith=function(b){return this.length>=b.length&&this.substring(this.length-b.length)===b};
var Sprint={Error:function(b){this.message=b;this.toString=function(){return this.message}},getAllElementsIn:function(b){var a=[];(function d(a,b){from(a).each(function(a,g){g.nodeType===1&&(b.push(g),d(g,b))})})(b,a);return a},getAllElements:function(){return Sprint.getAllElementsIn(document.documentElement)},getSiblings:function(b){return b.parentNode?from(b.parentNode).where(function(a,b){return b.nodeType===1}).toArray():[b]},getInfo:function(b){for(var a={ATTR:{},CLASS:[],PSEUDO:[]},c=!1,d=!1,
g=null,e=[],h=/^[^a-zA-Z0-9_\-]$/,j=null,l=-1,i,f="";++l<b.length;){i=b.charAt(l);if(d)d=!1;else if(i==="\\"){d=!0;continue}else if(g)g===i&&(g=null);else if("'\"".indexOf(i)>-1)g=i;else if(e.length)"(){}".indexOf(e[e.length-1])+1==="(){}".indexOf(i)&&e.pop();else if("(){}".indexOf(i)>-1)e.push(i);else if(h.test(i)){if(j)switch(j){case "#":a.ID=f;break;case ".":a.CLASS.push(f);break;case "[":case ",":if(c){var k;(k=f.indexOf("="))>-1?a.ATTR[f.substring(0,k)]=f.substring(k+1):a.ATTR[f]=!0}break;case ":":a.PSEUDO.push(f)}else a.TAG=
f;i==="]"?c=!1:i==="["&&(c=!0);j=i;f="";continue}f+=i}if(j)switch(j){case "#":a.ID=f;break;case ".":a.CLASS.push(f);break;case "[":case ",":c&&((k=f.indexOf("="))>-1?a.ATTR[f.substring(0,k)]=f.substring(k+1):a.ATTR[f]=!0);break;case ":":a.PSEUDO.push(f)}else a.TAG=f;return a},compileSingle:function(b){var a='var t=l.nodeName?l.nodeName.toLowerCase():"",i=l.id?l.id.toLowerCase():"",c=l.className?" "+l.className.toLowerCase()+" ":"",s=Sprint.getSiblings(l),ss=from(s).where(function(k,v){return v.nodeName?v.nodeName.toLowerCase()===t:false;}).toArray(),si=s.indexOf(l),ssi=ss.indexOf(l);return ';
b.TAG&&b.TAG!=="*"&&(a+="t==='"+b.TAG.toLowerCase().replace(/[\\']/g,function(a){return"\\"+a})+"'&&");b.ID&&(a+="i==='"+b.ID.toLowerCase().replace(/[\\']/g,function(a){return"\\"+a})+"'&&");if(b.CLASS)for(var c=0;c<b.CLASS.length;c++)a+="c.indexOf(' "+b.CLASS[c].toLowerCase()+" ')>-1&&";if(b.PSEUDO)for(c=0;c<b.PSEUDO.length;c++){var d=b.PSEUDO[c],g,e="";if((g=d.indexOf("("))>-1)e=d.substring(g+1,d.length-1),d=d.substring(0,g);switch(d){case "first-child":a+="!si";break;case "first-of-type":a+="!ssi";
break;case "nth-child":break;case "nth-of-type":break;case "last-child":a+="si===s.length-1";break;case "last-of-type":a+="ssi===ss.length-1";break;case "nth-last-child":break;case "nth-last-of-type":break;case "only-child":a+="s.length===1";break;case "only-of-type":a+="ss.length===1";break;case "disabled":a+="l.disabled";break;case "enabled":a+="!l.disabled";break;case "checked":a+="l.checked";break;case "empty":a+="!l.childNodes.length";break;case "not":a+="!Sprint.isMatch('"+e.replace(/\\'/g,
function(a){return"\\"+a})+"')(0,l)";break;default:throw new Sprint.Error('Unrecognized pseudo-class "'+d+'".');}a+="&&"}b.ATTR&&from(b.ATTR).each(function(b,d){var e=b.charAt(b.length-1);a+="l.getAttribute('"+("$^*~|".indexOf(e)>-1?b.substring(0,b.length-1):b).replace(/\\'/g,function(a){return"\\"+a})+"')";if(typeof d==="string")switch(d=d.replace(/\\'/g,function(a){return"\\"+a}),e){case "$":a+=".endsWith('"+d+"')";break;case "^":a+=".startsWith('"+d+"')";break;case "*":a+=".indexOf('"+d+"')+1";
break;case "~":a+=".split(' ').indexOf('"+d+"')+1";break;case "|":a+=".split('-').indexOf('"+d+"')+1";break;default:a+="==='"+d+"'"}a+="&&"});a.substring(a.length-2)!=="&&"&&(a="return true  ");return new Function(["l"],a.substring(0,a.length-2)+";")},compileTree:function(b){for(var b=Sprint.tokenizeSelector(b),a=-1,c;++a<b.length;)if(", >~+".indexOf(b[a])>-1){for(c=a;--c>=0&&b[c]===" ";)b[c]=null;for(c=a;++c<b.length&&b[c]===" ";)b[c]=null}return from(b).where().select(function(a,b){return a&#37;2?b:
Sprint.compileSingle(Sprint.getInfo(b))}).toArray()},matchSingleTree:function(b,a){if(!a.length)return!0;if(!a[a.length-1](b))return!1;for(var c=a.length-3;c>=0;c-=2)switch(a[c+1]||" "){case " ":for(;;){if(!(b=b.parentNode))return!1;if(a[c](b))break}break;case ">":if(!(b=b.parentNode)||!a[c](b))return!1;break;case "+":for(;;){if(!(b=b.previousSibling))return!1;if(b.nodeType===1)if(a[c](b))break;else return!1}break;case "~":for(;;){if(!(b=b.previousSibling))return!1;if(a[c](b))break}}return!0},matchTree:function(b,
a){for(var c=[],d=0;d<a.length;d++)if(a[d]===","){if(Sprint.matchSingleTree(b,c))return!0;c=[]}else c.push(a[d]);return Sprint.matchSingleTree(b,c)},tokenizeSelector:function(b){for(var a=!1,c=null,d=[],g=[],e=-1,h,j="";++e<b.length;){h=b.charAt(e);if(a)a=!1;else if(h==="\\"){a=!0;continue}else if(c)c===h&&(c=null);else if("'\"".indexOf(h)>-1)c=h;else if(d.length)"(){}[]".indexOf(d[d.length-1])+1==="(){}[]".indexOf(h)&&d.pop();else if("(){}[]".indexOf(h)>-1)d.push(h);else if(", >~+".indexOf(h)>-1){g.push(j);
g.push(h);j="";continue}j+=h}g.push(j);return g},isMatch:function(b){var a=Sprint.compileTree(b);return function(b,d){return Sprint.matchTree(d,a)}},select:function(b){return from(Sprint.getAllElements()).where(Sprint.isMatch(b)).toArray()},selectIn:function(b,a){return from(Sprint.getAllElementsIn(a)).where(Sprint.isMatch(b)).toArray()}};
function from(b){if(!b)throw new Sprint.Error("null or undefined passed to Sprint:from().");var a={keys:[],values:[]};if(b.length)for(var c=0;c<b.length;c++)a.keys.push(c),a.values.push(b[c]);else if(b.childNodes)return from(b.childNodes);else for(c in b)b.hasOwnProperty(c)&&(a.keys.push(c),a.values.push(b[c]));a.length=a.keys.length;a.where=function(a){if(a){if(typeof a==="string")return this.where(new Function(["k","v"],"return "+a+";"));for(var b={},e=0;e<this.length;e++)a(this.keys[e],this.values[e])&&
(b[this.keys[e]]=this.values[e]);return from(b)}else return this.where(function(a,b){return b})};a.select=function(a){for(var b={},e=0;e<this.length;e++)b[this.keys[e]]=a(this.keys[e],this.values[e]);return from(b)};a.each=function(a){for(var b=0;b<this.length;b++)a(this.keys[b],this.values[b])};a.first=function(){return this.values[0]};a.last=function(){return this.values[this.length-1]};a.splitBy=function(a){if(typeof a==="function"){for(var b=[],e={},c=0;c<this.length;c++)a(this.keys[c],this.values[c])?
(b.push(e),e={}):e[this.keys[c]]=this.values[c];b.push(e);return from(b)}else return this.splitBy(function(b){return b===a})};a.limit=function(a){var b={},c=-1;if(typeof a==="function")for(;++c<this.length&&a(this.keys[c],this.values[c]);)b[this.keys[c]]=this.values[c];else for(;++c<Math.min(this.length,a);)b[this.keys[c]]=this.values[c];return from(b)};a.after=function(a){var b={},c=-1;if(typeof a==="function"){for(;++c<this.length&&!a(this.keys[c],this.values[c]););for(;++c<this.length;)b[this.keys[c]]=
this.values[c]}else if(a<this.length)for(c=a-1;++c<this.length;)b[this.keys[c]]=this.values[c];return from(b)};a.toArray=function(){return this.values};return a};
```

Sprint 1.1 Dev Download, 04/11/2011 [8.64KB]

*Version 0.2*: Fixed some pseudo-class problems, gave things better names, reorganized code, added whitespace, removed whitespace with Closure Compiler.
*Version 0.2 Minified* removed.

*Version 0.1* removed.

----------


## akhileshbc

Hi,
Could you please post some info about what it does ? Or some screenshots or anything.

Thanks  :wave:

----------


## minitech

It's a CSS3 selector system, like Sizzle (or jQuery, sort of) for JavaScript. You can use it like so (version 2.0 code):



```
Sprint.select("my#selector.for[an=example]:pseudo")
```

But the uncompressed code is self-explanatory.

----------

