
var Evt=YAHOO.util.Event,Dom=YAHOO.util.Dom;if(typeof(Prototype)=='undefined')
{var $=function(x){return Dom.get(x);};var $F=function(x){return Dom.get(x).value;};}
var Browser={IE:!!(window.attachEvent&&!window.opera),Opera:!!window.opera,WebKit:navigator.userAgent.indexOf('AppleWebKit/')>-1,Gecko:navigator.userAgent.indexOf('Gecko')>-1&&navigator.userAgent.indexOf('KHTML')==-1,MobileSafari:!!navigator.userAgent.match(/Apple.*Mobile.*Safari/)};function newCalculator(namespace,functions,fields,buttons)
{var c=new Calculator(namespace);c.setFunctions(functions);c.setFields(fields);c.setButtons(buttons);c.init();calculators.push(c);}
Calculator=function(namespace)
{this.namespace=namespace;this.highlight=true;};Calculator.prototype={REGEX_INT:/(^-?\d\d*$)/,REGEX_FLOAT:/(^-?\d\d*\.\d*$)|(^-?\d\d*$)|(^-?\.\d\d*$)/,GLOSSARY_URL:'../ws/glossary/entry.php',namespace:'',fields:{},buttons:[],functions:{},highlight:true,highlightWidth:2,currentGid:null,footer:null,glossaryOverlay:null,glossaryIcon:null,glossaryHistory:[],init:function()
{if(this.functions.initialize)
{this.highlight=false;this.highlight=true;}
this.body=(Dom.getElementsByClassName('bd','div',this.namespace))[0];this.footer=(Dom.getElementsByClassName('ft','div',this.namespace))[0];this.glossaryIcon=(Dom.getElementsByClassName('glossary-icon','img',this.footer))[0];Dom.hideElement(this.glossaryIcon);Evt.addListener(this.glossaryIcon,'click',this.glossaryIconClick,this);this.initGlossaryIcons();},setFunctions:function(functions)
{this.functions=functions;},setFields:function(fields)
{this.fields=fields;var prefix=this.namespace+'.';for(var name in fields)
{var id=prefix+name;var elem=Dom.get(id);if(fields[name].onChange)
{var functions=fields[name].onChange.split(',');for(var i=0;i<functions.length;i++)
{var params={calculator:this,funcName:functions[i]};if(elem.type!='radio')
Evt.addListener(id,'keyup',this.fieldKeyUp,params);else
Evt.addListener(id,'click',this.fieldClick,params);}}
var params={calculator:this,id:name};Evt.addListener(elem,'focus',this.fieldFocus,params);Evt.addListener(elem,'blur',this.onValidate,params);}},setButtons:function(buttons)
{this.buttons=buttons;var prefix=this.namespace+'.';for(var i=0;i<buttons.length;i++)
{var b=buttons[i];Evt.addListener(prefix+b.id,'click',this.execFunction,{calculator:this,funcName:b.onClick});}},fieldKeyUp:function(e,params)
{var KEYS=YAHOO.util.KeyListener.KEY;var key=window.event?e.keyCode:e.which;if(key==KEYS.TAB||key==KEYS.LEFT||key==KEYS.RIGHT)
return;params.calculator.execFunction(params.funcName);},fieldClick:function(e,params)
{params.calculator.execFunction(params.funcName);},execFunction:function(funcName)
{var func=this.functions[funcName];var values={};var inputs=func.inputs;for(var i=0;i<inputs.length;i++)
{values[inputs[i]]=this.getValue(inputs[i]);}
try
{func.f(values);}
catch(ex)
{alert(ex.toString());}
var outputs=func.outputs;for(var i=0;i<outputs.length;i++)
{this.setValue(outputs[i],values[outputs[i]]);}},getValue:function(id)
{var value='';var field=this.fields[id];if(field.isRadio===true)
{var pId=this.namespace+'.'+id;var children=field.children;for(var i=0;i<children.length;i++)
{var e=Dom.get(pId+'.'+children[i]);if(e.checked)
value=e.value;}}
else
{value=$F(this.namespace+'.'+id);}
if(field.type=='float')
{value=parseFloat(value);}
else if(field.type=='int')
{value=parseInt(value);}
return value;},setValue:function(id,value)
{if(YAHOO.lang.isUndefined(value)||isNaN(value))
{value=null;}
else
{var field=this.fields[id];if(field.type=='int')
{value=parseInt(value);}
else if(field.type=='float')
{value=parseFloat(value);}
if(!YAHOO.lang.isUndefined(field.precision))
{value=value.toFixed(parseInt(field.precision));}}
var elem=$(this.namespace+'.'+id);if(elem.tagName.toUpperCase()=='INPUT')
{elem.value=(value===null)?'':value;if(value!==null){this.animateFieldChange(elem);}}
else
{elem.innerHTML=(value===null)?'&nbsp;':value;}},onValidate:function(e,params)
{params.calculator.validateField(params.id,this);},validateField:function(id,elem)
{var field=this.fields[id];var value=$F(elem);var isValid=true;if(value=='')
{return true;}
if(field.type)
{if(field.type=='int'&&!this.REGEX_INT.test(value))
{isValid=false;message='The value must be an integer.';}
else if(field.type=='float'&&!this.REGEX_FLOAT.test(value))
{isValid=false;message='The value must be a real number.';}}
if(isValid&&(field.type=='int'||field.type=='float'))
{var v=parseFloat(value),hasMin=!YAHOO.lang.isUndefined(field.min),hasMax=!YAHOO.lang.isUndefined(field.max);if((hasMin&&v<parseFloat(field.min))||(hasMax&&v>parseFloat(field.max)))
{isValid=false;}
if(!isValid)
{if(hasMin&&hasMax)
{message='The value must be between '+field.min+' and '+field.max+'.';}
else if(hasMin)
{message='The value must be greater than or equal to '+field.min+'.';}
else if(hasMax)
{message='The value must be less than or equal to '+field.max+'.';}}}
if(!isValid)
{this.displayErrorOverlay(elem,message);this.displayFieldError(elem,message);}
else if(elem._errorPanel!=null)
{elem._errorPanel.destroy();delete elem._errorPanel;}},displayErrorOverlay:function(elem,msg)
{var overlay=this.createOverlay(elem,'error-overlay',1,1,-2,-2);Dom.setStyle(overlay,'opacity','.5');},displayFieldError:function(element,message)
{if(element._errorPanel!=null){element._errorPanel.destroy();delete element._errorPanel;}
var region=YAHOO.util.Dom.getRegion(element);var panelWidth=Math.max(region.right-region.left,150);var errorPanel=new YAHOO.widget.Panel
(element.id+'.errorMsg',{width:panelWidth+'px',x:region.left,y:region.bottom-1,visible:true,draggable:false,close:false,iframe:false,className:'error-popup'});errorPanel.setHeader('');errorPanel.setBody('<div class="error-popup">'+message+'</div>');errorPanel.setFooter('');errorPanel.render('bd');element._errorPanel=errorPanel;Evt.addListener(element.id+'.errorMsg','click',function(){errorPanel.destroy();delete element._errorPanel;});},animateFieldChange:function(elem)
{if(!this.highlight)
{return;}
var overlay=this.createOverlay(elem,'highlight',-2,-2,0,0);var anim=new YAHOO.util.ColorAnim(overlay,{borderColor:{from:'#fff',to:'#F7FA5C'}},2);anim.onComplete.subscribe(this.animateFieldChange2);anim.animate();},animateFieldChange2:function()
{var anim=new YAHOO.util.ColorAnim(this.getEl(),{borderColor:{from:'#F7FA5C',to:'#fff'}},1,YAHOO.util.Easing.easeIn);anim.onComplete.subscribe(function(){Dom.removeElement(this.getEl());});anim.animate();},overlayClick:function()
{try
{this._inputField.focus();this._inputField=null;Dom.removeElement(this);}
catch(e){}},createOverlay:function(elem,className,x,y,width,height)
{var overlay,region;var overlayId=className+'-'+elem.id;if($(overlayId))
{Dom.removeElement(overlayId);}
overlay=document.createElement('div');overlay._inputField=elem;overlay.id=overlayId;Dom.addClass(overlay,className);document.body.appendChild(overlay);region=Dom.getRegion(elem);Dom.setXY(overlay,[region.left+x,region.top+y]);Dom.setStyle(overlay,'width',(region.right-region.left+width)+'px');Dom.setStyle(overlay,'height',(region.bottom-region.top+height)+'px');Evt.addListener(overlay,'click',this.overlayClick);return overlay;},fieldFocus:function(e,params)
{var calc=params.calculator;calc.updateFooter(params.id);var gidElem=$(calc.namespace+'.'+params.id+'.gid');if(gidElem)
{calc.currentGid=gidElem.value;Dom.showElement(calc.glossaryIcon);}
else
{Dom.hideElement(calc.glossaryIcon);}
var ovr=Dom.get('error-overlay-'+calc.namespace+'.'+params.id);if(ovr&&ovr.parentNode)
{ovr._inputField=null;Dom.removeElement(ovr);}},updateFooter:function(field)
{var summary=(Dom.getElementsByClassName('summary','td',this.footer))[0];summary.innerHTML=$(this.namespace+'.'+field).title;},glossaryIconClick:function(e,calc)
{calc.showGlossaryPopup(calc.currentGid);},showGlossaryPopup:function(glossaryId)
{if(this.glossaryOverlay!=null)
{return;}
var region=Dom.getRegion(this.footer);var bdRegion=Dom.getRegion(this.body);var startHeight=20,endHeight=(bdRegion.bottom-bdRegion.top)-10;var overlayId=this.namespace+'Glossary';var overlay=new YAHOO.widget.Overlay(overlayId,{xy:[region.left,region.top-startHeight],width:(region.right-region.left)+'px',height:startHeight+'px',monitorresize:false});overlay.setHeader('Loading...');overlay.setBody('');overlay.render('bd');Dom.setStyle(overlay.body,'height',endHeight-28+'px');var overlayElem=$(overlayId);if(!overlayElem)overlayElem=overlay.element;overlayElem._calculator=this;Dom.addClass(overlayElem,'glossary-overlay');var closeButton=document.createElement('div');Dom.addClass(closeButton,'container-close');overlayElem.appendChild(closeButton);Evt.addListener(closeButton,'click',this.hideGlossaryPopup,this);var backButton=document.createElement('div');Dom.addClass(backButton,'container-back');overlayElem.appendChild(backButton);Dom.hideElement(backButton);Evt.addListener(backButton,'click',this.glossaryBack,this,true);this.glossaryBackBtn=backButton;overlay.show();var attr={height:{from:startHeight,to:endHeight},top:{from:region.top-startHeight,to:region.top-endHeight}};var anim=new YAHOO.util.Anim(overlayId,attr,.5);anim.animate();attr={height:{from:0,to:endHeight-28}};anim=new YAHOO.util.Anim(overlay.body,attr,.5);anim.animate();this.glossaryOverlayElem=overlayElem;this.glossaryOverlay=overlay;var params={'id':glossaryId};this.glossaryHistory=[params];this.sendGlossaryRequest(params);},sendGlossaryRequest:function(params)
{var callback={success:this.updateGlossaryPopup,failure:this.glossaryError,scope:this};var tmp=[];for(var x in params)tmp.push(x+'='+params[x]);var url=this.GLOSSARY_URL+'?'+tmp.join('&');YAHOO.util.Connect.asyncRequest('GET',url,callback);},hideGlossaryPopup:function(e,calc)
{var region=Dom.getRegion(calc.footer);var attr={height:{to:0},top:{to:region.top}};var anim=new YAHOO.util.Anim(calc.glossaryOverlayElem,attr,.5);anim.animate();anim.onComplete.subscribe(calc.destroyGlossaryPopup,calc);if(Browser.Gecko)
{attr={height:{to:0}};anim=new YAHOO.util.Anim(calc.glossaryOverlay.body,attr,.5);anim.animate();}},destroyGlossaryPopup:function(e,args,calc)
{calc.glossaryOverlay.destroy();calc.glossaryOverlay=null;},updateGlossaryPopup:function(transport)
{var entry;eval('entry = '+transport.responseText);if(entry.error)
{this.glossaryOverlay.setHeader('Error');this.glossaryOverlay.setBody('Glossary entry not found.');return;}
this.glossaryOverlay.setHeader(entry.title);var old,content=entry.content;do
{old=content;content=content.replace(/(\[\[)([^(\])]+)(\]\])/,this.makeLink);}while(old!=content);var images=entry.images;for(var i=0;i<images.length;i++)
{if(i%3==0){content+='<div class="spacer"></div>';}
var img=images[i];content+='<a title="'+img.imagecaption+'" '
+'href="javascript:showGlossaryImage('+img.imageid+','
+img.width+','+img.height+')">'
+'<img src="'+'../'+'img'+img.imageid+'_75x75"></a>';}
this.glossaryOverlay.setBody(content);var back=this.glossaryBackBtn,history=this.glossaryHistory;if(!history||history.length<=1)
{Dom.hideElement(back);}
else if(history&&history.length>1)
{Dom.showElement(back);}},removeLink:function(full,ob,match,cb)
{match=match.split('|');return(match[1])?match[1]:match[0];},makeLink:function(full,ob,match,cb)
{match=match.split('|');var entry=match[0];var link=(match[1])?match[1]:entry;return'<a href="javascript:void(0)" onclick="glossaryLinkClick(this, \''+entry+'\')">'+link+'</a>';},glossaryBack:function()
{this.glossaryHistory.pop();this.sendGlossaryRequest(this.glossaryHistory[this.glossaryHistory.length-1]);},initGlossaryIcons:function()
{var container=$(this.namespace);var icons=Dom.getElementsByClassName('glossary-icon','img',this.body);for(var i=0;i<icons.length;i++)
{var id=(icons[i].id.split('.'))[1];Evt.addListener(icons[i],'click',this.fieldFocus,{calculator:this,id:id});}},glossaryError:function()
{this.glossaryTooltip.cfg.setProperty('text','Failed to load glossary entry');},glossaryLinkClick:function(entryName)
{var params={'name':entryName};this.glossaryHistory.push(params);this.sendGlossaryRequest(params);}};Dom.removeElement=function(element)
{element=Dom.get(element);element.parentNode.removeChild(element);return element;};Dom.hideElement=function(element)
{Dom.get(element).style.display='none';return element;};Dom.showElement=function(element)
{Dom.get(element).style.display='';return element;};function glossaryLinkClick(element,entry)
{var calc=Dom.getAncestorByClassName(element,'glossary-overlay')._calculator;calc.glossaryLinkClick(entry);}
function showGlossaryImage(imageId,w,h)
{var url='../glossaryimages.php?iid='+imageId;w+=20;h+=100;window.open(url,'glossaryImgWnd','toolbar=no, directories=no, location=no, status=no, menubar=no, resizable=yes, scrollbars=no, width='+w+', height='+h);}
function imagePopup(src,w,h)
{var url='../images/calculator/'+src;w+=35;h+=30;window.open(url,'imgWnd','toolbar=no, directories=no, location=no, status=no, menubar=no, resizable=yes, scrollbars=no, width='+w+', height='+h);}