coronagraphoto#

Coronagraphic image simulation built on JAX.

Scene primitives (Star, Planet, Disk, System, Scene, backgrounds) live in skyscapes. coronagraphoto consumes a skyscapes.Scene and produces either deterministic count-rate maps (*_rate functions, differentiable, used for fitting and retrievals) or Poisson-realised detector readouts (*_readout functions, used for data generation).

Submodules#

Functions#

load_scene_from_exovista(fits_file[, planet_indices, ...])

Load a full skyscapes.Scene from an ExoVista FITS file.

disk_rate(disk, optical_path, *, start_time_jd, ...)

Generate the disk count rate on the detector.

disk_readout(disk, optical_path, prng_key, *, ...)

Process a disk through the provided optical path.

planet_rate(planet, optical_path, *, start_time_jd, ...)

Generate the per-batch planet count rate on the detector.

planet_readout(planet, optical_path, prng_key, *, ...)

Process a per-batch Planet through the optical path.

speckle_rate(speckle, optical_path, *, start_time_jd, ...)

Generate the speckle count rate on the detector.

speckle_readout(speckle, optical_path, prng_key, *, ...)

Process a speckle field through the provided optical path.

star_rate(star, optical_path, *, start_time_jd, ...)

Generate the star count rate on the detector.

star_readout(star, optical_path, prng_key, *, ...)

Process a star through the provided optical path.

system_rate(scene, optical_path, *, start_time_jd, ...)

Sum of deterministic per-source count rates for a Scene.

system_readout(scene, optical_path, prng_key, *, ...)

Simulate a full Scene through the optical path.

zodi_rate(zodi, optical_path, *, start_time_jd, ...)

Generate the zodi count rate on the detector.

zodi_readout(zodi, optical_path, prng_key, *, ...)

Process a zodi source through the provided optical path.

Package Contents#

coronagraphoto.load_scene_from_exovista(fits_file, planet_indices=None, only_earths=False, zodi_surface_brightness_mag=22.0, load_disk=True)[source]#

Load a full skyscapes.Scene from an ExoVista FITS file.

Delegates system loading to skyscapes.from_exovista() and adds a default AYOZodi background using the host star’s wavelength grid.

The earlier required_planets parameter was removed: variadic planet tuples make the “pad to fixed shape” semantics unnecessary, and the underlying skyscapes.from_exovista no longer accepts it.

Args:

fits_file: Path to the ExoVista FITS file. planet_indices: Planet indices to load (0-based). None = all. only_earths: If True and planet_indices is None, auto-filter

Earths.

zodi_surface_brightness_mag: V-band surface brightness for the

default zodi background. Default 22.0 (AYO standard).

load_disk: If False, skip the disk extension and set

System.disk to None. Use this when the coronagraph has no PSF datacube (the disk pipeline requires one).

Returns:

skyscapes.Scene with the loaded system and a default zodi background.

Parameters:
Return type:

skyscapes.Scene

coronagraphoto.disk_rate(disk, optical_path, *, start_time_jd, wavelength_nm, bin_width_nm, telescope_pa_deg, star, incl_deg, pa_deg)[source]#

Generate the disk count rate on the detector.

Disks return CONTRAST (dimensionless flux ratio relative to the host star); we multiply by star.spec_flux_density here to convert to photon flux density per pixel before resampling and PSF convolution.

incl_deg / pa_deg are the disk’s intrinsic orientation in the sky frame; telescope_pa_deg is the telescope’s roll. The disk is rendered at its intrinsic geometry and the coronagraph’s extended_scene rotates it by -telescope_pa_deg into the detector frame while rendering.

Raises:
ValueError: from the coronagraph if it cannot render an extended

scene (e.g. a table-backed coronagraph built without a PSF datacube).

coronagraphoto.disk_readout(disk, optical_path, prng_key, *, start_time_jd, exposure_time_s, wavelength_nm, bin_width_nm, telescope_pa_deg, star, incl_deg, pa_deg)[source]#

Process a disk through the provided optical path.

incl_deg / pa_deg are the disk’s intrinsic sky-frame orientation; system_readout pulls them from scene.system.midplane_inc_deg / midplane_pa_deg so every disk component in the System renders at the same midplane.

coronagraphoto.planet_rate(planet, optical_path, *, start_time_jd, wavelength_nm, bin_width_nm, telescope_pa_deg, star, trig_solver)[source]#

Generate the per-batch planet count rate on the detector.

Operates on a single skyscapes.scene.Planet (which internally batches K planets sharing the same atmosphere class). The Python loop over a heterogeneous System.planets tuple lives in system_readout(); this function stays inside the per-Planet-type JIT cache boundary.

coronagraphoto.planet_readout(planet, optical_path, prng_key, *, start_time_jd, exposure_time_s, wavelength_nm, bin_width_nm, telescope_pa_deg, star, trig_solver)[source]#

Process a per-batch Planet through the optical path.

coronagraphoto.speckle_rate(speckle, optical_path, *, start_time_jd, wavelength_nm, bin_width_nm, star)[source]#

Generate the speckle count rate on the detector.

The speckle field returns a CONTRAST delta (fraction of host-star flux per pixel) – the stochastic wavefront-error residual that sits on top of the deterministic stellar_intens floor already applied in star_rate(). We multiply by the host-star flux to convert to a photon rate, then resample to the detector. Structurally this mirrors star_rate(), not disk_rate(): the field is already a post-coronagraph focal-plane map, so there is no PSF convolution.

Evolution is driven by time, not a PRNG key: the elapsed seconds are (start_time_jd - speckle.epoch_jd), so the rate is deterministic and differentiable and temporal correlation survives across a roll sequence. The realization’s randomness is fixed at construction.

The speckle map is taken on the plane declared by its own speckle.pixel_scale_lod and resampled to the detector grid directly, so it need not share a plate scale with the coronagraph.

coronagraphoto.speckle_readout(speckle, optical_path, prng_key, *, start_time_jd, exposure_time_s, wavelength_nm, bin_width_nm, star)[source]#

Process a speckle field through the provided optical path.

The PRNG key is used only for the photon Poisson draw; the speckle realization itself is deterministic in time (see speckle_rate()).

coronagraphoto.star_rate(star, optical_path, *, start_time_jd, wavelength_nm, bin_width_nm)[source]#

Generate the star count rate on the detector.

coronagraphoto.star_readout(star, optical_path, prng_key, *, start_time_jd, exposure_time_s, wavelength_nm, bin_width_nm)[source]#

Process a star through the provided optical path.

coronagraphoto.system_rate(scene, optical_path, *, start_time_jd, wavelength_nm, bin_width_nm, telescope_pa_deg, ecliptic_lat_deg, solar_lon_deg)[source]#

Sum of deterministic per-source count rates for a Scene.

The differentiable companion to system_readout(). Returns the total rate map (electrons/s/pixel, no Poisson noise, no QE multiply) summing star, every planet, the optional disk, the optional zodi, and the optional speckle field on optical_path. Use this for likelihood evaluation, retrievals, or any inference loop that needs gradients through the full forward model.

coronagraphoto.system_readout(scene, optical_path, prng_key, *, start_time_jd, exposure_time_s, wavelength_nm, bin_width_nm, telescope_pa_deg, ecliptic_lat_deg, solar_lon_deg)[source]#

Simulate a full Scene through the optical path.

Sums per-source detector readouts. Each source consumes its own independent PRNG subkey (see jax.random best practices). The optional speckle field on optical_path is the last source and consumes the final subkey, so scenes run without one are unaffected.

The Python loop over scene.system.planets is intentionally unjitted – it orchestrates JIT-cached per-Planet-type kernels. The expensive math is inside each planet_readout call, not the loop.

coronagraphoto.zodi_rate(zodi, optical_path, *, start_time_jd, wavelength_nm, bin_width_nm, ecliptic_lat_deg, solar_lon_deg)[source]#

Generate the zodi count rate on the detector.

Treats zodi as a spatially uniform surface-brightness source. The coronagraph’s sky transmission map sets the per-pixel attenuation; no PSF convolution is needed (a flat field convolved with any normalised PSF returns itself).

Parameters:

zodi (skyscapes.background.Zodi)

coronagraphoto.zodi_readout(zodi, optical_path, prng_key, *, start_time_jd, exposure_time_s, wavelength_nm, bin_width_nm, ecliptic_lat_deg, solar_lon_deg)[source]#

Process a zodi source through the provided optical path.

Parameters:

zodi (skyscapes.background.Zodi)