Skip to content

Commit

Permalink
Preparation for final delivery (#205)
Browse files Browse the repository at this point in the history
* specfile update

* environment.yml update

* remove installing s1-reader from source code

* update enrivonment.yml for CI test

* update environment.yml and specfile.txt to make CI running

* add scikit-image

* specfile update

* retract unused file `env_compass.yaml`; add whitespace to `environment.yml`

* bug fix when computing bounding box for land polygon rasterization

* remove debugging code in `_get_land_mask()`

* fix on y_spacing in metadata

* bump the version

* -abs(y_spacing) -> y_spacing

* Working version of shapely & pyproj-based land mask extractor

* coda cleanup

* land lask computation using gdal, ogr, and osr

* docstring cleanup

* Get rid of redundant `pysolid` in `environment.yml`

* revise lines for module import

---------

Co-authored-by: Seongsu Jeong <[email protected]>
  • Loading branch information
seongsujeong and Seongsu Jeong authored Aug 30, 2023
1 parent 998e203 commit 1428feb
Show file tree
Hide file tree
Showing 6 changed files with 185 additions and 175 deletions.
7 changes: 0 additions & 7 deletions docker/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -41,13 +41,6 @@ SHELL ["conda", "run", "-n", "COMPASS", "/bin/bash", "-c"]

WORKDIR /home/compass_user/OPERA

# installing OPERA s1-reader
RUN curl -sSL https://github.com/isce-framework/s1-reader/archive/refs/tags/v0.2.0.tar.gz -o s1_reader_src.tar.gz &&\
tar -xvf s1_reader_src.tar.gz &&\
ln -s s1-reader-0.2.0 s1-reader &&\
rm s1_reader_src.tar.gz &&\
python -m pip install ./s1-reader

# installing RAiDER
RUN mkdir RAiDER &&\
git clone https://github.com/dbekaert/RAiDER.git RAiDER &&\
Expand Down
217 changes: 90 additions & 127 deletions docker/specfile.txt

Large diffs are not rendered by default.

13 changes: 12 additions & 1 deletion environment.yml
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,17 @@ dependencies:
- scipy>=1.0,<1.13
- yamale>=4.0
- h5py>=3.5
- s1reader>=0.2.0
- s1reader>=0.2.1
- shapely>=1.8
- requests>=2.0
- scikit-image
# CI unit test
- pytest
- pluggy
- pytest-order
# Dependencies for RAiDER
- progressbar
- rasterio
- dem_stitcher
- gxx_linux-64>=9,<10

118 changes: 80 additions & 38 deletions src/compass/s1_cslc_qa.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,14 +5,11 @@
import json
import os
from pathlib import Path
import time

import isce3
import geopandas as gpd
from shapely.geometry import box
import numpy as np

import rasterio
from rasterio.features import rasterize
from osgeo import ogr, osr, gdal
from scipy import ndimage

from compass.s1_rdr2geo import (file_name_los_east,
Expand Down Expand Up @@ -620,43 +617,88 @@ def _get_valid_pixel_mask(arr_cslc):


def _get_land_mask(epsg_cslc: int, geotransform: tuple, shape_mask: tuple):
# Load the shapefile into a GeoDataFrame
if os.path.exists(LAND_GPKG_FILE):
gdf1 = gpd.read_file(LAND_GPKG_FILE)
else:
raise RuntimeError('Cannot find a land mask GPKG file for '
f'pixel classification: {LAND_GPKG_FILE}')
'''
Get the land mask within the CSLC bounding box
# Create a bounding box (minx, miny, maxx, maxy)
Parameters
----------
epsg_cslc: int
EPSG code of the CSLC layer
geotransform: tuple
Geotransform vector of the CSLC layer
shape_mask: tuple
Shape of the raster as numpy array
Returns
-------
mask_land: np.ndarray
Raster Mask for land area. `1` is land, `0` otherwise
'''
# Extract the land polygon
ds_land = ogr.Open(LAND_GPKG_FILE, 0)
layer_land = ds_land.GetLayer()
feature = layer_land.GetNextFeature()
land_polygon = feature.GetGeometryRef()

# extract the EPSG of the land polgyon GPKG
srs_gpkg = layer_land.GetSpatialRef()
land_epsg = int(srs_gpkg.GetAuthorityCode(None))

# Compute and create the bounding box
xmin = geotransform[0]
ymin = geotransform[3] + geotransform[5] * shape_mask[0]
xmax = geotransform[0] + geotransform[1] * shape_mask[1]
ymax = geotransform[3]

bbox = box(xmin, ymin, xmax, ymax)

# Make sure the CRS of the bounding box is the same as the GeoDataFrame
bbox = gpd.GeoSeries([bbox], crs=f'EPSG:{epsg_cslc}')
if epsg_cslc != 3413:
bbox_3413 = bbox.to_crs('EPSG:3413')

# Check if the polygon intersects with the bounding box.
if not gdf1.geometry.iloc[0].intersects(bbox_3413.iloc[0]):
# no overlap
bbox_cslc = ogr.Geometry(ogr.wkbPolygon)
ring_cslc = ogr.Geometry(ogr.wkbLinearRing)
ring_cslc.AddPoint(xmin, ymin)
ring_cslc.AddPoint(xmax, ymin)
ring_cslc.AddPoint(xmax, ymax)
ring_cslc.AddPoint(xmin, ymax)
ring_cslc.AddPoint(xmin, ymin)
bbox_cslc.AddGeometry(ring_cslc)

# Define the SRS for CSLC and land polygon
srs_cslc = osr.SpatialReference()
srs_cslc.ImportFromEPSG(epsg_cslc)

srs_land = osr.SpatialReference()
srs_land.ImportFromEPSG(land_epsg)

# Reproject the bounding box (in CSLC EPSG) to land polygon's EPSG
transformer_cslc_to_land = osr.CoordinateTransformation(srs_cslc, srs_land)
bbox_cslc.Transform(transformer_cslc_to_land)

# Return a numpy array full of `False` when there is no intersection
if not bbox_cslc.Intersects(land_polygon):
return np.full(shape_mask, False)

# Perform the intersection
intersection_3413 = gdf1.geometry.iloc[0].intersection(bbox_3413.iloc[0])
intersection_gs = gpd.GeoSeries([intersection_3413], crs='EPSG:3413')

if epsg_cslc != 3413:
intersection_gs = intersection_gs.to_crs(f'EPSG:{epsg_cslc}')

tform_bbox = rasterio.transform.from_bounds(xmin, ymin, xmax, ymax,
shape_mask[1], shape_mask[0])

image = rasterize(intersection_gs.geometry,
transform=tform_bbox,
out_shape=shape_mask,
dtype=np.uint8, default_value=1)
return image
# Compute the intersection and reproject the result back to CSLC's EPSG
intersection_land = bbox_cslc.Intersection(land_polygon)
transformer_land_to_cslc = osr.CoordinateTransformation(srs_land, srs_cslc)
intersection_land.Transform(transformer_land_to_cslc)

# Build up a vector layer, and add a feature that has `intersection_land`` as geometry
drv_intersection_polygon = ogr.GetDriverByName('Memory')
ds_intersection_polygon = drv_intersection_polygon.CreateDataSource(str(time.time_ns))
layer_intersection = ds_intersection_polygon.CreateLayer('layer_intersection',
srs_cslc,
ogr.wkbPolygon)
feature_defn = layer_intersection.GetLayerDefn()
feature = ogr.Feature(feature_defn)
feature.SetGeometry(intersection_land)
layer_intersection.CreateFeature(feature)

# Prepare for output layer for the rasterization
drv_raster_out = gdal.GetDriverByName('MEM')
rasterized_land = drv_raster_out.Create(str(time.time_ns),
shape_mask[1], shape_mask[0],
1, gdal.GDT_Byte)
rasterized_land.SetGeoTransform(geotransform)
rasterized_land.SetProjection(srs_cslc.ExportToWkt())

gdal.RasterizeLayer(rasterized_land, [1], layer_intersection)

mask_land = rasterized_land.ReadAsArray()

return mask_land
4 changes: 2 additions & 2 deletions src/compass/utils/h5_helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -163,7 +163,7 @@ def init_geocoded_dataset(grid_group, dataset_name, geo_grid, dtype,
Meta('x_spacing', geo_grid.spacing_x,
'Spacing of the geographical grid along X-direction',
{'units': 'meters'}),
Meta('y_spacing', np.abs(geo_grid.spacing_y),
Meta('y_spacing', geo_grid.spacing_y,
'Spacing of the geographical grid along Y-direction',
{'units': 'meters'})
]
Expand Down Expand Up @@ -781,7 +781,7 @@ def corrections_to_h5group(parent_group, burst, cfg, rg_lut, az_lut,
'spacing of slant range of LUT data', {'units': 'meters'}),
Meta('zero_doppler_time', azimuth, 'azimuth time of LUT data',
{'units': 'seconds'}),
Meta('zero_doppler_time_spacing', np.abs(rg_lut.y_spacing),
Meta('zero_doppler_time_spacing', rg_lut.y_spacing,
'spacing of azimuth time of LUT data', {'units': 'seconds'}),
Meta('bistatic_delay', ds.GetRasterBand(2).ReadAsArray(),
f'bistatic delay (azimuth) {desc}', {'units': 'seconds'}),
Expand Down
1 change: 1 addition & 0 deletions src/compass/version.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
# release history
Tag = collections.namedtuple('Tag', 'version date')
release_history = (
Tag('0.5.0', '2023-08-25'),
Tag('0.4.1', '2023-08-14'),
Tag('0.4.0', '2023-07-26'),
Tag('0.3.1', '2023-06-01'),
Expand Down

0 comments on commit 1428feb

Please sign in to comment.