|
20 | 20 | #include <isce3/product/Product.h>
|
21 | 21 |
|
22 | 22 | // isce3::geometry
|
| 23 | +#include <isce3/geometry/RTC.h> |
23 | 24 | #include "DEMInterpolator.h"
|
24 | 25 | #include "TopoLayers.h"
|
25 | 26 |
|
@@ -143,6 +144,9 @@ topo(Raster & demRaster, TopoLayers & layers)
|
143 | 144 | const double endingRange = _radarGrid.endingRange();
|
144 | 145 | const double midRange = _radarGrid.midRange();
|
145 | 146 |
|
| 147 | + info << "DEM EPSG: " << demRaster.getEPSG() << pyre::journal::newline; |
| 148 | + info << "Output EPSG: " << _epsgOut << pyre::journal::endl; |
| 149 | + |
146 | 150 | // Loop over blocks
|
147 | 151 | size_t totalconv = 0;
|
148 | 152 | for (size_t block = 0; block < nBlocks; ++block) {
|
@@ -619,16 +623,39 @@ _setOutputTopoLayers(Vec3 & targetLLH, TopoLayers & layers, size_t line,
|
619 | 623 | }
|
620 | 624 | layers.hdg(line, bin, heading);
|
621 | 625 |
|
| 626 | + // Project output coordinates to DEM coordinates |
| 627 | + auto input_coords_llh = _proj->inverse({x, y, targetLLH[2]}); |
| 628 | + Vec3 dem_vect = demInterp.proj()->forward(input_coords_llh); |
| 629 | + |
622 | 630 | // East-west slope using central difference
|
623 |
| - double aa = demInterp.interpolateXY(x - demInterp.deltaX(), y); |
624 |
| - double bb = demInterp.interpolateXY(x + demInterp.deltaX(), y); |
625 |
| - double gamma = targetLLH[1]; |
626 |
| - double alpha = ((bb - aa) * degrees) / (2.0 * _ellipsoid.rEast(gamma) * demInterp.deltaX()); |
| 631 | + double aa = demInterp.interpolateXY(dem_vect[0] - demInterp.deltaX(), dem_vect[1]); |
| 632 | + double bb = demInterp.interpolateXY(dem_vect[0] + demInterp.deltaX(), dem_vect[1]); |
| 633 | + |
| 634 | + Vec3 dem_vect_p_dx = {dem_vect[0] + demInterp.deltaX(), dem_vect[1], dem_vect[2]}; |
| 635 | + Vec3 dem_vect_m_dx = {dem_vect[0] - demInterp.deltaX(), dem_vect[1], dem_vect[2]}; |
| 636 | + Vec3 input_coords_llh_p_dx, input_coords_llh_m_dx; |
| 637 | + demInterp.proj()->inverse(dem_vect_p_dx, input_coords_llh_p_dx); |
| 638 | + demInterp.proj()->inverse(dem_vect_m_dx, input_coords_llh_m_dx); |
| 639 | + const Vec3 input_coords_xyz_p_dx = _ellipsoid.lonLatToXyz(input_coords_llh_p_dx); |
| 640 | + const Vec3 input_coords_xyz_m_dx = _ellipsoid.lonLatToXyz(input_coords_llh_m_dx); |
| 641 | + double dx = (input_coords_xyz_p_dx - input_coords_xyz_m_dx).norm(); |
| 642 | + |
| 643 | + double alpha = (bb - aa) / dx; |
627 | 644 |
|
628 | 645 | // North-south slope using central difference
|
629 |
| - aa = demInterp.interpolateXY(x, y - demInterp.deltaY()); |
630 |
| - bb = demInterp.interpolateXY(x, y + demInterp.deltaY()); |
631 |
| - double beta = ((bb - aa) * degrees) / (2.0 * _ellipsoid.rNorth(gamma) * demInterp.deltaY()); |
| 646 | + aa = demInterp.interpolateXY(dem_vect[0], dem_vect[1] - demInterp.deltaY()); |
| 647 | + bb = demInterp.interpolateXY(dem_vect[0], dem_vect[1] + demInterp.deltaY()); |
| 648 | + |
| 649 | + Vec3 dem_vect_p_dy = {dem_vect[0], dem_vect[1] + demInterp.deltaY(), dem_vect[2]}; |
| 650 | + Vec3 dem_vect_m_dy = {dem_vect[0], dem_vect[1] - demInterp.deltaY(), dem_vect[2]}; |
| 651 | + Vec3 input_coords_llh_p_dy, input_coords_llh_m_dy; |
| 652 | + demInterp.proj()->inverse(dem_vect_p_dy, input_coords_llh_p_dy); |
| 653 | + demInterp.proj()->inverse(dem_vect_m_dy, input_coords_llh_m_dy); |
| 654 | + const Vec3 input_coords_xyz_p_dy = _ellipsoid.lonLatToXyz(input_coords_llh_p_dy); |
| 655 | + const Vec3 input_coords_xyz_m_dy = _ellipsoid.lonLatToXyz(input_coords_llh_m_dy); |
| 656 | + double dy = (input_coords_xyz_p_dy - input_coords_xyz_m_dy).norm(); |
| 657 | + |
| 658 | + double beta = (bb - aa) / dy; |
632 | 659 |
|
633 | 660 | // Compute local incidence angle
|
634 | 661 | const Vec3 enunorm = enu.normalized();
|
@@ -675,6 +702,17 @@ setLayoverShadow(TopoLayers& layers, DEMInterpolator& demInterp,
|
675 | 702 | // Initialize mask to zero for this block
|
676 | 703 | layers.mask() = 0;
|
677 | 704 |
|
| 705 | + // Prepare function getDemCoords() to interpolate DEM |
| 706 | + std::function<Vec3(double, double, |
| 707 | + const isce3::geometry::DEMInterpolator&, |
| 708 | + isce3::core::ProjectionBase*)> getDemCoords; |
| 709 | + |
| 710 | + if (_epsgOut == demInterp.epsgCode()) { |
| 711 | + getDemCoords = isce3::geometry::getDemCoordsSameEpsg; |
| 712 | + } else { |
| 713 | + getDemCoords = isce3::geometry::getDemCoordsDiffEpsg; |
| 714 | + } |
| 715 | + |
678 | 716 | // Loop over lines in block
|
679 | 717 | #pragma omp parallel for firstprivate(x, y, ctrack, ctrackGrid, \
|
680 | 718 | slantRangeGrid, maskGrid)
|
@@ -720,12 +758,11 @@ setLayoverShadow(TopoLayers& layers, DEMInterpolator& demInterp,
|
720 | 758 | const double y_grid = y[k] * frac1 + y[k+1] * frac2;
|
721 | 759 |
|
722 | 760 | // Interpolate DEM at x/y
|
723 |
| - const float z_grid = demInterp.interpolateXY(x_grid, y_grid); |
| 761 | + Vec3 demXYZ = getDemCoords(x_grid, y_grid, demInterp, _proj); |
724 | 762 |
|
725 | 763 | // Convert DEM XYZ to ECEF XYZ
|
726 | 764 | Vec3 llh, xyz, satToGround;
|
727 |
| - Vec3 demXYZ{x_grid, y_grid, z_grid}; |
728 |
| - _proj->inverse(demXYZ, llh); |
| 765 | + demInterp.proj()->inverse(demXYZ, llh); |
729 | 766 | _ellipsoid.lonLatToXyz(llh, xyz);
|
730 | 767 |
|
731 | 768 | // Compute and save slant range
|
|
0 commit comments