curryer.correction.image_io

Image I/O utilities for correction pipeline.

Provides format-agnostic loading and saving of image data used in the correction pipeline. All format-specific logic is in private helpers; the public API dispatches on file extension so callers never need to know the underlying format.

Supported formats

.mat — MATLAB struct files (calibration and legacy test data). .nc / .netcdf / .nc4 — NetCDF (regridded GCPs, outputs). .hdf / .h5 — HDF4/5 raw GCP chips; use load_gcp_chip_from_hdf()

then curryer.correction.regrid to convert ECEF to an ImageGrid.

Public API (9 functions)

load_image_grid() — any image file → ImageGrid load_named_image_grid() — any image file → NamedImageGrid load_observation_file() — observation + spacecraft position load_los_vectors() — LOS unit vectors from calibration file load_optical_psf() — PSF entries from calibration file load_gcp_chip_from_hdf() — raw HDF chip (band + ECEF arrays) save_image_grid() — write ImageGrid; format from extension infer_spacecraft_state() — derive boresight/t_matrix from position geolocated_to_image_grid() — convert geolocated xr.Dataset → ImageGrid

Attributes

Functions

load_image_grid(→ curryer.correction.grid_types.ImageGrid)

Load any supported image file as an ImageGrid.

load_optical_psf(...)

Load optical PSF entries from a .mat calibration file.

load_los_vectors(→ numpy.ndarray)

Load line-of-sight unit vectors from a .mat calibration file.

load_gcp_chip_from_hdf() → tuple[numpy.ndarray, ...)

Load raw GCP chip data from HDF file (Landsat format).

save_image_grid(→ None)

Save an ImageGrid to file.

load_named_image_grid(...)

Load any supported image file as a NamedImageGrid.

load_observation_file(...)

Load one observation file and return (ImageGrid, spacecraft_position_m).

infer_spacecraft_state(→ tuple[numpy.ndarray, ...)

Deprecated — use resolve_spacecraft_ecef from curryer.correction.psf instead.

geolocated_to_image_grid(...)

Convert a geolocated xr.Dataset to an ImageGrid for image matching.

Module Contents

curryer.correction.image_io.logger
curryer.correction.image_io.load_image_grid(filepath: pathlib.Path | str, mat_key: str = 'subimage') curryer.correction.grid_types.ImageGrid

Load any supported image file as an ImageGrid.

Dispatches on file extension — callers do not need to know the underlying format.

Parameters:
  • filepath (path-like) – Path to the image file. Local paths and s3:// URIs supported (S3 requires boto3).

  • mat_key (str, optional) – MATLAB struct key. Defaults to "subimage". Ignored for NetCDF.

Return type:

ImageGrid

Raises:
  • ValueError – If the file extension is not recognised.

  • FileNotFoundError – If filepath does not exist.

Examples

>>> obs = load_image_grid(Path("subimage.mat"), mat_key="subimage")
>>> gcp = load_image_grid(Path("GCP12055_regridded.nc"))
curryer.correction.image_io.load_optical_psf(mat_file: str | pathlib.Path, key: str = 'PSF_struct_675nm') list[curryer.correction.grid_types.OpticalPSFEntry]

Load optical PSF entries from a .mat calibration file.

Parameters:
  • mat_file (str or Path) – Path to MATLAB file with PSF data (local path or s3:// URI).

  • key (str, default="PSF_struct_675nm") – Primary key to try for PSF data.

Returns:

Optical PSF samples with data, x, and field_angle arrays.

Return type:

list[OpticalPSFEntry]

Raises:
  • FileNotFoundError – If mat_file is a local path and doesn’t exist.

  • ImportError – If mat_file is an S3 URI and boto3 is not installed.

  • KeyError – If no PSF data found with common key names.

  • ValueError – If PSF entries missing field angle attribute.

curryer.correction.image_io.load_los_vectors(mat_file: str | pathlib.Path, key: str = 'b_HS') numpy.ndarray

Load line-of-sight unit vectors from a .mat calibration file.

Parameters:
  • mat_file (str or Path) – Path to MATLAB file with LOS vectors (local path or s3:// URI).

  • key (str, default="b_HS") – Primary key to try for LOS data.

Returns:

LOS unit vectors in instrument frame, shape (n_pixels, 3).

Return type:

np.ndarray

Raises:
  • FileNotFoundError – If mat_file is a local path and doesn’t exist.

  • ImportError – If mat_file is an S3 URI and boto3 is not installed.

  • KeyError – If no LOS vectors found with common key names.

curryer.correction.image_io.load_gcp_chip_from_hdf(filepath: pathlib.Path, band_name: str = 'Band_1', coord_names: tuple[str, str, str] = ('ECR_x_coordinate_array', 'ECR_y_coordinate_array', 'ECR_z_coordinate_array')) tuple[numpy.ndarray, numpy.ndarray, numpy.ndarray, numpy.ndarray]

Load raw GCP chip data from HDF file (Landsat format).

Supports both HDF4 and HDF5 formats. Tries HDF4 first (Landsat standard), then falls back to HDF5 if needed.

Parameters:
  • filepath (Path) – Path to HDF file containing GCP chip data.

  • band_name (str, default="Band_1") – Name of the dataset containing band/radiometric data.

  • coord_names (tuple[str, str, str], default=("ECR_x_coordinate_array", ...)) – Names of X, Y, Z coordinate datasets (ECEF coordinates in meters).

Returns:

  • band_data (np.ndarray) – 2D array of radiometric values, shape (nrows, ncols).

  • ecef_x, ecef_y, ecef_z (np.ndarray) – 2D arrays of ECEF coordinates in meters, each shape (nrows, ncols).

Raises:
  • FileNotFoundError – If filepath doesn’t exist.

  • KeyError – If required datasets not found in HDF file.

  • ValueError – If array shapes are inconsistent.

Examples

>>> band, x, y, z = load_gcp_chip_from_hdf("LT08CHP.20140803.hdf")
>>> band.shape
(1400, 1400)
curryer.correction.image_io.save_image_grid(filepath: pathlib.Path, image_grid: curryer.correction.grid_types.ImageGrid, metadata: dict | None = None, compression: bool = True, band_units: str = 'DN', band_long_name: str = 'regridded_radiance') None

Save an ImageGrid to file.

The output format is determined by the file extension:

  • .nc / .netcdf / .nc4 → CF-1.8 NetCDF (via netCDF4)

  • .mat → MATLAB struct (key "GCP")

  • .tif / .tiff → GeoTIFF (requires rasterio)

Parameters:
  • filepath (Path) – Output file path. Extension controls the format.

  • image_grid (ImageGrid) – Image data with lat/lon coordinates.

  • metadata (dict, optional) – Additional metadata written as file-level attributes or tags.

  • compression (bool, optional) – Enable compression for NetCDF output (default True). Ignored for other formats.

  • band_units (str, optional) – units / long_name for the band data variable in NetCDF output (defaults describe a regridded Landsat GCP chip in digital numbers). Ignored for other formats.

  • band_long_name (str, optional) – units / long_name for the band data variable in NetCDF output (defaults describe a regridded Landsat GCP chip in digital numbers). Ignored for other formats.

Raises:

ValueError – If the file extension is not supported.

Examples

>>> save_image_grid(Path("chip.nc"), regridded, metadata={"band": "red"})
>>> save_image_grid(Path("chip.mat"), regridded)
curryer.correction.image_io.load_named_image_grid(filepath: pathlib.Path | str, mat_key: str = 'subimage') curryer.correction.grid_types.NamedImageGrid

Load any supported image file as a NamedImageGrid.

Dispatches on file extension so callers do not need to know the underlying format. The returned grid always carries the file path as its name.

Supported formats

.mat

MATLAB struct file. The struct accessed via mat_key must have data, lat, and lon attributes (and optionally h).

.nc / .netcdf / .nc4

NetCDF file written by save_image_grid() or the regridding pipeline (expects band_data, lat, lon).

param filepath:

Path to the image file.

type filepath:

path-like

param mat_key:

MATLAB struct key to read. Defaults to "subimage". Ignored for NetCDF files.

type mat_key:

str, optional

returns:

Loaded image grid with name set to the string representation of filepath.

rtype:

NamedImageGrid

raises ValueError:

If the file extension is not recognised.

raises FileNotFoundError:

If filepath does not exist.

Examples

>>> obs = load_named_image_grid(Path("TestCase1a_subimage.mat"), mat_key="subimage")
>>> gcp = load_named_image_grid(Path("GCP12055Dili_regridded.nc"))
curryer.correction.image_io.load_observation_file(filepath: str | pathlib.Path, mat_key: str = 'subimage') tuple[curryer.correction.grid_types.ImageGrid, numpy.ndarray | None]

Load one observation file and return (ImageGrid, spacecraft_position_m).

Supports .mat and NetCDF (.nc, .nc4, .netcdf) formats. The spacecraft ECEF position is extracted when available in the file; when absent, None is returned and callers should fall back to infer_spacecraft_state().

Parameters:
  • filepath (str or Path) – Local path or s3:// URI to a .mat or .nc observation file.

  • mat_key (str, optional) – MATLAB struct key containing the image data. Defaults to "subimage". Ignored for NetCDF files.

Returns:

  • grid (ImageGrid) – Radiance data on a lat/lon grid.

  • r_spacecraft_m (ndarray of shape (3,) or None) – Spacecraft ECEF position in meters at the mid-frame, extracted from the file when available. None when not present — caller should use infer_spacecraft_state() to approximate.

Raises:
  • ValueError – If the file extension is not recognised.

  • FileNotFoundError – If filepath is a local path that does not exist.

  • ImportError – If filepath is an S3 URI and boto3 is not installed.

curryer.correction.image_io.infer_spacecraft_state(grid: curryer.correction.grid_types.ImageGrid, r_spacecraft_m: numpy.ndarray | None, default_altitude_m: float = 400000.0) tuple[numpy.ndarray, numpy.ndarray, numpy.ndarray]

Deprecated — use resolve_spacecraft_ecef from curryer.correction.psf instead.

curryer.correction.image_io.geolocated_to_image_grid(geo_dataset: xarray.Dataset) curryer.correction.grid_types.ImageGrid

Convert a geolocated xr.Dataset to an ImageGrid for image matching.

This is the canonical adapter between SPICE geolocation output and the image-matching subsystem. It should be used wherever an ImageGrid is needed from an already-geolocated dataset, ensuring a single consistent implementation across the correction pipeline and the verification module.

Parameters:

geo_dataset (xr.Dataset) – Geolocated dataset with latitude and longitude variables (2-D arrays) and optionally altitude/height, radiance, or reflectance.

Returns:

Image grid with lat, lon, h from the dataset and data set to the first available of radiance, reflectance, or an all-ones placeholder.

Return type:

ImageGrid

Notes

Altitude/height defaults to an all-zeros array when absent. The placeholder data array (all ones) is used only for geometric operations where actual radiance values are not yet required.