/**
 *  Prototype Xtensions 
 *  
 *  @author    Simon Martins
 *  @copyright (c) 2008 Netatoo SARL <http://www.netatoo.fr>
 *  @license   MIT License <http://www.prototypextensions.com/#main=license>
 *
 */
 
Prototype.X={Version:'0.1.2',Required:{Prototype:'1.6.0.2',Scripty:'1.8.1'},Require:function(){if(typeof Prototype=='undefined'||typeof Element=='undefined'||typeof Element.Methods=='undefined'||this.convertVersionString(Prototype.Version||0)<this.convertVersionString(this.Required.Prototype)){throw("Prototype.Xtensions require Prototype.js >= "
+this.Required.Prototype);}
if(typeof Scriptaculous=='undefined'||typeof Effect=='undefined'||this.convertVersionString(Scriptaculous.Version||0)<this.convertVersionString(this.Required.Scripty)){throw("Prototype.Xtensions require Scriptaculous >= "
+this.Required.Scripty);}},convertVersionString:function(versionString){var v=versionString.replace(/_.*|\./g,'');v=parseInt(v+'0'.times(4-v.length));return versionString.indexOf('_')>-1?v-1:v;}};Prototype.X.Require();Prototype.X.Registry={};(function(){var nav=navigator;var userAgent=ua=navigator.userAgent;var v=nav.appVersion;var version=parseFloat(v);Prototype.X.Browser={IE:(Prototype.Browser.IE)?parseFloat(v.split("MSIE ")[1])||0:0,Firefox:(Prototype.Browser.Gecko)?parseFloat(ua.split("Firefox/")[1])||0:0,Camino:(Prototype.Browser.Gecko)?parseFloat(ua.split("Camino/")[1])||0:0,Flock:(Prototype.Browser.Gecko)?parseFloat(ua.split("Flock/")[1])||0:0,Opera:(Prototype.Browser.Opera)?version:0,AIR:(ua.indexOf("AdobeAIR")>=0)?1:0,Mozilla:(Prototype.Browser.Gecko||!this.Khtml)?version:0,Khtml:(v.indexOf("Konqueror")>=0&&this.safari)?version:0,Safari:(function(){var safari=Math.max(v.indexOf("WebKit"),v.indexOf("Safari"),0);return(safari)?(parseFloat(v.split("Version/")[1])||((parseFloat(v.substr(safari+7))>=419.3)?3:2)||2):0;})()};})();$unixTime=function(inSeconds){var time=new Date();time=time.getTime();if(inSeconds==true)time=time/1000;return time;};Object.extend(String.prototype,{ucfirst:function(){return this.charAt(0).toUpperCase()+this.substring(1);}});Object.extend(Number.prototype,{minute:function(){return this*60;},hour:function(){return this*3600;},day:function(){return this*86400;},week:function(){return this*604800;},month:function(){return this*2629743.83;},year:function(){return this*31556926;},time:function(){return(this.toMs())+$unixTime();},toSeconds:function(){return this*1000;},toMs:function(){return this/1000;}});Object.extend(Class,{accessors:{createAccessors:function(options,entries){var entries=(!Object.isArray(entries))?Object.keys(entries):entries;entries.each(function(name){var cname=(name.camelize()).ucfirst();(function(name,that){that['get'+cname]=function(){return options[name];};that['set'+cname]=function(value){options[name]=value;return that;};})(name,this);},this);},setOptions:function(defaultOptions,userOptions,accessorize){var access=(Object.isUndefined(accessorize))?false:accessorize;if(!defaultOptions)defaultOptions={};Object.extend(defaultOptions,userOptions||{});if(accessorize)this.createAccessors(defaultOptions,defaultOptions);}}});var EventManager=Class.create({initialize:function(scope){this.scope=scope;this.events=new Hash();},addObserver:function(name){return this.events.set(name,new Hash());},observe:function(name,callback){var observers=this.events.get(name);if(!observers)observers=this.addObserver(name);if(!Object.isFunction(callback)){throw('EventManager.observe : callback must be an js function');}
var i=this.events.get(name).keys().length;observers.set(i,callback.bind(this.scope));return this;},notify:function(name){var observers=this.events.get(name);if(observers){var args=$A(arguments).slice(1);observers.each(function(callback){if(Object.isFunction(callback[1])){callback[1].apply(this.scope,args);}});}
return this;}});var Cookie={events:new EventManager(this),isEnabled:function(){this.set('enabled','ok');var test=this.get('enabled');this.unset('enabled');return(test=='ok')?true:false;},observe:function(name,callback){this.events.observe(name,callback);return this;},set:function(name,value,options,noevents){var expire='';var o=options||{};var path=(o.path)?'; path='+o.path:'; path=/';var domain=(o.domain)?'; domain='+o.domain:'';var secure=(o.secure==true)?'; secure':'';var date=new Date();if(Object.isNumber(o)){date.setTime(date.getTime()+(o*1000));expire='; expires='+date.toGMTString();}else if(o.expires){date.setTime(date.getTime()+(o.expires*1000));expire='; expires='+date.toGMTString();}
document.cookie=name+"="+value+expire+path+domain+secure;if(!noevents)this.events.notify('set',name,value,options);return this;},get:function(name){this.events.notify('get',name);var nameEQ=name+"=";var ca=document.cookie.split(';');for(var i=0;i<ca.length;i++){var c=ca[i];while(c.charAt(0)==' ')
c=c.substring(1,c.length);if(c.indexOf(nameEQ)==0)
return c.substring(nameEQ.length,c.length);}
return null;},unset:function(name){this.events.notify('unset',name);this.set(name,'',-1,true);return this;}};var History={__altered:false,__currentHash:null,__previousHash:null,__iframe:false,__title:false,init:function(){var inst=this;var hash=location.hash.substring(1);this.hash=$H(hash.toQueryParams());this.__currentHash=hash;this.__previousHash=hash;this.__title=document.title;if(Prototype.Browser.IE&&Prototype.X.Browser.IE<8){document.observe('dom:loaded',function(e){if(!$('px-historyframe')){History.__iframe=new Element('iframe',{name:'px-historyframe',id:'px-historyframe',src:'',width:'0',height:'0',style:{visibility:'hidden'}});document.body.appendChild(History.__iframe);History.setHashOnIframe(inst.hash.toQueryString());}});}},set:function($name,$value){this.__previousHash=this.hash.toQueryString();this.hash.set($name,$value);this.apply();},get:function($name){return this.hash.get($name);},unset:function($name){this.hash.unset($name);this.apply();},update:function(){this.__previousHash=this.hash.toQueryString();var hash=window.location.hash.substring(1);if(Prototype.Browser.IE&&Prototype.X.Browser.IE<8&&this.__iframe){var hashInFrame=this.getHashOnIframe();if(hashInFrame!=hash){hash=hashInFrame;}}
this.hash=$H(hash.toQueryParams());this.__currentHash=hash;},apply:function(){var newHash=this.hash.toQueryString();window.location.hash=newHash;if(Prototype.Browser.IE&&Prototype.X.Browser.IE<8&&this.__iframe){if(this.__currentHash!=newHash)
{this.setHashOnIframe(newHash);}
else if(newHash!=this.getHashOnIframe())
{this.setHashOnIframe(newHash);}}},isAltered:function(){if(this.__altered==true){return true;}
this.__altered=false;return(History.__currentHash!=History.__previousHash);},setHashOnIframe:function(hash){try{var doc=History.__iframe.contentWindow.document;doc.open();doc.write('<html><body id="history">'+hash+'</body></html>');doc.close();}catch(e){}},getHashOnIframe:function(){var doc=this.__iframe.contentWindow.document;if(doc&&doc.body.id=='history'){return doc.body.innerText;}else{return this.hash.toQueryString();}},setTitle:function(title){if(document.title){document.title=title;}},getTitle:function(){return this.__title;}};History.init();History.Registry={hash:new Hash(),set:function($config){if(typeof($config)!='object'){throw('History.Registry.set : $config must be an javascript object');}
if(!$config.id||!Object.isString($config.id)){throw('History.Registry.set : $config.id must be an string');}
if(!$config.onStateChange||!Object.isFunction($config.onStateChange)){throw('History.Registry.set : $config.onStateChange '
+'must be an javascript callback function');}
if(!$config.defaultValue||!Object.isString($config.defaultValue)){$config.defaultValue='';}
this.hash.set($config.id,$config);},get:function($id){return this.hash.get($id);},unset:function($id){this.hash.unset($id);}}
History.Observer={delay:0.2,interval:null,started:false,start:function(){if(this.started)return;this.interval=new PeriodicalExecuter(History.Observer.dispatch,this.delay);this.started=true;},stop:function(){if(!this.started)return;this.interval.stop();this.started=false;},dispatch:function(){History.update();if(History.isAltered()){History.hash.each(function(pair){var registry=History.Registry.get(pair.key);if(registry){registry.onStateChange.bind(History)(pair.value);}});}}};Ajax.History={types:['Request','Updater'],observe:function($type,$id,$url,$options){var getter=Ajax.History.Registry.get($id);var currentVersion=0;var output=false;if(this.types.indexOf($type)==-1){throw('Ajax.History.observer() -> type '+$type+' is invalid !');}
if(getter==undefined){currentVersion=($options.history.state)?$options.history.state:0;var hash=new Hash();hash.set(currentVersion,$options);Ajax.History.Registry.set($id,hash);}else{currentVersion=($options.history.state)?$options.history.state:this.getCurrentVersion($id);getter.set(currentVersion,$options);}
this.addCallback($type,$id);return currentVersion;},addCallback:function($type,$id){History.Observer.start();History.__altered=true;if(!Object.isUndefined(History.Registry.get($id)))return;History.Registry.set({id:$id,onStateChange:function(state){var options=Ajax.History.Registry.get($id).get(state.toString());var request=null;if(Object.isUndefined(options))return;if(options.history.cache==true&&options.history.__request){new Ajax.Cache(options.history.__request);}else{if($type=='Request'){request=new Ajax.Request(options.history.__url,options);}else if($type=='Updater'){request=new Ajax.Updater(options.container,options.history.__url,options);}
options.history.__request=request;}
History.__altered=false;if(Object.isFunction(options.history.onStateChange)){options.history.onStateChange(state);}}});},getCurrentVersion:function($id){var getter=Ajax.History.Registry.get($id);return Object.isUndefined(getter)?0:getter.keys().length;}};Ajax.History.Registry=new Hash();Ajax.History.Features={id:null,state:false,cache:false,onStateChange:null,__url:null,__request:null};Ajax.History.Request=Class.create({initialize:function($url,$options){this.options={};Object.extend(this.options,$options);if(this.options.history){var tmpOpt=Object.clone(Ajax.History.Features);Object.extend(tmpOpt,this.options.history);this.options.history=tmpOpt;this.options.history.__url=$url;if(Object.isUndefined($options.history.id)){throw('Ajax.History.Request error : you must define historyId');}else{var id=this.options.history.id;}
var version=Ajax.History.observe('Request',id,$url,this.options);History.set(id,version);}else{return new Ajax.Request($url,this.options);}}});Ajax.History.Updater=Class.create({initialize:function($container,$url,$options){this.options={};Object.extend(this.options,$options);if(this.options.history){var tmpOpt=Object.clone(Ajax.History.Features);Object.extend(tmpOpt,this.options.history);this.options.history=tmpOpt;this.options.history.__url=$url;if(Object.isUndefined($options.history.id)){var id=(Object.isString($container))?$container:$container.id;}else{var id=this.options.history.id;}
this.options.container=$container;var version=Ajax.History.observe('Updater',id,$url,this.options);History.set(id,version);}else{return new Ajax.Updater($container,$url,this.options);}}});Ajax.Cache=Class.create(Ajax.Base,{_complete:false,initialize:function($super,request){$super(request.options);request._complete=false;this.transport=request.transport;this.request(request.url);return this;},request:function(url){this.url=url;this.method=this.options.method;var params=Object.clone(this.options.parameters);try{var response=new Ajax.Response(this);if(this.options.onCreate)this.options.onCreate(response);Ajax.Responders.dispatch('onCreate',this,response);if(this.options.asynchronous)this.respondToReadyState.bind(this).defer(1);this.onStateChange();}
catch(e){this.dispatchException(e);}}});Object.extend(Ajax.Cache.prototype,{respondToReadyState:Ajax.Request.prototype.respondToReadyState,onStateChange:Ajax.Request.prototype.onStateChange,success:Ajax.Request.prototype.getStatus,getStatus:Ajax.Request.prototype.getStatus,isSameOrigin:Ajax.Request.prototype.isSameOrigin,getHeader:Ajax.Request.prototype.getHeader,evalResponse:Ajax.Request.prototype.evalResponse,dispatchException:Ajax.Request.prototype.dispatchException});Ajax.Request=Class.create(Ajax.Request,{initialize:function($super,url,options){$super(url,options);return this;}});Ajax.Request.Events=['Uninitialized','Loading','Loaded','Interactive','Complete'];Ajax.Updater=Class.create(Ajax.Updater,{initialize:function($super,container,url,options){$super(container,url,options);return this;}});Prototype.X.Registry.Tabs={};var Tabs=Class.create(Class.accessors,{initialize:function(element,options){var inst=this;this.items=[];this.options={element:null,elementId:null,tabsId:null,tabsContainer:null,domTabs:{},requests:{},selectEvent:'click',defaultActive:0,currentActive:null,history:true,sortable:false,sortableOptions:{tag:'li',overlap:'horizontal',constraint:'horizontal'},deletable:false},this.setOptions(this.options,options,true);this.setElement(element);this.setElementId(this.getElement().id);this.setTabsId(this.getElementId().camelize());var tabs=this.getElement().firstDescendant().childElements();this.setDomTabs(tabs);this.setTabsContainer(this.getElement().firstDescendant());this.__buildItems();this.__selectByDefault();},__buildItems:function(){var inst=this;var panels=this.getElement().childElements();var tabs=this.getDomTabs();panels.shift();tabs.each(function(elem,index){if(!inst.items[index]){var requestOptions={};var seekedOptions=inst.options.requests[panels[index].id];if(seekedOptions){requestOptions=seekedOptions;}
inst.items[index]=new TabsItem(inst,{item:elem,panel:panels[index],request:requestOptions,effect:inst.effect});}});},__selectByDefault:function(){var inst=this;if(this.getHistory()){History.Observer.start();History.Registry.set({id:this.getTabsId(),onStateChange:function(tabName){var getter=inst.get(tabName,false);if(getter){if(Prototype.Browser.Opera)
getter.__select();else
getter.select();}
this.setTitle(this.getTitle()+' ('+tabName.ucfirst()+')');}});var value=History.get(this.getTabsId());var tabs=this.get(value,false);if(value&&tabs){tabs.select();}else{this.get(this.getDefaultActive()).select();}}else{this.get(this.getDefaultActive()).select();}},makeSortable:function(options){if(this.getSortable())return;var opt=Object.extend(this.getSortableOptions(),options||{});Sortable.create(this.getTabsContainer().identify(),opt);this.setSortable(true)},show:function(index,select){var getter=this.get(index);if(getter){getter.show(select);}},hide:function(index){var getter=this.get(index);if(getter){getter.hide();}},select:function(index){var getter=this.get(index);if(getter){getter.select();}},selectFirst:function(){this.items.each(function(elem,index){if(elem.getDisplay()){elem.select();throw $break;}});},selectLast:function(){this.items.last().select();},unSelectAll:function(without){without=(Object.isUndefined(without))?false:without;this.items.each(function(tabs,index){if(without){if(tabs!=without)tabs.unSelect();}else{tabs.unSelect();}});},get:function(index,throwHandler){var inst=this;var error='Error on Tabs.get() : index '+index+' is undefined ! ';if(Object.isUndefined(throwHandler)){throwHandler=true;}
if(Object.isNumber(index)){if(!this.items[index]){if(throwHandler)throw(error);else return false;}
return this.items[index];}else if(Object.isString(index)){var seeked=false;var itemOut=null;this.getDomTabs().each(function(elem,id){if(inst.items[id]){var item=inst.items[id];var itemId=item.getPanel().id;if(itemId==index){seeked=true;itemOut=item;}}});if(!seeked){if(throwHandler)throw(error);else return false;}
return itemOut;}
if(throwHandler)throw(error);else return false;}});var TabsItem=Class.create(Class.accessors,{initialize:function(tabs,options){this.options={tabs:null,item:null,panel:null,display:true,request:null,loaded:false,titleElement:null,selected:false,iframe:null};this.setOptions(this.options,options,true);this.setTabs(tabs);this.__getTitleElement();this.__setEvents();this.__voidAhref();this.events=new EventManager(this);},__setEvents:function(){var inst=this;var selectEvent=this.getTabs().getSelectEvent();$(this.getItem()).observe(selectEvent,this.select.bindAsEventListener(this));},__getTitleElement:function(){this.setTitleElement(this.getItem().firstDescendant());},__voidAhref:function(){var a=this.getItem().firstDescendant();if(a.hasAttribute('href')){a.href='javascript:void(0)';}},observe:function(eventName,callback){this.events.observe(eventName,callback);return this;},getTitle:function(){return this.getTitleElement().innerHTML;},setTitle:function(title){this.getTitleElement().update(title);},select:function(){if(this.getTabs().getHistory()){History.set(this.getTabs().getTabsId(),this.getPanel().id);History.setTitle(History.getTitle()+' ('+this.getPanel().id.ucfirst()+')');}
this.__select();},__select:function(){if(this.getTabs().getHistory()){History.setTitle(History.getTitle()+' ('+this.getPanel().id.ucfirst()+')');}
this.getTabs().unSelectAll(this);this.getItem().className='tab-show';this.getPanel().className='panel-show';this.getPanel().show();this.load();this.events.notify('select',this);this.setSelected(true);},unSelect:function(){this.getItem().className='tab-hide';this.getPanel().className='panel-hide';if(this.getSelected()){this.events.notify('unselect',this);}
this.setSelected(false);},show:function(select){if(this.getDisplay())return;this.events.notify('show',this);this.getItem().show();this.getPanel().show();this.setDisplay(true);if(select===true)this.select();},hide:function(){if(!this.getDisplay())return;this.events.notify('hide',this);this.getItem().hide();this.getPanel().hide();this.setDisplay(false);this.getTabs().selectFirst();},toggle:function(select){if(!this.getDisplay()){return this.show(select);}
this.hide();},load:function(options){var inst=this;var options=Object.extend(options||{},this.getRequest().options||{});if(this.getRequest().url!=null&&!this.getLoaded()){var loadType=this.getRequest().type;if(loadType=='ajax'){options=Object.clone(Object.extend({onLoading:function(response,json,tabs){tabs.setTitle('Loading...');}},options));var onCreate=options.onCreate;options.onCreate=(function(response){if(Object.isFunction(onCreate))onCreate(response,inst);}).bind(this);var onSuccess=options.onSuccess;options.onSuccess=(function(response,json){inst.setLoaded(true);if(Object.isFunction(onSuccess))onSuccess(response,json,inst);}).bind(this);var onFailure=options.onFailure;options.onFailure=(function(response,json){if(Object.isFunction(onFailure))onFailure(response,json,inst);}).bind(this);var onComplete=options.onComplete;options.onComplete=(function(response,json){inst.setTitle(inst.options.tmpTitle);if(Object.isFunction(onComplete))onComplete(response,json,inst);}).bind(this);var onLoading=options.onLoading;options.onLoading=(function(response,json){inst.options.tmpTitle=inst.getTitle();if(Object.isFunction(onLoading))onLoading(response,json,inst);}).bind(this);var onLoaded=options.onLoaded;options.onLoaded=(function(response,json){if(Object.isFunction(onLoaded))onLoaded(response,json,inst);}).bind(this);var onException=options.onException;options.onException=(function(request,exception){if(Object.isFunction(onException))onException(request,exception,inst);}).bind(this);new Ajax.Updater(this.getPanel(),this.getRequest().url,Object.extend({onLoading:function(tabs){tabs.setTitle('Loading...');}},options||{}));}
else if(loadType=='iframe'){this.iframe=new Element('iframe',{name:this.getRequest().id,id:this.getRequest().id,src:this.getRequest().url});this.getPanel().update(this.iframe);this.setLoaded(true);}}},reload:function(options){this.setLoaded(false);this.load(options);}});Element.addMethods({tabs:function(element,options){var id=element.id.camelize();if(!Prototype.X.Registry.Tabs[id]){Prototype.X.Registry.Tabs[id]={};var instance=new Tabs(element,options);Prototype.X.Registry.Tabs[id].instance=instance;return instance;}
var instance=Prototype.X.Registry.Tabs[id].instance;instance.setOptions(instance.options,options,true);return instance;}});
