Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

(Un)wrapping of DEM tiles across dateline #50

Merged
merged 43 commits into from
Dec 20, 2022
Merged

(Un)wrapping of DEM tiles across dateline #50

merged 43 commits into from
Dec 20, 2022

Conversation

cmarshak
Copy link
Collaborator

@cmarshak cmarshak commented Nov 23, 2022

Solves #47 by (un)wrapping DEM tiles and geoid when extents cross anti-meridian / dateline.

@cmarshak cmarshak marked this pull request as draft November 23, 2022 20:56
@review-notebook-app
Copy link

Check out this pull request on  ReviewNB

See visual diffs & provide feedback on Jupyter Notebooks.


Powered by ReviewNB

@cmarshak
Copy link
Collaborator Author

cmarshak commented Nov 30, 2022

Here are two examples that include typical resampling for square resolution cells at these higher latitudes:

aleutian_example_l.tif
aleutian_example_r.tif

Unfortunately, QGIS has some difficulty wrapping map tiles at the dateline too. When using epsg:3857 for viewing in QGIS, the rasters wrapped automatically so a lat/lon that extended beyond the dateline appeared as disjoint rasters. When using epsg:4326, the memory on my machine spiked and I had to force quit. In the next comment, I provide some tiles for more direct comparison, albeit much more annoying.

The rasters were generated as indicated here:

from dem_stitcher.stitcher import stitch_dem
import rasterio
from pathlib import Path

# Aleutian Volcano Chain
# xmin, ymin, xmax, ymax
bounds_l = [-181, 51, -179, 52]
bounds_r = [179, 51, 181, 52]

dst_area_or_point = 'Point'
dst_ellipsoidal_height = False
dem_name = 'glo_30'

X_l, p_l = stitch_dem(bounds_l,
                      dem_name=dem_name,
                      dst_ellipsoidal_height=dst_ellipsoidal_height,
                      dst_resolution=0.00027777777777777,
                      dst_area_or_point=dst_area_or_point)

X_r, p_r = stitch_dem(bounds_r,
                      dem_name=dem_name,
                      dst_ellipsoidal_height=dst_ellipsoidal_height,
                      dst_resolution=0.00027777777777777,
                      dst_area_or_point=dst_area_or_point)

with rasterio.open('aleutian_example_l.tif', 'w', **p_l) as ds:
    ds.write(X_l, 1)
    ds.update_tags(AREA_OR_POINT=dst_area_or_point) 

with rasterio.open('aleutian_example_r.tif', 'w', **p_r) as ds:
    ds.write(X_r, 1)
    ds.update_tags(AREA_OR_POINT=dst_area_or_point) 

Comment on lines +180 to +188
tags = dataset.tags()
if crossing == 180 and xmax <= 0:
memfile, dataset_new = translate_dataset(dataset, 360 / res_x, 0)
# Ensures area or point are correctly stored!
dataset_new.update_tags(**tags)
elif crossing == -180 and xmin >= 0:
memfile, dataset_new = translate_dataset(dataset, -360 / res_x, 0)
# Ensures area or point are correctly stored!
dataset_new.update_tags(**tags)
Copy link
Collaborator Author

@cmarshak cmarshak Dec 6, 2022

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copying tags from the tiles ensures rest of workflow is correct. If relevant tags are not present, the tiles are assumed to have AREA tag and there will be a nefarious half pixel shift. I realized this when I made an (embarrassing) post on the Affine library and Sean Gillies very nicely responded indicating that I was not writing down the affine transformation correctly.

Comment on lines +85 to +102
@pytest.mark.integration
def test_stitcher_across_dateline_approaching_from_left_and_right():
bounds_l = [-181, 51.25, -179, 51.75]
X_l, p_l = stitch_dem(bounds_l, 'glo_30', dst_ellipsoidal_height=False, dst_area_or_point='Point')

bounds_r = [179, 51.25, 181, 51.75]
X_r, p_r = stitch_dem(bounds_r, 'glo_30', dst_ellipsoidal_height=False, dst_area_or_point='Point')

# Metadata should be the same after translation
res_x = p_r['transform'].a
p_r_t = translate_profile(p_r, -360 / res_x, 0)

# Georefernencing
assert p_r_t['crs'] == p_l['crs']
assert p_r_t['transform'] == p_l['transform']

# Arrays should be the same as well
assert_almost_equal(X_r, X_l, 5)
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This demonstrates that approaching Aleutians from the left of the globe or the right provides identical arrays and the same geo-metadata after translation through the stitch_dem API.

@cmarshak cmarshak marked this pull request as ready for review December 6, 2022 18:06
@cmarshak cmarshak requested a review from mgovorcin December 6, 2022 18:09
@cmarshak cmarshak added the minor Bump the minor version number of this project label Dec 6, 2022
@cmarshak cmarshak changed the title Wrapping of DEM tiles across dateline Unwrapping of DEM tiles across dateline Dec 7, 2022
@cmarshak cmarshak changed the title Unwrapping of DEM tiles across dateline (Un)wrapping of DEM tiles across dateline Dec 9, 2022
@cmarshak cmarshak merged commit abc1e81 into dev Dec 20, 2022
@cmarshak cmarshak deleted the antimeridian branch December 20, 2022 20:23
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
minor Bump the minor version number of this project
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants