// (c) 2005 Jonathan Stott
//
// Created on 21-Dec-2005
// License: GPL - http://www.jstott.me.uk/jscoord/
function LatLng(_1,_2){
this.lat=_1;
this.lng=_2;
this.distance=LatLngDistance;
this.toOSRef=LatLngToOSRef;
this.toUTMRef=LatLngToUTMRef;
this.WGS84ToOSGB36=WGS84ToOSGB36;
this.OSGB36ToWGS84=OSGB36ToWGS84;
this.toString=LatLngToString;
}
function LatLngToString(){
return "("+this.lat+", "+this.lng+")";
}
function OSRef(_3,_4){
this.easting=_3;
this.northing=_4;
this.toLatLng=OSRefToLatLng;
this.toString=OSRefToString;
this.toSixFigureString=OSRefToSixFigureString;
}
function OSRefToString(){
return "("+this.easting+", "+this.northing+")";
}
function OSRefToSixFigureString(){
var _5=Math.floor(this.easting/100000);
var _6=Math.floor(this.northing/100000);
var _7="";
if(_6<5){
if(_5<5){
_7="S";
}else{
_7="T";
}
}else{
if(_6<10){
if(_5<5){
_7="N";
}else{
_7="O";
}
}else{
_7="H";
}
}
var _8="";
var _9=65+((4-(_6%5))*5)+(_5%5);
var ti=_9;
if(_9>=73){
_9++;
}
_8=chr(_9);
var e=Math.floor((this.easting-(100000*_5))/100);
var n=Math.floor((this.northing-(100000*_6))/100);
var es=e;
if(e<100){
es="0"+es;
}
if(e<10){
es="0"+es;
}
var ns=n;
if(n<100){
ns="0"+ns;
}
if(n<10){
ns="0"+ns;
}
return _7+_8+es+ns;
}
function UTMRef(_f,_10,_11,_12){
this.easting=_f;
this.northing=_10;
this.latZone=_11;
this.lngZone=_12;
this.toLatLng=UTMRefToLatLng;
this.toString=UTMRefToString;
}
function UTMRefToString(){
return this.lngZone+this.latZone+" "+this.easting+" "+this.northing;
}
function RefEll(maj,min){
this.maj=maj;
this.min=min;
this.ecc=((maj*maj)-(min*min))/(maj*maj);
}
function sinSquared(x){
return Math.sin(x)*Math.sin(x);
}
function cosSquared(x){
return Math.cos(x)*Math.cos(x);
}
function tanSquared(x){
return Math.tan(x)*Math.tan(x);
}
function sec(x){
return 1/Math.cos(x);
}
function deg2rad(x){
return x*(Math.PI/180);
}
function rad2deg(x){
return x*(180/Math.PI);
}
function chr(x){
var h=x.toString(16);
if(h.length==1){
h="0"+h;
}
h="%"+h;
return unescape(h);
}
function ord(x){
var c=x.charAt(0);
var i;
for(i=0;i<256;++i){
var h=i.toString(16);
if(h.length==1){
h="0"+h;
}
h="%"+h;
h=unescape(h);
if(h==c){
break;
}
}
return i;
}
function LatLngDistance(to){
var er=6366.707;
var _23=deg2rad(this.lat);
var _24=deg2rad(to.lat);
var _25=deg2rad(this.lng);
var _26=deg2rad(to.lng);
var x1=er*Math.cos(_25)*Math.sin(_23);
var y1=er*Math.sin(_25)*Math.sin(_23);
var z1=er*Math.cos(_23);
var x2=er*Math.cos(_26)*Math.sin(_24);
var y2=er*Math.sin(_26)*Math.sin(_24);
var z2=er*Math.cos(_24);
var d=Math.sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2)+(z1-z2)*(z1-z2));
return d;
}
function OSGB36ToWGS84(){
var _2e=new RefEll(6377563.396,6356256.909);
var a=_2e.maj;
var b=_2e.min;
var _31=_2e.ecc;
var phi=deg2rad(this.lat);
var _33=deg2rad(this.lng);
var v=a/(Math.sqrt(1-_31*sinSquared(phi)));
var H=0;
var x=(v+H)*Math.cos(phi)*Math.cos(_33);
var y=(v+H)*Math.cos(phi)*Math.sin(_33);
var z=((1-_31)*v+H)*Math.sin(phi);
var tx=446.448;
var ty=-125.157;
var tz=542.06;
var s=-0.0000204894;
var rx=deg2rad(0.00004172222);
var ry=deg2rad(0.00006861111);
var rz=deg2rad(0.00023391666);
var xB=tx+(x*(1+s))+(-rx*y)+(ry*z);
var yB=ty+(rz*x)+(y*(1+s))+(-rx*z);
var zB=tz+(-ry*x)+(rx*y)+(z*(1+s));
var _43=new RefEll(6378137,6356752.3141);
a=_43.maj;
b=_43.min;
_31=_43.ecc;
var _44=rad2deg(Math.atan(yB/xB));
var p=Math.sqrt((xB*xB)+(yB*yB));
var _46=Math.atan(zB/(p*(1-_31)));
for(var i=1;i<10;i++){
v=a/(Math.sqrt(1-_31*sinSquared(_46)));
phiN1=Math.atan((zB+(_31*v*Math.sin(_46)))/p);
_46=phiN1;
}
var _48=rad2deg(_46);
this.lat=_48;
this.lng=_44;
}
function WGS84ToOSGB36(){
var _49=new RefEll(6378137,6356752.3141);
var a=_49.maj;
var b=_49.min;
var _4c=_49.ecc;
var phi=deg2rad(this.lat);
var _4e=deg2rad(this.lng);
var v=a/(Math.sqrt(1-_4c*sinSquared(phi)));
var H=0;
var x=(v+H)*Math.cos(phi)*Math.cos(_4e);
var y=(v+H)*Math.cos(phi)*Math.sin(_4e);
var z=((1-_4c)*v+H)*Math.sin(phi);
var tx=-446.448;
var ty=124.157;
var tz=-542.06;
var s=0.0000204894;
var rx=deg2rad(-0.00004172222);
var ry=deg2rad(-0.00006861111);
var rz=deg2rad(-0.00023391666);
var xB=tx+(x*(1+s))+(-rx*y)+(ry*z);
var yB=ty+(rz*x)+(y*(1+s))+(-rx*z);
var zB=tz+(-ry*x)+(rx*y)+(z*(1+s));
var _5e=new RefEll(6377563.396,6356256.909);
a=_5e.maj;
b=_5e.min;
_4c=_5e.ecc;
var _5f=rad2deg(Math.atan(yB/xB));
var p=Math.sqrt((xB*xB)+(yB*yB));
var _61=Math.atan(zB/(p*(1-_4c)));
for(var i=1;i<10;i++){
v=a/(Math.sqrt(1-_4c*sinSquared(_61)));
phiN1=Math.atan((zB+(_4c*v*Math.sin(_61)))/p);
_61=phiN1;
}
var _63=rad2deg(_61);
this.lat=_63;
this.lng=_5f;
}
function OSRefToLatLng(){
var _64=new RefEll(6377563.396,6356256.909);
var _65=0.9996012717;
var N0=-100000;
var E0=400000;
var _68=deg2rad(49);
var _69=deg2rad(-2);
var a=_64.maj;
var b=_64.min;
var _6c=_64.ecc;
var phi=0;
var _6e=0;
var E=this.easting;
var N=this.northing;
var n=(a-b)/(a+b);
var M=0;
var _73=((N-N0)/(a*_65))+_68;
do{
M=(b*_65)*(((1+n+((5/4)*n*n)+((5/4)*n*n*n))*(_73-_68))-(((3*n)+(3*n*n)+((21/8)*n*n*n))*Math.sin(_73-_68)*Math.cos(_73+_68))+((((15/8)*n*n)+((15/8)*n*n*n))*Math.sin(2*(_73-_68))*Math.cos(2*(_73+_68)))-(((35/24)*n*n*n)*Math.sin(3*(_73-_68))*Math.cos(3*(_73+_68))));
_73+=(N-N0-M)/(a*_65);
}while((N-N0-M)>=0.001);
var v=a*_65*Math.pow(1-_6c*sinSquared(_73),-0.5);
var rho=a*_65*(1-_6c)*Math.pow(1-_6c*sinSquared(_73),-1.5);
var _76=(v/rho)-1;
var VII=Math.tan(_73)/(2*rho*v);
var _78=(Math.tan(_73)/(24*rho*Math.pow(v,3)))*(5+(3*tanSquared(_73))+_76-(9*tanSquared(_73)*_76));
var IX=(Math.tan(_73)/(720*rho*Math.pow(v,5)))*(61+(90*tanSquared(_73))+(45*tanSquared(_73)*tanSquared(_73)));
var X=sec(_73)/v;
var XI=(sec(_73)/(6*v*v*v))*((v/rho)+(2*tanSquared(_73)));
var XII=(sec(_73)/(120*Math.pow(v,5)))*(5+(28*tanSquared(_73))+(24*tanSquared(_73)*tanSquared(_73)));
var _7d=(sec(_73)/(5040*Math.pow(v,7)))*(61+(662*tanSquared(_73))+(1320*tanSquared(_73)*tanSquared(_73))+(720*tanSquared(_73)*tanSquared(_73)*tanSquared(_73)));
phi=_73-(VII*Math.pow(E-E0,2))+(_78*Math.pow(E-E0,4))-(IX*Math.pow(E-E0,6));
_6e=_69+(X*(E-E0))-(XI*Math.pow(E-E0,3))+(XII*Math.pow(E-E0,5))-(_7d*Math.pow(E-E0,7));
return new LatLng(rad2deg(phi),rad2deg(_6e));
}
function LatLngToOSRef(){
var _7e=new RefEll(6377563.396,6356256.909);
var _7f=0.9996012717;
var N0=-100000;
var E0=400000;
var _82=deg2rad(49);
var _83=deg2rad(-2);
var a=_7e.maj;
var b=_7e.min;
var _86=_7e.ecc;
var phi=deg2rad(this.lat);
var _88=deg2rad(this.lng);
var E=0;
var N=0;
var n=(a-b)/(a+b);
var v=a*_7f*Math.pow(1-_86*sinSquared(phi),-0.5);
var rho=a*_7f*(1-_86)*Math.pow(1-_86*sinSquared(phi),-1.5);
var _8e=(v/rho)-1;
var M=(b*_7f)*(((1+n+((5/4)*n*n)+((5/4)*n*n*n))*(phi-_82))-(((3*n)+(3*n*n)+((21/8)*n*n*n))*Math.sin(phi-_82)*Math.cos(phi+_82))+((((15/8)*n*n)+((15/8)*n*n*n))*Math.sin(2*(phi-_82))*Math.cos(2*(phi+_82)))-(((35/24)*n*n*n)*Math.sin(3*(phi-_82))*Math.cos(3*(phi+_82))));
var I=M+N0;
var II=(v/2)*Math.sin(phi)*Math.cos(phi);
var III=(v/24)*Math.sin(phi)*Math.pow(Math.cos(phi),3)*(5-tanSquared(phi)+(9*_8e));
var _93=(v/720)*Math.sin(phi)*Math.pow(Math.cos(phi),5)*(61-(58*tanSquared(phi))+Math.pow(Math.tan(phi),4));
var IV=v*Math.cos(phi);
var V=(v/6)*Math.pow(Math.cos(phi),3)*((v/rho)-tanSquared(phi));
var VI=(v/120)*Math.pow(Math.cos(phi),5)*(5-(18*tanSquared(phi))+(Math.pow(Math.tan(phi),4))+(14*_8e)-(58*tanSquared(phi)*_8e));
N=I+(II*Math.pow(_88-_83,2))+(III*Math.pow(_88-_83,4))+(_93*Math.pow(_88-_83,6));
E=E0+(IV*(_88-_83))+(V*Math.pow(_88-_83,3))+(VI*Math.pow(_88-_83,5));
return new OSRef(E,N);
}
function UTMRefToLatLng(){
var _97=new RefEll(6378137,6356752.314);
var _98=0.9996;
var a=_97.maj;
var _9a=_97.ecc;
var _9b=_9a/(1-_9a);
var e1=(1-Math.sqrt(1-_9a))/(1+Math.sqrt(1-_9a));
var x=this.easting-500000;
var y=this.northing;
var _9f=this.lngZone;
var _a0=this.latZone;
var _a1=(_9f-1)*6-180+3;
if((ord(_a0)-ord("N"))<0){
y-=10000000;
}
var m=y/_98;
var mu=m/(a*(1-_9a/4-3*_9a*_9a/64-5*Math.pow(_9a,3)/256));
var _a4=mu+(3*e1/2-27*Math.pow(e1,3)/32)*Math.sin(2*mu)+(21*e1*e1/16-55*Math.pow(e1,4)/32)*Math.sin(4*mu)+(151*Math.pow(e1,3)/96)*Math.sin(6*mu);
var n=a/Math.sqrt(1-_9a*Math.sin(_a4)*Math.sin(_a4));
var t=Math.tan(_a4)*Math.tan(_a4);
var c=_9b*Math.cos(_a4)*Math.cos(_a4);
var r=a*(1-_9a)/Math.pow(1-_9a*Math.sin(_a4)*Math.sin(_a4),1.5);
var d=x/(n*_98);
var _aa=(_a4-(n*Math.tan(_a4)/r)*(d*d/2-(5+(3*t)+(10*c)-(4*c*c)-(9*_9b))*Math.pow(d,4)/24+(61+(90*t)+(298*c)+(45*t*t)-(252*_9b)-(3*c*c))*Math.pow(d,6)/720))*(180/Math.PI);
var _ab=_a1+((d-(1+2*t+c)*Math.pow(d,3)/6+(5-(2*c)+(28*t)-(3*c*c)+(8*_9b)+(24*t*t))*Math.pow(d,5)/120)/Math.cos(_a4))*(180/Math.PI);
return new LatLng(_aa,_ab);
}
function LatLngToUTMRef(){
var _ac=new RefEll(6378137,6356752.314);
var _ad=0.9996;
var a=_ac.maj;
var _af=_ac.ecc;
var _b0=this.lng;
var _b1=this.lat;
var _b2=_b1*(Math.PI/180);
var _b3=_b0*(Math.PI/180);
var _b4=Math.floor((_b0+180)/6)+1;
if(_b1>=56&&_b1<64&&_b0>=3&&_b0<12){
_b4=32;
}
if(_b1>=72&&_b1<84){
if(_b0>=0&&_b0<9){
_b4=31;
}else{
if(_b0>=9&&_b0<21){
_b4=33;
}else{
if(_b0>=21&&_b0<33){
_b4=35;
}else{
if(_b0>=33&&_b0<42){
_b4=37;
}
}
}
}
}
var _b5=(_b4-1)*6-180+3;
var _b6=_b5*(Math.PI/180);
var _b7=getUTMLatitudeZoneLetter(_b1);
ePrimeSquared=(_af)/(1-_af);
var n=a/Math.sqrt(1-_af*Math.sin(_b2)*Math.sin(_b2));
var t=Math.tan(_b2)*Math.tan(_b2);
var c=ePrimeSquared*Math.cos(_b2)*Math.cos(_b2);
var A=Math.cos(_b2)*(_b3-_b6);
var M=a*((1-_af/4-3*_af*_af/64-5*_af*_af*_af/256)*_b2-(3*_af/8+3*_af*_af/32+45*_af*_af*_af/1024)*Math.sin(2*_b2)+(15*_af*_af/256+45*_af*_af*_af/1024)*Math.sin(4*_b2)-(35*_af*_af*_af/3072)*Math.sin(6*_b2));
var _bd=(_ad*n*(A+(1-t+c)*Math.pow(A,3)/6+(5-18*t+t*t+72*c-58*ePrimeSquared)*Math.pow(A,5)/120)+500000);
var _be=(_ad*(M+n*Math.tan(_b2)*(A*A/2+(5-t+(9*c)+(4*c*c))*Math.pow(A,4)/24+(61-(58*t)+(t*t)+(600*c)-(330*ePrimeSquared))*Math.pow(A,6)/720)));
if(_b1<0){
_be+=10000000;
}
return new UTMRef(_bd,_be,_b7,_b4);
}
function getOSRefFromSixFigureReference(ref){
var _c0=ref.substring(0,1);
var _c1=ref.substring(1,2);
var _c2=parseInt(ref.substring(2,5),10)*100;
var _c3=parseInt(ref.substring(5,8),10)*100;
if(_c0=="H"){
_c3+=1000000;
}else{
if(_c0=="N"){
_c3+=500000;
}else{
if(_c0=="O"){
_c3+=500000;
_c2+=500000;
}else{
if(_c0=="T"){
_c2+=500000;
}
}
}
}
var _c4=ord(_c1);
if(_c4>73){
_c4--;
}
var nx=((_c4-65)%5)*100000;
var ny=(4-Math.floor((_c4-65)/5))*100000;
return new OSRef(_c2+nx,_c3+ny);
}
function getUTMLatitudeZoneLetter(_c7){
if((84>=_c7)&&(_c7>=72)){
return "X";
}else{
if((72>_c7)&&(_c7>=64)){
return "W";
}else{
if((64>_c7)&&(_c7>=56)){
return "V";
}else{
if((56>_c7)&&(_c7>=48)){
return "U";
}else{
if((48>_c7)&&(_c7>=40)){
return "T";
}else{
if((40>_c7)&&(_c7>=32)){
return "S";
}else{
if((32>_c7)&&(_c7>=24)){
return "R";
}else{
if((24>_c7)&&(_c7>=16)){
return "Q";
}else{
if((16>_c7)&&(_c7>=8)){
return "P";
}else{
if((8>_c7)&&(_c7>=0)){
return "N";
}else{
if((0>_c7)&&(_c7>=-8)){
return "M";
}else{
if((-8>_c7)&&(_c7>=-16)){
return "L";
}else{
if((-16>_c7)&&(_c7>=-24)){
return "K";
}else{
if((-24>_c7)&&(_c7>=-32)){
return "J";
}else{
if((-32>_c7)&&(_c7>=-40)){
return "H";
}else{
if((-40>_c7)&&(_c7>=-48)){
return "G";
}else{
if((-48>_c7)&&(_c7>=-56)){
return "F";
}else{
if((-56>_c7)&&(_c7>=-64)){
return "E";
}else{
if((-64>_c7)&&(_c7>=-72)){
return "D";
}else{
if((-72>_c7)&&(_c7>=-80)){
return "C";
}else{
return "Z";
}
}
}
}
}
}
}
}
}
}
}
}
}
}
}
}
}
}
}
}
}

