JAME.Package('JAME.DOM');
JAME.Package('JAME.__STORE__');

new function() {

 var store      = {};
 JAME.__STORE__ = {
	add : function(elm,key,val) {
		if(!store[elm]){
			store[elm]={};
		}
		store[elm][key]=val;	
	},
	remove : function(elm,key) {
		if(store[elm] && store[elm][key]){
			store[elm][key]=null;
			delete store[elm][key];
		}	
	},
	get : function(elm,key) {
		if(!store[elm])
			return undefined;
		return store[elm][key];
	},
	removeAll : function(elm){
		if(store[elm]){
			for(var prop in store[elm]){
				store[elm][prop]=null;
				delete store[elm][prop];
			}
		}		
	},
	cleanup : function() {
		for(var obj in store){
			JAME.__STORE__.removeAll(obj);
		}
		store=null;
	}
 };

}



JAME.DOM = {
   lastNode : function (elm) {
      if (!elm.lastChild) return false;
      elm = elm.lastChild;
      return (elm && elm.nodeType!=1)
          ? JAME.DOM.prevNode(elm) 
          : elm;
   },
   prevNode : function(elm) {
      if (!elm)  return false; 
      do {
        elm = elm.previousSibling;
      } while (elm && elm.nodeType!=1);
      return elm;
   },
   nextNode : function(elm) {
       if (!elm) return false;
       do { elm = elm.nextSibling; } while (elm && elm.nodeType!=1);
       return elm;
   },
   firstNode : function(elm) {
      if (!elm.firstChild) return false;
      elm = elm.firstChild;
      return (elm && elm.nodeType!=1)
             ? JAME.DOM.nextNode(elm) 
             : elm;
   },
   getText : function(elm) {
      var txt=[];
      elm = elm.childNodes;
      for(var i=0,ln=elm.length;i<ln;i++) {
         txt.push(
              (elm[i].nodeType!=1) 
              ? elm[i].nodeValue 
              : JAME.DOM.getText(elm[i])
        )
      }
      return txt.join('');
   },
   Ready : function (f) {
      if (JAME.DOM.Ready.loaded) return f();

	  JAME.Events.addListener(window,'load',function() { setTimeout(JAME.DOM.__isDOMReady,0)});

      if (!JAME.DOM.Ready.pool) {
          JAME.DOM.Ready.todo = [ f ];
          JAME.DOM.Ready.pool = setInterval(JAME.DOM.__isDOMReady,10);
      }
      else
        JAME.DOM.Ready.todo.push(f);
   },
   __isDOMReady : function () {
      if (JAME.DOM.Ready.loaded) return false;

		try {
			var d = document;
			if(window.attachEvent){
				d.documentElement.doScroll('left');
			}
		}catch(e){
			return;
		}

      if (document && document.body && document.getElementById) {

         clearInterval(JAME.DOM.Ready.pool);

         for (var i = 0,ln=JAME.DOM.Ready.todo.length; i < ln; i++){
            JAME.DOM.Ready.todo[i]();
		 }
         JAME.DOM.Ready.todo = null;
         JAME.DOM.Ready.loaded = true;
      }
    },
    createNode : function(node) {
        return document.createElement(node);
    },
    wrapNode : function(elm,wrapper) {
        var oWrapper = JAME.DOM.createNode(wrapper);
        var elmClone = elm.cloneNode(true);
        oWrapper.appendChild(elmClone);
        oparent = elm.parentNode;
        JAME.DOM.insertNodeAfter(oWrapper,elm);
        oparent.removeChild(elm);
        return oWrapper;
    },
    insertNodeBefore : function(elm, targetElm ) {
         var oparent = targetElm.parentNode;
         oparent.insertBefore(elm, targetElm);
    },
    insertNodeAfter : function(elm, targetElm ) {
       var oparent = targetElm.parentNode;
       if (targetElm == oparent.lastChild)
           oparent.appendChild(elm);
        else
           oparent.insertBefore(elm,JAME.DOM.nextNode(targetElm));
    },
	contains : function(str,item,sep) {
		return ((sep+str+sep).indexOf(sep+item+sep)>-1);
	},
	hasClass : function(elm,sClass){
		return JAME.DOM.contains(elm.className,sClass,' ');
	},
    hasAttr:function(attr,val,scope) {
        if(scope[attr]==val) return scope;
        if(parseInt(scope[attr])===val) return scope;
        if(parseInt(scope[attr])===parseInt(val)) return scope;
		return undefined;
    },
    byTags:function(tag,scope) {

        if(scope===undefined) return JAME.DOM.byTag(tag);
        scope = (scope.constructor!==Array) ? [scope] : scope;

        var elms = [];
        for(var i = 0; i < scope.length; i++) { 
            var s = scope[i];
            var r = JAME.DOM.byTag(tag,s);
            if(r.length>0) {
               for(var j = 0; j < r.length; j++) {
					elms.push(r[j]);
			   }
            }
        }
        return elms;
    },
    byAttr:function(attr,val,scope) {
        scope = (scope.constructor!==Array) ? [scope] : scope;
        var elms=[];
        for(var i=0;i<scope.length;i++) { 
            var s=scope[i];
            var r= JAME.DOM.hasAttr(attr,val,s);
            if(r) elms.push(r);
        }
        return elms;
    },
	byClass: function(t,s) {
        var ar = [];
        s      = s || document.body.getElementsByTagName('*');
        var e;
        for(var i=0,ln=s.length;i<ln;i++) {
            e=s[i];
            if (e.className) {
				var reg = new RegExp('\s*'+t+'\s*');
				if (reg.test(e.className)) 
					ar.push(e);
			}
        }
        return ar;
    },
    byTag: function(tag,scope) {
        if(tag=="body") return document.body;
        var elms = (scope || document).getElementsByTagName(tag);
        var ar = [];
        for(var i=0,ln=elms.length;i<ln;i++) ar.push(elms[i]);
        return ar;
    },
	addClass : function(elm,sClass){
		elm.className = (elm.className) ? elm.className+' '+ sClass : sClass;
	},
	removeClass : function(elm,sClass){
		var str = elm.className;
		elm.className = str.replace(new RegExp('\s*'+sClass+'\s*'),'');
	},
	toggleClass :  function(elm,sClass){
		JAME.DOM[JAME.DOM.hasClass(elm,sClass) ? 'removeClass': 'addClass'](elm,sClass);
	},
	addKey : function(elm,key,value) {
		JAME.__STORE__.add(elm,key,value);
	},
	getKey : function(elm,key) {
		JAME.__STORE__.get(elm,key);
	},
	removeKey : function(elm,key) {
		JAME.__STORE__.remove(elm,key);
	},
	removeAllKeys : function(elm) {
		JAME.__STORE__.removeAll(elm);
	},
    Export : function() {
        JAME.Exporter(JAME.DOM);
    }
};
