iactrace.telescope

The Telescope class and helper modules for building optical systems.

Telescope Class

class iactrace.telescope.Telescope[source]

Bases: Module

IACT telescope optical system as an Equinox Module.

The Telescope owns the full optical path including the camera frame (position and orientation of the detector plane). After ray tracing, rays are transformed into the camera frame so that the Camera class operates purely in its local coordinate system.

Optical elements (mirrors and lenses) are stored separately for clarity, but can be accessed together via the optical_groups property for unified ray tracing through mixed reflective/refractive systems.

__init__(mirror_groups, obstruction_groups=None, name='telescope', lens_groups=None, camera_position=None, camera_rotation=None)[source]

Initialize Telescope.

Args:

mirror_groups: List of Mirror groups (reflective elements) obstruction_groups: List of Obstruction groups name: Telescope name lens_groups: List of Lens groups (refractive elements) camera_position: Camera origin in world coordinates (3,).

Defaults to [0, 0, 0].

camera_rotation: Camera orientation as Euler angles in degrees (3,).

Defaults to [0, 0, 0].

mirror_groups = <dataclasses._MISSING_TYPE object>
lens_groups = <dataclasses._MISSING_TYPE object>
obstruction_groups = <dataclasses._MISSING_TYPE object>
name = <dataclasses._MISSING_TYPE object>
camera_position = <dataclasses._MISSING_TYPE object>
camera_rotation = <dataclasses._MISSING_TYPE object>
property optical_groups

Return all optical groups (mirrors + lenses) combined.

render(sources, values, source_type='point')[source]

Describe a render through the optics; do not execute yet.

Returns a LazyRayBundle packaging this telescope’s optics and camera frame with the given sources. Downstream camera methods (Camera.image(), Camera.response_matrix(), Camera.collect()) consume it directly: image and response_matrix fold per primary element so the full ray buffer is never materialised; collect materialises (per-ray output cannot be folded).

Args:

sources: Source positions (N, 3) or directions (N, 3). values: Source strengths (N,). For 'parallel' these are

irradiances on the aperture; for 'point' they are radiant intensities, and the irradiance each primary sample sees is value / d^2 for that sample’s distance d to the source.

source_type: 'point' or 'parallel'.

trace(ray_origins, ray_directions, values, record_trajectory=False)[source]

Trace rays from arbitrary origins through the full optical system.

Args:

ray_origins: Ray starting positions (N, 3) ray_directions: Ray directions (N, 3), should be normalized values: Ray intensities (N,) record_trajectory: When True, also record the per-stage ray path for

diagnostics / 3D visualization (see iactrace.viz.show_telescope()). Off by default and free when off – nothing extra is computed. Mirrors the trace_chain() option on the chain side.

Returns:

A TraceResult, as every tracer returns. Its rays are in the camera’s local coordinate system; pass them to camera.collect() or camera.image() for detection:

rays = telescope.trace(origins, directions, values).rays
rays, trajectory = telescope.trace(..., record_trajectory=True)

trajectory is None unless record_trajectory was set, in which case the Trajectory holds the source point, each optical stage’s landing point, and finally the converging leg’s landing on the camera reference plane – (n_stages + 2, N, 3), so the beam is seen coming to a focus. rays stops on the last optic (the sensor intersection happens downstream in Camera); the trajectory adds that last leg for display.

The trajectory is in the world frame (the frame iactrace.viz.show_telescope() draws the optics in), not the camera frame rays is reframed into.

classmethod from_yaml(filename, n_samples=100, *, key)[source]

Load a telescope from a standalone telescope YAML file.

The telescope file describes only the optical system and the camera frame. Load the camera separately via Camera.from_yaml().

Args:

filename: Path to telescope YAML file. n_samples: Number of Monte Carlo samples per mirror element. key: JAX random key for sampling and roughness.

to_yaml(filename, precision=6, overwrite=True)[source]

Save the telescope configuration to a standalone YAML file.

Args:

filename: Output file path. precision: Number of decimal places for float values. overwrite: If True, overwrite existing file.

Returns:

Path to the saved file.

to_dict()[source]

Convert telescope to a telescope-only configuration dictionary.

focus(delta_z)[source]

Adjust camera position along the camera’s local z-axis (optical axis).

set_camera_position(position)[source]

Set the camera position in world coordinates.

set_camera_rotation(rotation)[source]

Set the camera rotation (Euler angles in degrees).

stage(idx)[source]

Return the OpticalElementGroup at optical_stage == idx.

stage_indices()[source]

Sorted list of all optical stages present.

stages_of_kind(kind)[source]

Sorted stages whose group has the given kind (‘mirror’, ‘lens’, ‘slab’).

property n_stages
property n_mirror_elements
property n_lens_elements
set_positions(stage, positions)[source]
set_rotations(stage, rotations)[source]
apply_displacement(stage, sigma_z, key)[source]
apply_misalignment(stage, sigma_h, sigma_v, key)[source]
apply_roughness(stage, sigma)[source]
set_curvatures(stage, curvatures)[source]
set_conics(stage, conics)[source]
set_aspherics(stage, aspherics)[source]
scale_curvatures(stage, factor)[source]
offset_curvatures(stage, offset)[source]
apply_conic_error(stage, sigma, key)[source]
apply_aspheric_error(stage, sigmas, key)[source]
apply_zernike_error(stage, sigmas, key)[source]
apply_astigmatism(stage, sigma, key)[source]
apply_coma(stage, sigma, key)[source]
apply_trefoil(stage, sigma, key)[source]
resample(stage, key)[source]
set_reflectivity(stage, reflectivity)[source]
scale_reflectivity(stage, factor)[source]
set_transmittance(stage, transmittance)[source]
scale_transmittance(stage, factor)[source]
set_refractive_index(stage, n_inside)[source]
set_thickness(stage, thickness)[source]
set_focal_lengths(stage, focal_lengths, n_outside=1.0)[source]
apply_focal_error(stage, sigma, key, relative=False, n_outside=1.0)[source]
add_obstruction(obstruction)[source]
remove_obstruction(group_idx)[source]
clear_obstructions()[source]
get_obstruction_count()[source]
get_info()[source]

Optical Element Composition

Mirrors and lenses are both represented as OpticalElementGroup instances composed from a surface, an aperture, an interaction, and an optional BSDF (see iactrace.core). The helper submodules below provide builders that assemble the right combination for common optical elements.

Mirror builders

iactrace.telescope.mirrors.mirror_group(*, positions, rotations, curvatures, conics, aspherics, offsets, aperture, reflectivity=1.0, sample_key, coating=None, bsdf=None, optical_stage=0, n_samples=100)[source]

Canonical reflective OpticalElementGroup builder.

Takes pre-shaped per-element arrays plus a pre-built aperture and an optional BSDF instance, and assembles the surface + interaction + group wiring.

Args:

positions: Per-element vertex positions, shape (N, 3). rotations: Per-element Euler angles in degrees, shape (N, 3). curvatures: Per-element curvatures 1/R, shape (N,). conics: Per-element Schwarzschild conic constants, shape (N,). aspherics: Per-element even aspheric coefficients [A4, A6, ...],

shape (N, K); column i multiplies r^(2i + 4).

offsets: Per-element surface decentering, shape (N, 2). Use

jnp.zeros((N, 2)) for a centred disk.

aperture: Pre-built aperture. reflectivity: Per-element reflectivity in [0, 1], shape (N,). sample_key: JAX PRNG key used for aperture sampling and BSDF. bsdf: Optional BSDF instance. None leaves the element

perfectly specular (the OpticalElementGroup constructor fills in a zero-scale GaussianBSDF).

optical_stage: Stage index within the Telescope; each group in a

telescope must have a unique stage.

n_samples: Monte Carlo samples per element per render.

Returns:

A ready-to-use OpticalElementGroup.

iactrace.telescope.mirrors.spherical(*, position, focal_length, radius, rotation=(0.0, 0.0, 0.0), inner_radius=0.0, reflectivity=1.0, coating=None, bsdf_scale=0.0, optical_stage=0, n_samples=100, key)[source]

Build a spherical mirror as a single-element group.

Uses c = 1 / (2 * focal_length) with conic = 0. Set inner_radius > 0 for an annular mirror.

Args:

position: Mirror vertex in world coordinates, shape (3,). focal_length: Paraxial focal length in metres (positive = concave). radius: Outer disk radius in metres. rotation: Euler angles in degrees. Defaults to no rotation. inner_radius: Inner hole radius in metres. Zero for a solid disk. reflectivity: Per-element reflectivity in [0, 1]. bsdf_scale: Gaussian roughness sigma in arcseconds (0 disables). optical_stage: Stage index within the Telescope. n_samples: Monte Carlo samples per render call. key: JAX PRNG key.

iactrace.telescope.mirrors.parabolic(*, position, focal_length, radius, rotation=(0.0, 0.0, 0.0), inner_radius=0.0, reflectivity=1.0, coating=None, bsdf_scale=0.0, optical_stage=0, n_samples=100, key)[source]

Build a parabolic mirror as a single-element group.

Uses c = 1 / (2 * focal_length) and conic = -1, matching the reference configs/BASIC/Cassegrain_telescope.yaml primary (focal_length=0.4 -> curvature=1.25).

Args: see spherical().

iactrace.telescope.mirrors.aspheric(*, position, curvature, radius, rotation=(0.0, 0.0, 0.0), conic=0.0, aspheric_coeffs=None, inner_radius=0.0, reflectivity=1.0, coating=None, bsdf_scale=0.0, optical_stage=0, n_samples=100, key)[source]

Build a general aspheric mirror as a single-element group.

Fully explicit version of spherical() / parabolic(): you supply the curvature, conic constant, and optional even aspheric coefficients. Use this for hyperbolic / elliptic / higher-order aspheric mirrors.

Args:

position: Mirror vertex in world coordinates, shape (3,). curvature: Paraxial curvature 1/R in m^-1. radius: Outer disk radius in metres. rotation: Euler angles in degrees. Defaults to no rotation. conic: Schwarzschild conic constant. 0 spherical, -1

parabolic, -1 < k < 0 prolate ellipsoid, k < -1 hyperboloid.

aspheric_coeffs: Even aspheric coefficients [A4, A6, ...],

i.e. aspheric_coeffs[i] multiplies r^(2i + 4). The polynomial starts at r^4.

inner_radius, reflectivity, bsdf_scale, optical_stage, n_samples, key:

see spherical().

iactrace.telescope.mirrors.disk_array(*, positions, rotations, curvatures, radii, conics=None, aspheric_coeffs=None, inner_radii=None, reflectivities=None, coating=None, bsdf_scales=None, offsets=None, optical_stage=0, n_samples=100, key)[source]

Build a batched N-element disk-aperture mirror group.

Use this for segmented primary mirrors. Per-element arrays must all match length N. Scalar defaults fill in where an argument is omitted. For anything beyond disk apertures / Gaussian BSDF, drop down to mirror_group().

Args:

positions: Per-element vertex positions, shape (N, 3). rotations: Per-element Euler angles in degrees, shape (N, 3). curvatures: Per-element curvatures 1/R, shape (N,). radii: Outer disk radii, shape (N,). conics: Per-element conic constants, shape (N,). Defaults to

zeros (spherical).

aspheric_coeffs: Per-element aspheric coefficients, shape (N, K).

None disables aspherics.

inner_radii: Per-element central hole radii, shape (N,).

Defaults to zeros.

reflectivities: Per-element reflectivities, shape (N,). Defaults

to ones.

bsdf_scales: Per-element Gaussian BSDF roughness in arcseconds,

shape (N,). Zero (the default) disables the BSDF.

offsets: Per-element surface decentering, shape (N, 2). Defaults

to zeros.

optical_stage: Stage index shared by all elements in this group. n_samples: Monte Carlo samples per element per render. key: JAX PRNG key for aperture sampling and BSDF.

Lens builders

iactrace.telescope.lenses.refractive_group(*, positions, rotations, curvatures, conics, aspherics, offsets, aperture, n_inside, transmittance=1.0, sample_key, coating=None, optical_stage=0, n_samples=100)[source]

Canonical builder for refractive OpticalElementGroup instances.

Assembles an AsphericSurfaceGroup + RefractInteraction + group wiring from pre-shaped arrays. Use this for curved single-surface refracting lenses with any aperture type. Both the user-facing sugar helpers and the YAML adapter delegate to this function.

Args:

positions: Per-element vertex positions, shape (N, 3). rotations: Per-element Euler angles in degrees, shape (N, 3). curvatures: Per-element curvatures 1/R, shape (N,). conics: Per-element conic constants, shape (N,). aspherics: Per-element even aspheric coefficients [A4, A6, ...],

shape (N, K); column i multiplies r^(2i + 4).

offsets: Per-element surface decentering, shape (N, 2). aperture: Pre-built aperture sized to N. n_inside: Per-element refractive index, shape (N,). The ambient

index on the incident side is not stored: the render loop reads it dynamically from each ray’s current medium (see RefractInteraction).

transmittance: Per-element bulk transmittance in [0, 1], shape

(N,).

sample_key: JAX PRNG key for aperture sampling. optical_stage: Stage index within the Telescope. n_samples: Monte Carlo samples per element per render.

iactrace.telescope.lenses.slab_group(*, positions, rotations, aperture, n_inside, thickness, transmittance=1.0, sample_key, coating=None, optical_stage=0, n_samples=100)[source]

Canonical builder for parallel-sided slab (window) groups.

The surface is always zero curvature, conic, and aspheric, a slab is by definition flat, so no surface parameters are exposed. Both the user-facing plano_slab() helper and the YAML adapter delegate to this function.

Args:

positions: Per-element front-surface positions, shape (N, 3). rotations: Per-element Euler angles in degrees, shape (N, 3). aperture: Pre-built aperture sized to N. n_inside: Per-element slab refractive index, shape (N,). The

ambient index is not stored: the render loop reads it dynamically from each ray’s current medium (see SlabInteraction).

thickness: Per-element slab thickness in metres, shape (N,). transmittance: Per-element bulk transmittance in [0, 1], shape

(N,).

sample_key: JAX PRNG key for aperture sampling. optical_stage: Stage index within the Telescope. n_samples: Monte Carlo samples per element per render.

iactrace.telescope.lenses.aspheric_lens(*, position, curvature, radius, rotation=(0.0, 0.0, 0.0), conic=0.0, aspheric_coeffs=None, n_inside=1.5, transmittance=1.0, coating=None, optical_stage=0, n_samples=100, key)[source]

Build a general aspheric-disk refracting lens as a single-element group.

Fully explicit version of thin(): you supply the raw curvature, conic constant and optional aspheric coefficients. Use this for precisely-specified lens prescriptions.

Args:

position: Vertex position in world coordinates, shape (3,). curvature: Surface curvature 1/R in m^-1. radius: Outer disk radius in metres. rotation: Euler angles in degrees. Defaults to no rotation. conic: Schwarzschild conic constant. aspheric_coeffs: Even aspheric coefficients [A4, A6, ...],

i.e. aspheric_coeffs[i] multiplies r^(2i + 4).

n_inside, transmittance, optical_stage, n_samples, key:

see thin().

iactrace.telescope.lenses.plano_slab(*, position, radius, thickness, rotation=(0.0, 0.0, 0.0), n_inside=1.5, transmittance=1.0, coating=None, optical_stage=0, n_samples=100, key)[source]

Build a flat parallel-sided window as a single-element group.

The surface is zero-curvature (flat) and rays pass through a SlabInteraction that handles entry refraction, propagation through the slab, and exit refraction. Useful for entrance windows and filters.

Args:

position: Vertex position of the front surface, shape (3,). radius: Outer disk radius in metres. thickness: Slab thickness in metres (along the optical axis). rotation: Euler angles in degrees. Defaults to no rotation. n_inside: Refractive index of the slab material. Defaults to 1.5. transmittance: Bulk transmittance in [0, 1]. Defaults to 1.0. optical_stage: Stage index within the Telescope. n_samples: Monte Carlo samples per element per render. key: JAX PRNG key for aperture sampling.

Obstruction builders

class iactrace.telescope.obstructions.ObstructionGroup[source]

Bases: Module

Base class for grouped obstructions.

Subclasses supply their intersection kernel and stacked parameters via _primitive(); the two traversal strategies are shared from here.

abstractmethod __len__()[source]

Number of obstruction primitives in this group.

intersect(ray_origin, ray_direction)[source]

Returns min t across all primitives in group.

intersect_batch(origins, directions)[source]

Nearest hit distance per ray, for (n_rays, 3) rays.

Same answer as vmap(self.intersect), but chooses how to walk the primitives based on how many rays there are.

__init__()
class iactrace.telescope.obstructions.CylinderGroup[source]

Bases: ObstructionGroup

Group of cylinders for efficient batched intersection.

__init__(p1, p2, r)[source]
p1 = <dataclasses._MISSING_TYPE object>
p2 = <dataclasses._MISSING_TYPE object>
r = <dataclasses._MISSING_TYPE object>
class iactrace.telescope.obstructions.OpenCylinderGroup[source]

Bases: ObstructionGroup

Group of open cylinders (no end caps) for efficient batched intersection.

An open cylinder is a finite cylindrical surface without circular caps at the ends. Useful for modeling tubes, pipes, or hollow cylindrical structures where rays can pass through the ends.

__init__(p1, p2, r)[source]
p1 = <dataclasses._MISSING_TYPE object>
p2 = <dataclasses._MISSING_TYPE object>
r = <dataclasses._MISSING_TYPE object>
class iactrace.telescope.obstructions.BoxGroup[source]

Bases: ObstructionGroup

Group of axis-aligned boxes for efficient batched intersection.

__init__(p1, p2)[source]
p1 = <dataclasses._MISSING_TYPE object>
p2 = <dataclasses._MISSING_TYPE object>
class iactrace.telescope.obstructions.SphereGroup[source]

Bases: ObstructionGroup

Group of spheres for efficient batched intersection.

__init__(centers, radii)[source]
centers = <dataclasses._MISSING_TYPE object>
radii = <dataclasses._MISSING_TYPE object>
class iactrace.telescope.obstructions.OrientedBoxGroup[source]

Bases: ObstructionGroup

Group of oriented boxes for efficient batched intersection.

__init__(centers, half_extents, rotations)[source]
centers = <dataclasses._MISSING_TYPE object>
half_extents = <dataclasses._MISSING_TYPE object>
rotations = <dataclasses._MISSING_TYPE object>
class iactrace.telescope.obstructions.TriangleGroup[source]

Bases: ObstructionGroup

Group of triangles for efficient batched intersection.

__init__(v0, v1, v2)[source]
v0 = <dataclasses._MISSING_TYPE object>
v1 = <dataclasses._MISSING_TYPE object>
v2 = <dataclasses._MISSING_TYPE object>
iactrace.telescope.obstructions.cylinder(*, p1, p2, r)[source]

Build a single closed cylinder as a CylinderGroup of size one.

Args:

p1: One endpoint of the cylinder axis, shape (3,). p2: The other endpoint, shape (3,). r: Cylinder radius in metres.

iactrace.telescope.obstructions.open_cylinder(*, p1, p2, r)[source]

Build a single open cylinder (no end caps) as a size-one group.

Args:

p1: One endpoint of the cylinder axis, shape (3,). p2: The other endpoint, shape (3,). r: Cylinder radius in metres.

iactrace.telescope.obstructions.box(*, p1, p2)[source]

Build a single axis-aligned box as a BoxGroup of size one.

Args:

p1: One corner of the box, shape (3,). p2: The diagonally opposite corner, shape (3,).

iactrace.telescope.obstructions.sphere(*, center, r)[source]

Build a single sphere as a SphereGroup of size one.

Args:

center: Sphere centre, shape (3,). r: Sphere radius in metres.

Operations

Functional operations for modifying telescope configurations (e.g., for calibration, error injection, optimization). All operations return new telescope instances.

iactrace.telescope.operations.set_positions(telescope, stage, positions)[source]

Set element positions for the group at stage.

iactrace.telescope.operations.set_rotations(telescope, stage, rotations)[source]

Set element rotations (Euler XYZ degrees) for the group at stage.

iactrace.telescope.operations.apply_displacement(telescope, stage, sigma_z, key)[source]

Apply random Gaussian z-displacement to elements in the group at stage.

iactrace.telescope.operations.apply_misalignment(telescope, stage, sigma_h, sigma_v, key)[source]

Apply random Gaussian tip/tilt to element orientations.

sigma_h / sigma_v are in arcseconds.

iactrace.telescope.operations.apply_roughness(telescope, stage, sigma)[source]

Apply Gaussian BSDF roughness (arcseconds RMS) to the group at stage.

iactrace.telescope.operations.set_curvatures(telescope, stage, curvatures)[source]

Set surface curvatures (1/R) for the group at stage.

iactrace.telescope.operations.set_conics(telescope, stage, conics)[source]

Set surface conic constants for the group at stage.

iactrace.telescope.operations.set_aspherics(telescope, stage, aspherics)[source]

Set surface aspheric coefficients for the group at stage.

iactrace.telescope.operations.scale_curvatures(telescope, stage, factor)[source]

Multiply curvatures by factor (scalar or per-element).

iactrace.telescope.operations.offset_curvatures(telescope, stage, offset)[source]

Add offset to curvatures (scalar or per-element).

iactrace.telescope.operations.apply_conic_error(telescope, stage, sigma, key)[source]

Apply random Gaussian error to conic constants.

iactrace.telescope.operations.apply_aspheric_error(telescope, stage, sigmas, key)[source]

Apply random Gaussian errors to aspheric coefficients.

iactrace.telescope.operations.apply_zernike_error(telescope, stage, sigmas, key)[source]

Add random Gaussian Zernike figure error to the surface at stage.

Draws independent per-element coefficients for each Noll mode and composes them onto the stage’s surface: a bare aspheric mirror becomes an asphere + Zernike SumSurfaceGroup, while a surface that already carries a Zernike term has the new draw added to it (matching apply_conic_error() and apply_aspheric_error(), which accumulate noise rather than replace).

The Noll terms are RMS-normalized, so sigmas are RMS surface-error sigmas in metres. sigmas[m] scales Noll index m + 1: index 0 is piston (removed by the surface re-zero), 1/2 tilt, 3 defocus, 4/5 astigmatism, 6/7 coma, 8/9 trefoil, 10 spherical. Only the first 11 Noll terms are available; a longer sigmas raises.

Args:

stage: Optical stage to perturb. sigmas: Per-Noll-mode RMS sigmas in metres, shape (J,) with

J <= 11.

key: JAX PRNG key for the coefficient draw.

iactrace.telescope.operations.apply_astigmatism(telescope, stage, sigma, key)[source]

Add random astigmatism (Noll Z5/Z6) of RMS sigma metres per component.

iactrace.telescope.operations.apply_coma(telescope, stage, sigma, key)[source]

Add random coma (Noll Z7/Z8) of RMS sigma metres per component.

iactrace.telescope.operations.apply_trefoil(telescope, stage, sigma, key)[source]

Add random trefoil (Noll Z9/Z10) of RMS sigma metres per component.

iactrace.telescope.operations.resample(telescope, stage, key)[source]

Refresh the Monte-Carlo sampling key on the group at stage.

iactrace.telescope.operations.set_reflectivity(telescope, stage, reflectivity)[source]

Set per-element mirror reflectivity. Mirror stages only.

iactrace.telescope.operations.scale_reflectivity(telescope, stage, factor)[source]

Multiply mirror reflectivity by factor. Mirror stages only.

Scales the bulk multiplier reflectivity_scalar; the coating on the interaction is left untouched.

iactrace.telescope.operations.set_transmittance(telescope, stage, transmittance)[source]

Set per-element bulk transmittance. Lens or slab stages only.

Writes the bulk multiplier transmittance_scalar; the coating on the interaction is left untouched.

iactrace.telescope.operations.scale_transmittance(telescope, stage, factor)[source]

Multiply bulk transmittance by factor. Lens or slab stages only.

Scales the bulk multiplier transmittance_scalar; the coating on the interaction is left untouched.

iactrace.telescope.operations.set_refractive_index(telescope, stage, n_inside)[source]

Set per-element refractive index. Lens or slab stages only.

iactrace.telescope.operations.set_thickness(telescope, stage, thickness)[source]

Set slab thickness in metres. Slab stages only.

iactrace.telescope.operations.set_focal_lengths(telescope, stage, focal_lengths, n_outside=1.0)[source]

Set focal lengths via curvature.

Mirror stages: c = 1 / (2 f). Lens stages (single refracting surface): c = 1 / ((n_inside - n_outside) f), where n_outside is a design-time ambient-index assumption (default 1.0), not a value stored on the lens.

iactrace.telescope.operations.apply_focal_error(telescope, stage, sigma, key, relative=False, n_outside=1.0)[source]

Perturb focal lengths by Gaussian noise; update curvatures accordingly.

Kind-aware: uses the mirror or single-refracting-lens formula. Slabs are rejected. n_outside is the design-time ambient index for the lens formula (default 1.0); see set_focal_lengths().

iactrace.telescope.operations.add_obstruction(telescope, obstruction)[source]

Append an obstruction group.

iactrace.telescope.operations.remove_obstruction(telescope, group_idx)[source]

Remove the obstruction group at group_idx.

iactrace.telescope.operations.clear_obstructions(telescope)[source]

Drop all obstruction groups.

iactrace.telescope.operations.get_obstruction_count(telescope)[source]

Total number of obstruction elements across all groups.

iactrace.telescope.operations.get_info(telescope)[source]

Summary dict of telescope configuration.