|
// constants |
|
var N_0 = 819069.80; // northing of projection origin |
|
var E_0 = 836694.05; // easting of projection origin |
|
var m_0 = 1; // scale factor |
|
var lat_0 = (22 + 18 / 60 + 43.68 / 3600) * Math.PI / 180; // DMS to radian, lat of projection origin |
|
var lng_0 = (114 + 10 / 60 + 42.80 / 3600) * Math.PI / 180; // DMS to decimal, lng of projection origin |
|
|
|
var M_0 = 0; // meridian distance measured from equator to origin |
|
var a = 0; |
|
var f = 0; |
|
var e_squared = 0; // first eccentricity of reference ellipsoid |
|
var e_quad = 0; |
|
var A_0 = 0; |
|
var A_2 = 0; |
|
var A_4 = 0; |
|
var v_s = 0; // radius of curvature in the prime vertical |
|
var p_s = 0; // radius of curvature in the meridian |
|
var psi_s = 0; // isometric latitude |
|
|
|
class Constants { |
|
static initAllConstants(type) { |
|
if (type == "grid") { |
|
a = 6378388; |
|
f = 1 / 297.0; |
|
} else if (type == "wgs") { |
|
a = 6378137; |
|
f = 1 / 298.2572235634; |
|
} |
|
e_squared = 2 * f - f * f; |
|
e_quad = e_squared * e_squared; |
|
A_0 = 1 - e_squared / 4 - (3 / 64) * e_quad; |
|
A_2 = 3 / 8 * (e_squared + e_quad / 4); |
|
A_4 = 15 / 256 * e_quad; |
|
v_s = a / Math.sqrt((1 - e_squared * Math.pow(Math.sin(lat_0), 2))); |
|
p_s = a * (1 - e_squared) / Math.pow(Math.sqrt(1 - e_squared * Math.pow(Math.sin(lat_0), 2)), 3); |
|
psi_s = v_s / p_s; |
|
M_0 = this.meridianDistance(lat_0); |
|
} |
|
|
|
static meridianDistance(phi) { |
|
return a * ((A_0 * phi) - (A_2 * Math.sin(2 * phi)) + (A_4 * Math.sin(4 * phi))); |
|
} |
|
|
|
static derivativeM(phi) { |
|
return a * (A_0 - A_2 * 2 * Math.cos(2 * phi) + 4 * A_4 * Math.cos(4 * phi)); |
|
} |
|
|
|
static getPhiP(N) { |
|
var deltaN = N - N_0; |
|
var c = (deltaN + M_0) / m_0; |
|
var error = Math.pow(10, -17); |
|
var err = 1; // initialize |
|
var x0 = 0.3; |
|
// double x1 = 0.4; |
|
// var x; |
|
var xn = x0; |
|
var fxn; |
|
var i = 1; |
|
var maxIteration = 500; |
|
// double fx0; |
|
// double fx1; |
|
// double dx; |
|
// int i = 2; |
|
// while(err > error) { |
|
// fx0 = meridianDistance(x0) - c; |
|
// fx1 = meridianDistance(x1) - c; |
|
// x = x1 - (x1 - x0) * fx1 / (fx1 - fx0); |
|
// x0 = x1; |
|
// x1 = x; |
|
// err = (x0-x1).abs(); |
|
// print("x" + i.toString() + " = " + x.toString() + ', error: ' + err.toString()); |
|
// i ++; |
|
// } |
|
while (err > error && i < maxIteration) { |
|
fxn = this.meridianDistance(xn) - c; |
|
xn = xn - fxn / this.derivativeM(xn); |
|
err = Math.abs(fxn); |
|
i++; |
|
} |
|
return xn; |
|
} |
|
|
|
static getV(phi) { |
|
return a / Math.sqrt(1 - (e_squared * Math.pow(Math.sin(phi), 2))); |
|
} |
|
|
|
static getRoll(phi) { |
|
return a * (1 - e_squared) / Math.pow(Math.sqrt(1 - e_squared * Math.pow(Math.sin(phi), 2)), 3); |
|
} |
|
|
|
static getAllConstants(x, y, type) { |
|
var constants = {}; |
|
this.initAllConstants(type); |
|
var phiP = this.getPhiP(y); |
|
var secantPhiP = 1 / Math.cos(phiP); |
|
var vP = this.getV(phiP); |
|
var rollP = this.getRoll(phiP); |
|
var psiP = vP / rollP; |
|
var tanP = Math.tan(phiP); |
|
var deltaE = x - E_0; |
|
var deltaN = y - N_0; |
|
constants['phiP'] = phiP; |
|
constants['secantPhiP'] = secantPhiP; |
|
constants['vP'] = vP; |
|
constants['rollP'] = rollP; |
|
constants['psiP'] = psiP; |
|
constants['tanP'] = tanP; |
|
constants['deltaE'] = deltaE; |
|
constants['deltaN'] = deltaN; |
|
return constants; |
|
} |
|
} |