-
Notifications
You must be signed in to change notification settings - Fork 3
Description
When processing Sentinel-1 GRD data with SNAP (via snappy / GPF), the GeoTIFF-BigTIFF output generated after Terrain-Correction contains zero-valued pixels at image borders, where NoData or NaN values are expected.
This occurs even when attempting to define NoData explicitly (via SetNoDataValue or BandMaths).
This behavior affects products and makes it difficult to distinguish between physically valid zero backscatter or invalid / out-of-swath pixels.
Is there a recommended way to force NoData (-9999, float32) propagation to GeoTIFF outputs after Terrain-Correction? Or is this a known limitation/bug in the GeoTIFF writer for floating-point products?
Minimal reproducible example:
`
from esa_snappy import ProductIO, HashMap, GPF
import os
proj = 'WGS84(DD)'
def do_apply_orbit_file(source):
parameters = HashMap()
parameters.put('Apply-Orbit-File', True)
return GPF.createProduct('Apply-Orbit-File', parameters, source)
def do_remove_grd_border_noise(source):
return GPF.createProduct('Remove-GRD-Border-Noise', HashMap(), source)
def do_thermal_noise_removal(source):
parameters = HashMap()
parameters.put('removeThermalNoise', True)
return GPF.createProduct('ThermalNoiseRemoval', parameters, source)
def do_calibration(source):
parameters = HashMap()
parameters.put('outputSigmaBand', False)
parameters.put('outputBetaBand', True)
return GPF.createProduct("Calibration", parameters, source)
def do_terrain_flattening(source):
parameters = HashMap()
parameters.put('demName', 'Copernicus 30m Global DEM')
parameters.put('nodataValueAtSea', False)
return GPF.createProduct("Terrain-Flattening", parameters, source)
def do_terrain_correction(source, proj):
parameters = HashMap()
parameters.put('demName', 'Copernicus 30m Global DEM')
parameters.put('mapProjection', proj)
parameters.put('nodataValueAtSea', False)
parameters.put('saveSelectedSourceBand', True)
parameters.put('saveLocalIncidenceAngle', True)
return GPF.createProduct('Terrain-Correction', parameters, source)
def do_subset_band(source, band_name):
parameters = HashMap()
parameters.put('sourceBands', band_name)
return GPF.createProduct('Subset', parameters, source)
path = './data_s1/GRD/S1A_IW_GRDH_1SDV_20250704T094105_20250704T094130_059932_0771DC_011E.SAFE'
outpath = './s1_preprocessed/GRD'
os.makedirs(outpath, exist_ok=True)
product = ProductIO.readProduct(os.path.join(path, 'manifest.safe'))
applyorbit = do_apply_orbit_file(product)
removebordernoise = do_remove_grd_border_noise(applyorbit)
thermalnoiseremoval = do_thermal_noise_removal(removebordernoise)
calibration = do_calibration(thermalnoiseremoval)
terrainflattening = do_terrain_flattening(calibration)
rtc = do_terrain_correction(terrainflattening, proj)
gamma0_vv = do_subset_band(rtc, 'Gamma0_VV')
output = os.path.join(outpath, 'gamma0VV_RTC')
ProductIO.writeProduct(gamma0_vv, output, 'GeoTIFF-BigTIFF')
`