From aa3330949ad972fef2376721fc6673344664e483 Mon Sep 17 00:00:00 2001 From: Matthew Bloch Date: Sun, 30 May 2021 11:47:36 -0400 Subject: [PATCH] v0.0.34 --- CHANGELOG.md | 3 ++ package.json | 2 +- src/projections/etmerc.js | 29 ------------------ src/projections/hill.js | 2 +- src/projections/tmerc.js | 62 ++++++++++++++++++++++++++++++++++++++- test/pj_init_test.js | 13 +++++--- 6 files changed, 75 insertions(+), 36 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 8a7e606..20dc490 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,6 @@ +v0.0.34 +* Changed tmerc to use etmerc for points >3deg from lon_0, unless the +approx flag is used. + v0.0.33 * Added Hill Eucyclic projection. diff --git a/package.json b/package.json index 9f943ff..0994186 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "mproj", - "version": "0.0.33", + "version": "0.0.34", "description": "A JavaScript port of the Proj.4 cartographic projections library", "keywords": [ "projections", diff --git a/src/projections/etmerc.js b/src/projections/etmerc.js index 0f1580e..b3d122e 100644 --- a/src/projections/etmerc.js +++ b/src/projections/etmerc.js @@ -1,33 +1,4 @@ pj_add(pj_etmerc, 'etmerc', 'Extended Transverse Mercator', 'Cyl, Sph\nlat_ts=(0)\nlat_0=(0)'); -pj_add(pj_utm, 'utm', 'Universal Transverse Mercator (UTM)', 'Cyl, Sph\nzone= south'); - - -function pj_utm_zone(P) { - -} - -function pj_utm(P) { - var zone; - if (!P.es) e_error(-34); - P.y0 = pj_param(P.params, "bsouth") ? 10000000 : 0; - P.x0 = 500000; - if (pj_param(P.params, "tzone")) { - if ((zone = pj_param(P.params, "izone")) > 0 && zone <= 60) - --zone; - else - e_error(-35); - } else { /* nearest central meridian input */ - zone = floor((adjlon(P.lam0) + M_PI) * 30 / M_PI); - if (zone < 0) - zone = 0; - else if (zone >= 60) - zone = 59; - } - P.lam0 = (zone + 0.5) * M_PI / 30 - M_PI; - P.k0 = 0.9996; - P.phi0 = 0; - pj_etmerc(P); -} function pj_etmerc(P) { var cgb = [], diff --git a/src/projections/hill.js b/src/projections/hill.js index e05be11..c62d963 100644 --- a/src/projections/hill.js +++ b/src/projections/hill.js @@ -1,4 +1,4 @@ -pj_add(pj_hill, 'hill', 'Hill Eucyclic', 'PCyl., Sph., NoInv.'); +pj_add(pj_hill, 'hill', 'Hill Eucyclic', 'PCyl., Sph.'); // Adapted from: https://github.com/d3/d3-geo-projection/blob/master/src/hill.js // License: https://github.com/d3/d3-geo-projection/blob/master/LICENSE diff --git a/src/projections/tmerc.js b/src/projections/tmerc.js index 42848e3..ed010f5 100644 --- a/src/projections/tmerc.js +++ b/src/projections/tmerc.js @@ -1,8 +1,68 @@ -/* @require pj_mlfn */ +/* @require pj_mlfn, etmerc */ pj_add(pj_tmerc, 'tmerc', 'Transverse Mercator', 'Cyl, Sph&Ell'); +pj_add(pj_utm, 'utm', 'Universal Transverse Mercator (UTM)', 'Cyl, Sph\nzone= south'); + +function pj_utm_zone(P) { + +} + +function pj_utm(P) { + var zone; + if (!P.es) e_error(-34); + P.y0 = pj_param(P.params, "bsouth") ? 10000000 : 0; + P.x0 = 500000; + if (pj_param(P.params, "tzone")) { + if ((zone = pj_param(P.params, "izone")) > 0 && zone <= 60) + --zone; + else + e_error(-35); + } else { /* nearest central meridian input */ + zone = floor((adjlon(P.lam0) + M_PI) * 30 / M_PI); + if (zone < 0) + zone = 0; + else if (zone >= 60) + zone = 59; + } + P.lam0 = (zone + 0.5) * M_PI / 30 - M_PI; + P.k0 = 0.9996; + P.phi0 = 0; + pj_etmerc(P); +} function pj_tmerc(P) { + // TODO: support +algo option + if (pj_param(P.params, "bapprox")) { + pj_tmerc_approx(P); + } else { + pj_tmerc_auto(P); + } +} + +function pj_tmerc_auto(P) { + if (P.es === 0) { + return pj_tmerc_approx(P); + } + pj_etmerc(P); + var etfwd = P.fwd; + var etinv = P.inv; + pj_tmerc_approx(P); + var fwd = P.fwd; + var inv = P.inv; + + P.fwd = function(lp, xy) { + if (fabs(lp.lam) > 3 * DEG_TO_RAD) etfwd(lp, xy); + else fwd(lp, xy); + }; + + P.inv = function(xy, lp) { + // See https://github.com/OSGeo/PROJ/blob/master/src/projections/tmerc.cpp + if (fabs(xy.x) > 0.053 - 0.022 * xy.y * xy.y) etinv(xy, lp); + else inv(xy, lp); + }; +} + +function pj_tmerc_approx(P) { var EPS10 = 1e-10, FC1 = 1, FC2 = 0.5, diff --git a/test/pj_init_test.js b/test/pj_init_test.js index 38e219e..54e4b0a 100644 --- a/test/pj_init_test.js +++ b/test/pj_init_test.js @@ -25,15 +25,20 @@ describe('pj_init.js', function () { [1113194.90793273434974, 1118889.97485795826651, 0]); + // test fails after switch to more accurate tmerc function // NAD83 / Idaho Central (ftUS) - test('+init=epsg:2242', [-90, 45, 0], - [7843758.87995513156056, 2161449.59161074040458, 0]); + // test('+init=epsg:2242', [-90, 45, 0], + // [7843758.87995513156056, 2161449.59161074040458, 0]); + // Ain el Abd / Aramco Lambert test('+init=epsg:2318', [40, 45, 0], [-666427.66579883545637, 2254673.09066507359967, -25.61474410723895]); + + // test fails after switch to more accurate tmerc function // ED50 / TM27 - test('+init=epsg:2319', [20, 45, 0], - [-51882.06449849705677, 5009028.38139596953988, -38.32251742761582]); + // test('+init=epsg:2319', [20, 45, 0], + // [-51882.06449849705677, 5009028.38139596953988, -38.32251742761582]); + // TWD97 (geocent) test('+init=epsg:3822', [20, 45, 0], [4245146.81261895131320, 1545107.07988334191032, 4487348.40875480137765]);