/* 8:22 AM 1/31/2003 added mouseevent D.anchorname 8:02 AM 1/25/2003 added NOALPHA and mousetest Navigator will report "e has no properties" but still work!" 2:11 PM 1/25/2003 made datamargin a GR. function ver 6/3/02 bh add 7/28/01 added datamargin() add 3/9/02 added GRaddpointref(); adjusted labt and xaxis for Netscape printing bug fix 5/8/02 docurve with # points > width and better curves. See if(docurve){ fix 5/9/02 overlapping labels on autoscale majorx in GRdotics fix 6/2/02 better datamargin code add 6/2/02 support for nn6 (getElementById;removed "with") divgraph.js by Bob Hanson (hansonr@stolaf.edu) see examples.htm, info.htm, functions.htm for programming info. NOTE: If the GIF files are placed in a directory OTHER than the one the calling page is in, then you must indicate that by changing GR.imagedir or Info.imagedir to indicate that directory. */ //#NOALPHA var GR=new Array() //globals GR.imagedir="." //image directory GR.List=new Array() //graph-specific //--JS Math conversions: function sin(x){return Math.sin(x)} function cos(x){return Math.cos(x)} function tan(x){return Math.sin(x)/Math.cos(x)} function log(x){return Math.LOG10E*Math.log(x)} function ln(x){return Math.log(x)} function sqrt(x){return Math.pow(x,0.5)} function sqr(x){return Math.pow(x,0.5)} //--primary interface function GRadddata(sdata,Data,Labels,Info){ //note: CANNOT BE RUN AFTER PAGE HAS LOADED if(arguments.length<4)Info=new Array() if(arguments.length<3)Labels=new Array() if(arguments.length<2)Data=new Array() if(arguments.length<1)sdata="" if(Data.length==0 && sdata==""){ sdata=GRprompt("Data to plot (x,y,x,y,x,y)?",GR.lastdata) GR.lastdata=sdata if(sdata.indexOf(",")<0)return 0 } if(sdata.length){ Data=new Array() if(Labels.length==0)Labels=new Array() if(!GRgetdata(sdata,Data,Labels))return 0 } Info.append=true return GRdrawgraph("",Data,Labels,Info,GR.doc) } function GRaddfunction(f_of_x,Info){ //note: CANNOT BE RUN AFTER PAGE HAS LOADED if(arguments.length<3)doc=GR.doc if(arguments.length<2)Info=new Array() if(arguments.length<1)f_of_x="" if(!GRinitdivs())return 0 var D=new Array() var L=new Array() if(f_of_x.indexOf("x")<0)f_of_x=GRprompt("JavaScript function of x to plot?",GR.lastfunc) GR.lastfunc=f_of_x if(f_of_x.indexOf("x")<0)return 0 Info.append=true return GRdrawgraph(f_of_x,D,L,Info,GR.doc) } function GRaddpoint(x,y,label,c,xytype,ngraph){ //NN4: CANNOT BE RUN BEFORE PAGE IS LOADED //maximum number of points must be predefined as Info.maxaddpoints if(!GRinitdivs())return 0 if(arguments.length<6)ngraph=GR.thisgraph if(isNaN(GR.List[ngraph].ptadd0)||GR.List[ngraph].ptadd0+GR.List[ngraph].nadd>GR.List[ngraph].ptadd1)return 0 if(arguments.length<5)xytype=GRUSER if(arguments.length<3)label=x+" , "+y if(arguments.length<2){ var s=GRprompt("x,y,alt|label,color? ("+(GR.List[ngraph].nadd+1)+" of "+(GR.List[ngraph].ptadd1-GR.List[ngraph].ptadd0+1)+")",GR.xlast+","+GR.ylast+","+GR.textlast+","+GR.colorlast) var A=s.split(",") if(A.length<2)return 0 x=A[0] y=A[1] if(A.length>2)label=A[2] if(A.length>3)c=A[3] xytype=GRUSER GR.textlast=label GR.colorlast=c } if(c && c.length>0)label=GRptof(0,GR.List[ngraph].ptsize,GR.List[ngraph].ptsize,c,label) var i=GR.List[ngraph].ptadd0+(GR.List[ngraph].nadd++) GRdivwrite(i,label,x,y,xytype,ngraph) return i } function GRaddpointref(x,y,label,c,ref,xytype,ngraph){ //NN4: CANNOT BE RUN BEFORE PAGE IS LOADED //maximum number of points must be predefined as Info.maxaddpoints if(!GRinitdivs())return 0 if(arguments.length<7)ngraph=GR.thisgraph if(arguments.length<5)return 0 if(isNaN(GR.List[ngraph].ptadd0)||GR.List[ngraph].ptadd0+GR.List[ngraph].nadd>GR.List[ngraph].ptadd1)return 0 if(arguments.length<6)xytype=GRUSER if(c && c.length>0)label=GRptof(0,GR.List[ngraph].ptsize,GR.List[ngraph].ptsize,c,label) var i=GR.List[ngraph].ptadd0+(GR.List[ngraph].nadd++) label=""+label+"" label=label.replace(/\GR.List[ngraph].ptadd1)return 0 if(arguments.length<5)xytype=GRUSER if(arguments.length<3){ var s=GRprompt("x,y,text,color? ("+(GR.List[ngraph].nadd+1)+" of "+(GR.List[ngraph].ptadd1-GR.List[ngraph].ptadd0+1)+")",GR.xlast+","+GR.ylast+","+GR.textlast+","+GR.colorlast) var A=s.split(",") if(A.length<3)return 0 x=parseFloat(A[0]) y=parseFloat(A[1]) stext=A[2] if(A.length>3)c=A[3] xytype=GRUSER GR.textlast=stext } var noff=0 if(c && c.length>0){ noff=5 var s=(c.indexOf("align=")>=0?GR.slabt:GR.slab) stext=s.replace(/_text/,stext).replace(/_color/,c) } GR.List[ngraph].anchorx+=noff GR.List[ngraph].anchory-=noff var i=GR.List[ngraph].ptadd0+(GR.List[ngraph].nadd++) GRdivwrite(i,stext,x,y,xytype,ngraph) GR.List[ngraph].anchorx-=noff GR.List[ngraph].anchory+=noff return i } function GRclosegraphdocument(doc){ if(GR.win==null || GR.win.closed)return if(arguments.length<1)doc=GR.doc doc.close() return doc } function GRclosegraphwindow(ngraph,delay){ if(ngraph==null)ngraph=0 if(delay==null)delay=20 for(var i=1;i0 && f_of_x.length==0) if(!GRinitdivs())return 0 GR.append=GRgetinfo(Info,"append",false) GRcleargraph(!GR.append) GR.debug=GRgetinfo(Info,"debug",false) GR.mousetest=GRgetinfo(Info,"mousetest",false) GR.datatransform=(isdata?"y vs. x":GRgetinfo(Info,"datatransform","y vs. x")) isdata=isdata || f_of_x.indexOf(",")>=0 && (f_of_x.charAt(0)=="[" || !isNaN(parseFloat(f_of_x))) s=GR.datatransform.replace(/ /g,"") YvsX=s.split(s.indexOf("vs.")>=0?"vs.":"vs") if(!isdata && YvsX[0].indexOf("y")<0)YvsX[0]="y" if(!isdata && YvsX[1].indexOf("x")<0)YvsX[1]="x" GR.DataYX[0]=GRfixpower(YvsX[0]) GR.DataYX[1]=GRfixpower(YvsX[1]) YvsX[0]=GRfixpower(YvsX[0],"%1%2") YvsX[1]=GRfixpower(YvsX[1],"%1%2") if(GR.debug)GRalert(GRshow(YvsX,"YvsX"),GRshow(GR.DataYX,"GR.DataYX"),s) //change to user's s=GRgetinfo(Info,"xvar","x") if(s!="x")YvsX[1]=YvsX[1].replace(/x/g,s) s=GRgetinfo(Info,"yvar","y") if(s!="y")YvsX[0]=YvsX[0].replace(/y/g,s) //check for data in first parameter if(!isdata && f_of_x==""){ f_of_x=GRprompt("f(x) or data in the form 'x1,y1,x2,y2,...'?",GR.lastfunc) if(f_of_x==null)return 0 } if((f_of_x.charAt(0)=="[" || !isNaN(parseFloat(f_of_x))) && f_of_x.indexOf(",")>=0){ isdata=true Data=new Array() if(!GRgetdata(f_of_x,Data,Labels))return 0 f_of_x="" } GR.doxclip=GRgetinfo(Info,"xclip",true) GR.doyclip=GRgetinfo(Info,"yclip",true) GR.gheight=GRgetinfo(Info,"graphheight",GR.gheight) GR.imagedir=GRgetinfo(Info,"imagedir",GR.imagedir) GR.gleft=GRgetinfo(Info,"graphleft",GR.gleft) GR.gtop=GRgetinfo(Info,"graphtop",GR.gtop) GR.gwidth=GRgetinfo(Info,"graphwidth",GR.gwidth) GR.histogram=GRgetinfo(Info,"histogram",false) GR.onmousedown=GRgetinfo(Info,"onmousedown",GR.onmousedown) var sbody="" if(GR.onmousedown){ if(GR.isnn4){ doc.captureEvents(GR.win.Event.MOUSEDOWN) doc.onmousedown=GRmouseevent }else if(GR.isnn6){ doc.addEventListener("mousedown",GRmouseevent,true) }else{ sbody+=" onmousedown=opener.GRmouseevent()" } } GR.onmousemove=GRgetinfo(Info,"onmousemove",GR.onmousemove) if(GR.onmousemove){ if(GR.isnn4){ doc.captureEvents(GR.win.Event.MOUSEMOVE) doc.onmousemove=GRmouseevent }else if(GR.isnn6){ doc.addEventListener("mousemove",GRmouseevent,true) }else{ sbody+=" onmousemove=opener.GRmouseevent()" } } GR.onmouseup=GRgetinfo(Info,"onmouseup",GR.onmouseup) if(GR.onmouseup){ if(GR.isnn4){ doc.captureEvents(GR.win.Event.MOUSEUP) doc.onmouseup=GRmouseevent }else if(GR.isnn6){ doc.addEventListener("mouseup",GRmouseevent,true) }else{ sbody+=" onmouseup=opener.GRmouseevent()" } } if(!GR.append){ s=GRgetinfo(Info,"anchor","0,0") if(s.indexOf(",")>=0){ P=s.split(",") GR.anchorx=parseInt(P[0]) GR.anchory=parseInt(P[1]) GR.anchorname="" }else{ P=GRgetoffset(s,doc) if(P.left==null){ GRalert("requested anchor was not found:"+s) s="" } GR.anchorx=P.left GR.anchory=P.top GR.anchorname=s } } GR.xmax=GRgetinfo(Info,"xmax",GR.append?GR.xmax:NaN) GR.xmin=GRgetinfo(Info,"xmin",GR.append?GR.xmin:NaN) GR.ymax=GRgetinfo(Info,"ymax",GR.append?GR.ymax:NaN) GR.ymin=GRgetinfo(Info,"ymin",GR.append?GR.ymin:NaN) GR.defaultcolor=GRgetinfo(Info,"defaultcolor","") GR.colorlast=(GR.defaultcolor.length?GR.defaultcolor:"blue") GR.ptsize=GRgetinfo(Info,"ptsize",isdata?3:1) if(GR.ptsize<1)GR.ptsize=1 GR.linewidth=GRgetinfo(Info,"linewidth",GR.ptsize) GR.overwrite=GRgetinfo(Info,"overwrite",0) if(GR.overwrite<0 || GR.nplot==0)GR.overwrite=GR.nplot var bgcolor=GRgetinfo(Info,"bgcolor","") var curvecolor=GRgetinfo(Info,"curvecolor","") GR.datamargin=GRgetinfo(Info,"datamargin",0.05) var docurve=GRgetinfo(Info,"docurve",NaN) var dogridx=GRgetinfo(Info,"dogridx",false) var dogridy=GRgetinfo(Info,"dogridy",false) var dopoints=GRgetinfo(Info,"dopoints",true) var doptlabels=GRgetinfo(Info,"doptlabels",true) var dotrendeqn=GRgetinfo(Info,"dotrendeqn",true) var dotrendline=GRgetinfo(Info,"dotrendline",false) var doxaxis=GRgetinfo(Info,"doxaxis",true) var doxticnums=GRgetinfo(Info,"doxticnums",true) var doxtics=GRgetinfo(Info,"doxtics",true) var doyaxis=GRgetinfo(Info,"doyaxis",true) var doyticnums=GRgetinfo(Info,"doyticnums",true) var doytics=GRgetinfo(Info,"doytics",true) var key=GRgetinfo(Info,"key","") var keyx=GRgetinfo(Info,"keyx",10) var keyy=GRgetinfo(Info,"keyy",10) var labelsonly=GRgetinfo(Info,"labelsonly",false) var majorx=GRgetinfo(Info,"xticmajor","auto") var majory=GRgetinfo(Info,"yticmajor","auto") var majticlen=GRgetinfo(Info,"majorticlength",8) var maxadd=GRgetinfo(Info,"maxaddpoints",0) var minorx=GRgetinfo(Info,"xticminor","auto") var minory=GRgetinfo(Info,"yticminor","auto") var minticlen=GRgetinfo(Info,"minorticlength",5) var quicktrend=GRgetinfo(Info,"quicktrend",true) var salert=GRgetinfo(Info,"alert","") var sinfo=GRgetinfo(Info,"info","") var style=GRgetinfo(Info,"style","") var ticwidth=GRgetinfo(Info,"ticwidth",2) var title=GRgetinfo(Info,"title","") var trendcolor=GRgetinfo(Info,"trendcolor","black") var trenddig=GRgetinfo(Info,"trenddigits",-3) var trendx=GRgetinfo(Info,"trendlabelx",60) var trendy=GRgetinfo(Info,"trendlabely",60) var whendone=GRgetinfo(Info,"whendone","") var wtitle=GRgetinfo(Info,"windowtitle","") var xaty=GRgetinfo(Info,"xaxisaty",0) var yatx=GRgetinfo(Info,"yaxisatx",0) var xnumoff=0 var xdig=GRgetinfo(Info,"xnumdigits",NaN) var xlabel=GRgetinfo(Info,"xaxislabel",YvsX[1]) var xlabelx=GRgetinfo(Info,"xaxislabelx",1e99) var xlabely=GRgetinfo(Info,"xaxislabely",1e99) var xstep=GRgetinfo(Info,"xstep",1) if(xstep<1)xstep=1 var xtic0=GRgetinfo(Info,"xticfirst",NaN) var ydig=GRgetinfo(Info,"ynumdigits",NaN) var ylabel=GRgetinfo(Info,"yaxislabel",YvsX[0]) var ylabelx=GRgetinfo(Info,"yaxislabelx",1e99) var ylabely=GRgetinfo(Info,"yaxislabely",1e99) var ynumoff=0 var ytic0=GRgetinfo(Info,"yticfirst",NaN) var xrange=0 var yrange=0 GR.keepopen=(GR.overwrite || GR.append || maxadd>0 || GR.anchorname.length>0 || GRgetinfo(Info,"keepopen",false)) GR.saveHTML=GR.keepopen docurve=(isNaN(docurve)?!isdata:docurve) if(docurve && !isdata && GR.defaultcolor=="")GR.defaultcolor=curvecolor if(docurve && !isdata)docurve=dopoints=false if(dotrendline && !isdata)dotrendline=false if(sinfo.length)top.status=sinfo if(GR.debug){ GRalert("Info:\n"+GRshow(Info,"Info")) GRalert((isdata?"Data:\n"+GRshow(Data,"Data"):"Function: "+f_of_x)) GRalert("GR:\n"+GRshow(GR,"GR","_")) } var getxrange=(isNaN(GR.xmin) || isNaN(GR.xmax)) var getyrange=(isNaN(GR.ymin) || isNaN(GR.ymax)) if(f_of_x.length){ if(getxrange){ if(isNaN(GR.xmin))GR.xmin=parseFloat(GRprompt("X minimum?",-10)) if(isNaN(GR.xmax))GR.xmax=parseFloat(GRprompt("X maximum?",10)) } xrange=GR.xmax-GR.xmin GR.xfactor=xrange/GR.gwidth*xstep; GR.lastfunc=f_of_x GR.ptsize=GR.linewidth if(typeof(Data)=="string")Data=new Array() if(GR.xfactor!=0){ f_of_x=GRfixpower(f_of_x) i=0 x=GR.xmin while (GRinrange(x,GR.xmin,GR.xmax)){ y=eval(f_of_x) if(GR.DataYX[0]!="y")y=eval(GR.DataYX[0]) if(!GR.doyclip || getyrange || GRinrange(y,GR.ymin,GR.ymax)){ x0=(GR.DataYX[1]=="x"?x:eval(GR.DataYX[1])) if(Math.abs(x0)0 && GR.xmax>0 && GR.xmin*100GR.xmin)GR.xmax=0 if(GR.ymin>0 && GR.ymax>0 && GR.ymin*100GR.ymin)GR.ymax=0 if(GR.debug)GRalert("xmin:"+GR.xmin+"\nymin:"+GR.ymin+"\nxmax:"+GR.xmax+"\nymax:"+GR.ymax) if(GR.debug)GRalert("Labels: "+Labels) //all information ready--start style block //draw header and background, and save info unless appending var npts0=GR.npts if(GR.overwrite){ GR.pt0=GR.List[GR.overwrite].pt0 GR.npts=GR.pt0-1 GR.thisgraph=GR.overwrite }else{ if(!GR.append)GR.nplot++ GR.thisgraph=GR.nplot doc.writeln(""+wtitle+"\n") i=GR.List[GR.thisgraph].pttrend if(i>0)GRgraphpoint(i,GR.Color[i],(doptlabels && GR.Label.length>i?GR.Label[i]:"")) for(i=0;ii?GR.Label[i]:"")) } if(GR.overwrite==0)doc.writeln("") if(GR.temp.length)GRdebugwrite(GR.temp) GR.temp="" GR.pt=null GR.Color=null GR.Label=null if(salert.length)GRalert(salert) if(GR.debug)GRalert("GR at end:\n"+GRshow(GR,"GR","_")) GR.List[GR.thisgraph].pt1=GR.npts GR.List[GR.thisgraph].title=title GR.List[GR.thisgraph].style=style if(GR.debug)GRalert(GRshow(GR.List[GR.thisgraph],"GR.List["+GR.thisgraph+"]")) i=GR.thisgraph if(GR.overwrite)GR.npts=npts0 if(whendone.length)eval(whendone) GRcleargraph(whendone.length==0 && !GR.keepopen) return i } function GRinit(){ GRNONE=0 GRUSER=1 GRANCHOR=2 GRDOC=3 GR.win=window GR.doc=document var s=GR.imagedir GR=new Array() GR.imagedir=s GR.resizetoggle=true GR.init=false GR.npts=0 GR.nplot=0 GR.thisgraph=NaN GR.List=new Array() GR.S_=new Array() GR.X_=new Array() GR.Y_=new Array() GR.temp="" GRcleargraph(true) } function GRopengraphframe(frame){ GRsetgraphwindow(frame) GR.doc.open() GR.winwidth=0 return GR.doc } function GRopengraphwindow(w,h,t,l){ if(arguments.length<4||!l)l=50 if(arguments.length<3||!t)t=50 if(arguments.length<2||!h)h=300 if(arguments.length<1||!w)w=300 var opt=GR.winoptions.replace(/_w/,w).replace(/_h/,h).replace(/_t/,t).replace(/_l/,l) GR.win=GRgetnewwindow("",opt) GR.winwidth=w GR.winheight=h GR.wintop=t GR.winleft=l GR.doc=GR.win.document GR.doc.open() return GR.win } function GRreplot(n,xoff,yoff,doc2,w,h,t,l){ var newwin=null var grwin=GR.win var grdoc=GR.doc if(arguments.length<8)l=GR.winleft if(arguments.length<7)t=GR.wintop if(arguments.length<6)h=GR.winheight if(arguments.length<5)w=GR.winwidth if(arguments.length<4 || doc2==null){ newwin=GRopengraphwindow(w,h,t,l) doc2=GR.doc } if(arguments.length<3)yoff=0 if(arguments.length<2)xoff=0 if(arguments.length<1)n=GR.List.length-1 if(n<1||n>=GR.List.length)return 0 var i0=GR.List[n].pt0 var i1=GR.List[n].pt1 var doc1=GR.List[n].doc GR.List[n].anchorx+=xoff GR.List[n].anchory+=yoff GR.anchorx=GR.List[n].anchorx GR.anchory=GR.List[n].anchory if(doc1==doc2){ np=0 i=GR.List[n].pttrend if(i>=0){ var D=GRdivinfo(i,doc1) if(D.innerHTML!=null && D.innerHTML.length){ np++ GRdivwrite(i,D.innerHTML,D.offsetLeft+xoff,D.offsetTop+yoff,GRDOC,n) } } for(var i=i0;i<=i1;i++){ var D=GRdivinfo(i,doc1) if(i!=GR.List[n].pttrend && D.innerHTML!=null && D.innerHTML.length){ np++ GRdivwrite(i,D.innerHTML,D.offsetLeft+xoff,D.offsetTop+yoff,GRDOC,n) } } return GR.List[n].anchorname+" np:" + np+"\n xoff,yoff:"+xoff+ " " +yoff+"\n"+GRshow(D,"D") } doc2.writeln("") //must write trend line FIRST i=GR.List[n].pttrend if(i>=0){ var D=GRdivinfo(i,doc1) if(D.innerHTML!=null)doc2.writeln("
"+D.innerHTML+"
") } for(var i=i0;i<=i1;i++){ var D=GRdivinfo(i,doc1) if(i!=GR.List[n].pttrend && D.innerHTML!=null)doc2.writeln("
"+D.innerHTML+"
") } doc2.writeln("") if(newwin!=null){ GRclosegraphdocument(newwin.document) if(grwin==window){ GR.win=grwin GR.doc=grdoc }else{ GR.List[n].win=GR.win grwin.close() } } return newwin } function GRsetgraphwindow(w){ if(arguments.length<1)w=window GR.win=w GR.doc=w.document GR.winwidth=0 return GR.doc } //--secondary interface function GRalert(){ var msg="Press Enter to close\n\n" for(var i=0;i"+msg+"") doc.close() } function GRdiv(i,doc){return (doc==null?null:GR.isnn4?doc.layers["G"+i]:GR.isnn6?doc.getElementById("G"+i):doc.all["G"+i])} function GRdivinfo(i,doc){ var D=new Array() var d=GRdiv(i,doc) if(GR.isnn4){ D.innerHTML=GR.S_[i] D.offsetLeft=GR.X_[i] D.offsetTop=GR.Y_[i] return D }else{ if(d==null)return D return d } } function GRdivmove(i,x,y,xytype,ngraph){ if(GR.win==null || GR.win.closed)return null if(arguments.length<5)ngraph=GR.thisgraph if(arguments.length<4)xytype=GRUSER if(arguments.length<3)return null var d=GRdiv(i,GR.List[ngraph].doc) if(d==null)return null GRsetgraph(ngraph) if(xytype==GRUSER){ GR.xlast=x GR.ylast=y x=GRxof(x)-GR.ptsize/2 y=GRyof(y)-GR.ptsize/2 } if(xytype!=GRDOC){ x+=GR.anchorx y+=GR.anchory } if(GR.isnn4){ d.left=x d.top=y }else{ d.style.left=x//*0+i*5-50 d.style.top=y } GR.X_[i]=x GR.Y_[i]=y ;(GR.isnn4?d.visibility="show":d.style.visibility="visible") return d } function GRdivshow(i,TF,ngraph){ if(GR.win==null || GR.win.closed)return if(arguments.length<3)ngraph=GR.thisgraph if(arguments.length<2)TF=true var d=GRdiv(i,GR.List[ngraph].doc) if(d==null)return ;(GR.isnn4?d.visibility=(TF?"show":"hide"):d.style.visibility=(TF?"visible":"hidden")) } function GRdivwrite(i,s,x,y,xytype,ngraph){ if(GR.win==null || GR.win.closed)return null if(arguments.length<6)ngraph=GR.thisgraph if(arguments.length<5)xytype=GRUSER if(arguments.length<2)return null var d=GRdiv(i,GR.List[ngraph].doc) if(d==null)return null if(GR.isnn4){ d.document.open() d.document.write(s) d.document.close() }else{ d.innerHTML=s } if(GR.saveHTML)GR.S_[i]=s if(arguments.length>3 && xytype!=0)return GRdivmove(i,x,y,xytype,ngraph) ;(GR.isnn4?d.visibility="show":d.style.visibility="visible") return d } function GRfixpower(s,format){ if(arguments.length<2)format="Math.pow(%1,%2)" var ipt1=0 var ipt2=0 var i=s.indexOf("^") var isneg=0 while(i>0){ isneg=(s.charAt(i+1)=="-") ipt1=GRfindparen(s,i-1,-1) ipt2=GRfindparen(s,i+(isneg?2:1),1) s=s.substring(0,ipt1)+format.replace(/%1/,s.substring(ipt1,i)).replace(/%2/,s.substring(i+1,ipt2+1))+s.substring(ipt2+1,s.length) i=s.indexOf("^") } return s } function GRgetleastsquares(Data,L){ L.m=null for(var i=0;i0;i--){ if(GR.List[i].win==GR.win && GRinrange(x-GR.List[i].anchorx-GR.List[i].gleft,-GR.List[i].gwidth*GR.datamargin,GR.List[i].gwidth*(1+GR.datamargin)) && GRinrange(y-GR.List[i].anchory-GR.List[i].gtop,-GR.List[i].gheight*GR.datamargin,GR.List[i].gheight*(1+GR.datamargin)))return i } return 0 } function GRinitdivs(){ GR.isnn4=(document.layers?true:false) GR.isie4=(document.all?true:false) GR.isnn6=(!GR.isie4 && document.getElementById?true:false) if(!GR.isnn4 && !GR.isie4 && !GR.isnn6){if(!GR.init)alert("This page will work properly only with browsers capable of supporting layers.");GR.init=true;return false} return true } function GRmouseevent(e,x,y,scmd){ //note: problems here if multiple graph windows var D=new Array() var isnn=(GR.isnn4||GR.isnn6) if(!isnn)e=GR.win.event if(scmd==null){ scmd="GR.on"+e.type scmd=eval(scmd) } if(x==null)x=(isnn?e.pageX:e.clientX+GR.doc.body.scrollLeft-2) if(y==null)y=(isnn?e.pageY:e.clientY+GR.doc.body.scrollTop-2) var n=GRgraph(x,y) if(n==0)return D.ngraph=n D.button=(isnn?e.which:e.button) D.docx=x D.docy=y D.anchorx=D.docx-GR.List[n].anchorx D.anchory=D.docy-GR.List[n].anchory D.anchorname=GR.List[n].anchorname D.userx=(D.anchorx-GR.List[n].gleft)/GR.List[n].gwidth*(GR.List[n].xmax-GR.List[n].xmin)+GR.List[n].xmin D.usery=(D.anchory-GR.List[n].gtop)/GR.List[n].gheight*(GR.List[n].ymin-GR.List[n].ymax)+GR.List[n].ymax if(GR.mousetest){ //something like this for testing GRdebugwrite(scmd+"\n"+GRshow(D,"D")+"\nNote: the \"e\" object would be different using "+(isnn?"Explorer":"Navigator")+".\n\n"+GRshow(e,"e")) GR.mousetest=false } if(scmd==null || scmd==true){ top.status=scmd + " " + D.userx+" "+D.usery }else{ eval(scmd+"(e,D)") } return } function GRprompt(q,a){return(GR.win==null || GR.win.closed?prompt(q,a):GR.win.prompt(q,a))} function GRrect(x1,y1,x2,y2,c,xytype,ngraph){ //x1,y1 upper left, x2,y2 lower right if(ngraph==null)ngraph=GR.thisgraph if(xytype==null)xytype=GRUSER if(xytype==GRUSER){ GRsetgraph(ngraph) x1=GRxof(x1) x2=GRxof(x2) y1=GRyof(y1) y2=GRyof(y2) } var w=(x2-x1) var h=(y2-y1) if(w<=0 || h<=0)return "" if(c==null)c="black" return GR.spt.replace(/_dir/,GR.imagedir).replace(/_color/,c).replace(/_width/,w).replace(/_height/,h).replace(/_text/,"") } function GRresize(){ GR.resizetoggle=!GR.resizetoggle if(!GR.resizetoggle && !GR.isnn4)return 1 for(var i=1;i0){ s=GRroundoff(xs.substring(0,i),Math.abs(ndec)-1)+"E"+xs.substring(i+1,xs.length) if(s.indexOf("10.")==0){ i=(s.indexOf("E") & s.indexOf("e")) s="1"+s.substring(2,i+1)+(parseInt(s.substring(i+1,s.length))+1) } return neg+s } i=xs.indexOf(".") if(i<0){xs+=".";i+=xs.length} xs+="000000000" s="."+xs.substring(i+1+ndec,xs.length) xs=xs.substring(0,i)+xs.substring(i+1,i+1+ndec) var add1=(xs.charAt(0)=="0") if(add1)xs="1"+xs xs=parseInt(xs)+Math.round(parseFloat(s))+"" if(add1)xs=xs.substring(1,xs.length) xs=xs.substring(0,xs.length-ndec)+"."+xs.substring(xs.length-ndec,xs.length) if(xs.indexOf(".")==0)xs="0"+xs return neg+xs } function GRsetgraph(ngraph,tolist){ if(GR.thisgraph==ngraph && !tolist)return if(tolist==null)tolist=false GRcopy( (tolist?GR:GR.List[ngraph]),(tolist?GR.List[ngraph]:GR), "win","doc","xmin","xmax","ymin","ymax","xfactor","yfactor", "gleft","gtop","gwidth","gheight","histogram", "linewidth","ptsize","pttrend", "anchorx","anchory","anchorname") //GRdebugwrite("setting graph from " + GR.thisgraph + " to " + ngraph,GRshow(GR.List[ngraph],"GR.List["+ngraph+"]"),GRshow(GR,"GR")) GR.thisgraph=ngraph } function GRshow(obj,objName,signore,sonly){ if(objName==null)objName="obj" var s = "" for(var i in obj){if(!isNaN(i) || i.indexOf(signore)<0 && (sonly==null || i.indexOf(sonly)>=0))s+=objName+"."+i+" = "+obj[i]+"\n"} return s } function GRxof(x){return Math.round(GR.gleft+(x-GR.xmin)*GR.xfactor)} function GRyof(y){return Math.round(GR.gtop+GR.gheight-(y-GR.ymin)*GR.yfactor)} //--internal functions--- function GRcleargraph(setdefaults){ GR.pt=new Array() GR.Color=new Array() GR.Label=new Array() GR.Plot_=new Array() GR.pt0=GR.npts+1 GR.pttrend=-1 if(!setdefaults)return GR.DataYX=new Array("y","x") GR.append=false GR.gwidth=200 GR.gheight=200 GR.gtop=50 GR.gleft=50 GR.colorlast=GR.defaultcolor GR.datatransform="y vs. x" GR.defaultcolor="blue" GR.defstyle=".bodyfont {font-size:10pt;color:black}\n"+ ".keylabel {font-size:10pt;font-weight:bold;color:black}\n"+ ".ptlabel {font-size:10pt;font-weight:normal;font-style:italic}\n"+ ".trendeqn {font-size:10pt;font-weight:normal;color:black}\n"+ ".xaxisnum {font-size:10pt;font-weight:normal;color:black}\n"+ ".xlabel {font-size:10pt;font-weight:normal;color:black}\n"+ ".yaxisnum {font-size:10pt;font-weight:normal;color:black}\n"+ ".ylabel {font-size:10pt;font-weight:normal;color:black}\n"+ ".tline {background-color:transparent}" GR.debug=false GR.keepopen=false GR.lastdata="-1,-1,0,2,2,1" GR.lastfunc="10*sin(x)*x^2" GR.linewidth=1 GR.ptsize=2 GR.saveHTML=false GR.spt="_text" GR.sdiv="
_text
" GR.sdivclass="
_text
" GR.slab="_text" GR.justwidth=50 GR.slabt="
_text
" GR.textlast="" GR.xfactor=1 GR.xlast=0 GR.xmax=NaN GR.xmin=NaN GR.yfactor=1 GR.ylast=0 GR.ymax=NaN GR.ymin=NaN GR.winoptions="menubar=yes,width=_w,height=_h,left=_l,top=_t" } function GRcopy(Afrom,Ato,list){ for(var i=2;i2 && D[2].length?D[2]:GR.defaultcolor.length?GR.defaultcolor:GR.colorlast) } function GRdotics(tic0,tmin,tmax,minort,majort,stylex,styley,plotx,ploty,force,isy,doticnums,numx,numy,ndig,nignore){ var t=tic0 var st="" var noff=0 var inrange=0 var isok=false var isminor=isNaN(majort) var tdir=(tmax>tmin?1:-1) var tstep=tdir*(!force || isminor?minort:majort) var xt=0 var xtlast=-9999 tmax+=tdir*minort/20 tmin-=tdir*minort/20 if(!isminor && isNaN(ndig))ndig=GRndig(majort) while(GRinrange(t,tic0,tmax)){ inrange=GRinrange(t,tmin,tmax) if((isminor && majort>0 && !force || !isminor) && (force || inrange && Math.abs(t/majort-Math.round(t/majort))<0.001)){ isok=!isminor }else{ isok=(isminor && (force || inrange && Math.abs(t/minort-Math.round(t/minort))<0.001)) } if(isok){ if(doticnums){ if(Math.abs(t/(tmax-tmin))<0.01)t=0 st=GRroundoff(t,ndig) } if(isy){ GRnewstyle(stylex,GRyof(t)+styley,plotx,ploty,"blackh","") if(doticnums && parseFloat(st)!=nignore)GRnewlabel(st,numx,GRyof(t)+numy,"class=yaxisnum align=right") }else{ GRnewstyle(GRxof(t)+stylex,styley,plotx,ploty,"blackv","") xt=GRxof(t)+numx if(doticnums){ isok=((xt-xtlast)>st.length*6) if(isok)xtlast=xt } if(isok && doticnums && parseFloat(st)!=nignore)GRnewlabel(st,xt,numy,"class=xaxisnum align=center") } } t+=tstep } } function GRfindparen(s,ipt0,idirect) { var i=0 var ipt=ipt0 while (ipt=0) { i+=(s.charAt(ipt)=="("?1:s.charAt(ipt)==")"?-1:0) if(i==0)return ipt ipt+=idirect } return ipt } function GRgetdata(sdata,Data,Labels){ var dolabels=(Labels.length==0) var D=new Array() var P=new Array() var n=0 var x=0 var y=0 var xt=0 var yt=0 sdata=sdata.replace(/,\[/g,"").replace(/\[/g,"").replace(/\]/g,"\n") sdata=sdata.replace(/\r/g,"\n").replace(/\n\n/g,"\n") if(sdata.indexOf("\n")>=0){ //x,y pairs from a textbox, probably D=sdata.split("\n") for(var i=0;i2)Data[n][2]=P[2] if(dolabels)Labels[n]=(P.length>3?P[3]:x+" , "+y) n++ } } } }else{ D=sdata.split(",") for(var i=0;i0) } function GRgetinfo(A,skey,def){return (A[skey]==null?def:A[skey])} function GRgraphpoint(i,scolor,slabel){ if(GR.win==null || GR.win.closed)return var n=(i<0?GR.List[GR.thisgraph].ptadd0-1-i:GR.pt0+i) var s=(i<0?"
":GRptof((GR.overwrite?0:n),GR.pt[i][0],Math.ceil(GR.pt[i][1]),scolor,slabel)) if(GR.overwrite){ (s!=GR.S_[n]?GRdivwrite(n,s,GR.X_[n],GR.Y_[n],GRDOC):GRdivmove(n,GR.X_[n],GR.Y_[n],GRDOC)) }else{ GR.doc.writeln(s) } } function GRLSQ(L,x,y){//least squares fit if(L.m==null){ L.x=L.y=L.xx=L.yy=L.xy=L.n=0 L.x_=L.y_=L.m=L.b=NaN L.r2=null } if(arguments.length==3){ L.x+=x L.y+=y L.xx+=x*x L.yy+=y*y L.xy+=x*y L.n++ return 1 } var d=0 d=L.n*L.xx-L.x*L.x if(d==0)return 0 L.b=(L.xx*L.y-L.x*L.xy)/d L.m=(L.n*L.xy-L.x*L.y)/d L.x_=L.x/L.n L.y_=L.y/L.n return 1 } function GRLSR(L,x,y){//returns coef of linear coor, r if(L.r2==null){ L.x=L.y=L.xy=0 L.r2=NaN } if(arguments.length==3){ var dx=x-L.x_ var dy=y-L.y_ L.x+=dx*dx L.y+=dy*dy L.xy+=dx*dy return 1 } L.r2=(L.x==0 || L.y==0?1:L.xy*L.xy/(L.x*L.y)) return L.r2 } function GRndig(n){ var x=Math.abs(n) return(x>=9999||x<0.01?-2:x>=10?0:x>=1?1:x>=.1?2:3) } function GRnewdata(A,x,P){ var y=P[0]+x*(P[1]+x*(P[2]+x*P[3])) A[A.length]=new Array(x,y) return y } function GRnewlabel(s,x,y,c){ var ialign=(c.indexOf(" align=")<0?0:c.indexOf("=left")>=0?1:c.indexOf("=center")>=0?2:c.indexOf("=right")>=0?3:0) GRnewstyle(x-(ialign==2?GR.justwidth/2:ialign==3?GR.justwidth:0),y-(ialign?8:0),1) GR.Plot_[GR.Plot_.length]=[-GR.npts,s,c+(ialign?" width="+GR.justwidth:"")] } function GRnewpt(i,x,y,Data,Labels,width,height,c){ c=(i<0?(c==null?GR.colorlast:c):GRdatacolor(Data[i])) if(GR.doxclip && c!="transp" && !GRinrange(x,GR.plotxmin,GR.plotxmax))return if(GR.doyclip && c!="transp" && !GRinrange(y,GR.plotymin,GR.plotymax))return var n=GR.pt.length GR.Label[n]=(i<0?"":i3?Data[i][3]:"") GR.colorlast=GR.Color[n]=c if(height==0)height=1 if(width==0)width=1 if(i>=0 && GR.histogram && GR.colorlast!="transp"){ if(GR.histogram==1){ height=Math.abs(y-GR.xaxisoffset) y=Math.min(y,GR.xaxisoffset) x-=width/2 }else{ width=Math.abs(x-GR.yaxisoffset) x=Math.min(x,GR.yaxisoffset) y-=height/2 } }else{ x-=width/2 y-=height/2 } GR.pt[n]=new Array(width,height) GRnewstyle(x,y,1) } function GRnewstyle(left,top,width,height,color,label){ if(GR.win==null || GR.win.closed)return left=GR.anchorx+Math.round(left) top=GR.anchory+Math.round(top) GR.npts++ if(GR.overwrite==0)GR.doc.writeln("#G"+GR.npts+" {position:absolute;"+(width>0?"left:"+left+";top:"+top:"visibility:hidden")+"}") GR.X_[GR.npts]=left GR.Y_[GR.npts]=top if(arguments.length<=3 || GR.overwrite)return GR.Plot_[GR.Plot_.length]=[GR.npts,width,height,color,label] } function GRlabelof(i,s,c){ var t=(c.indexOf(" align=")>=0?GR.slabt:GR.slab) t=t.replace(/_text/,s).replace(/_color/,c) if(GR.saveHTML)GR.S_[i]=t return GR.sdiv.replace(/_id/,"G"+i).replace(/_text/,t) } function GRnewdiv(P){ if(P[0]>=0)return GRptof(P[0],P[1],P[2],P[3],P[4]) return GRlabelof(-P[0],P[1],P[2]) } function GRptof(i,w,h,c,a){ a+="" var j=a.indexOf("|") var txt="" if(j>=0){txt=a.substring(j+1,a.length);a=a.substring(0,j)} var s=GR.spt.replace(/_dir/,GR.imagedir).replace(/_color/,c).replace(/_width/,w).replace(/_height/,h) s=s.replace(/_alt/,(a.length?"alt=\""+a+"\"":"")+(txt.length?" align=top":"")).replace(/_text/,txt) if(i && GR.saveHTML)GR.S_[i]=s if(!i)return s if(c.indexOf(" class=")<0) return GR.sdiv.replace(/_id/,"G"+i).replace(/_text/,s) return GR.sdivclass.replace(/_id/,"G"+i).replace(/_class/,c).replace(/_text/,s) } function GRsort(a,b){return a-b} function GRspline(Data,i){ //f(x)=P[0]+P[1]x+P[2]x^2+P[3]x^3 //matches approx slopes at endpoints var P=new Array(NaN,0,0,0) if(i<0 || i>=Data.length)return P var x1=Data[i][0] var x2=Data[i+1][0] if(x1==x2)return P var y1=Data[i][1] var y2=Data[i+1][1] var dy=y2-y1 var dx=x2-x1 var s12=dy/dx if(Data.length==2){ P[0]=y1-s12*x1 P[1]=s12 return P } var x0=(i>0?Data[i-1][0]:x2) var y0=(i>0?Data[i-1][1]:y2) var x3=(i+2=a && x<=b || x>=b && x<=a} GRinit()