diff options
| author | Even Rouault <even.rouault@spatialys.com> | 2020-09-26 14:40:29 +0200 |
|---|---|---|
| committer | Even Rouault <even.rouault@spatialys.com> | 2020-09-26 18:55:25 +0200 |
| commit | 3d88b6fc89f95803bfd4d59c47eef1c05bda710c (patch) | |
| tree | a67c595277c9cdce18dac60b771fdaad7ff089eb /src/projections | |
| parent | 2e104e092578347de11208e9a3a80a3bf711265d (diff) | |
| download | PROJ-3d88b6fc89f95803bfd4d59c47eef1c05bda710c.tar.gz PROJ-3d88b6fc89f95803bfd4d59c47eef1c05bda710c.zip | |
Ortho: add visibility condition for ellipsoidal case. Credits to @cffk
Diffstat (limited to 'src/projections')
| -rw-r--r-- | src/projections/ortho.cpp | 15 |
1 files changed, 15 insertions, 0 deletions
diff --git a/src/projections/ortho.cpp b/src/projections/ortho.cpp index ff9d9341..0594205b 100644 --- a/src/projections/ortho.cpp +++ b/src/projections/ortho.cpp @@ -50,6 +50,13 @@ static PJ_XY ortho_s_forward (PJ_LP lp, PJ *P) { /* Spheroidal, forwar break; case OBLIQ: sinphi = sin(lp.phi); + + // Is the point visible from the projection plane ? + // From https://lists.osgeo.org/pipermail/proj/2020-September/009831.html + // this is the dot product of the normal of the ellipsoid at the center of + // the projection and at the point considered for projection. + // [cos(phi)*cos(lambda), cos(phi)*sin(lambda), sin(phi)] + // Also from Snyder's Map Projection - A working manual, equation (5-3), page 149 if (Q->sinph0 * sinphi + Q->cosph0 * cosphi * coslam < - EPS10) return forward_error(P, lp, xy); xy.y = Q->cosph0 * sinphi - Q->sinph0 * cosphi * coslam; @@ -131,6 +138,14 @@ static PJ_XY ortho_e_forward (PJ_LP lp, PJ *P) { /* Ellipsoidal, forwa const double sinphi = sin(lp.phi); const double coslam = cos(lp.lam); const double sinlam = sin(lp.lam); + + // Is the point visible from the projection plane ? + // Same condition as in spherical case + if (Q->sinph0 * sinphi + Q->cosph0 * cosphi * coslam < - EPS10) { + xy.x = HUGE_VAL; xy.y = HUGE_VAL; + return forward_error(P, lp, xy); + } + const double nu = 1.0 / sqrt(1.0 - P->es * sinphi * sinphi); xy.x = nu * cosphi * sinlam; xy.y = nu * (sinphi * Q->cosph0 - cosphi * Q->sinph0 * coslam) + |
