Skip to content

Shack-Hartmann Wavefront Sensor

queue_listerner instance-attribute

queue_listerner = setup_logging()

logger instance-attribute

logger = getLogger()

external_logger_flag instance-attribute

external_logger_flag = False

tag instance-attribute

tag = 'shackHartmann'

plate_scale instance-attribute

plate_scale = plate_scale

fieldOfView instance-attribute

fieldOfView = fieldOfView

guardPx instance-attribute

guardPx = guardPx

fft_fieldOfView_oversampling instance-attribute

fft_fieldOfView_oversampling = fft_fieldOfView_oversampling

nSubap instance-attribute

nSubap = nSubap

lightRatio instance-attribute

lightRatio = lightRatio

threshold_convolution instance-attribute

threshold_convolution = threshold_convolution

use_brightest instance-attribute

use_brightest = use_brightest

unit_in_rad instance-attribute

unit_in_rad = unit_in_rad

device instance-attribute

device = device('cuda' if is_available() else 'cpu')

subaperture_size instance-attribute

subaperture_size = D / nSubap

npix_lenslet instance-attribute

npix_lenslet = int(
    round(
        (fieldOfView + fft_fieldOfView_oversampling)
        / plate_scale
    )
)

npix_subap instance-attribute

npix_subap = int(round(fieldOfView / plate_scale))

npix_phase instance-attribute

npix_phase = resolution // nSubap

pupil_interpolation_mask instance-attribute

pupil_interpolation_mask = numpy()

camera_size instance-attribute

camera_size = nSubap * npix_lenslet + (nSubap + 1) * guardPx

camera_params instance-attribute

camera_params = dict()

cam instance-attribute

cam = Detector(
    nPix=camera_size,
    samplingTime=samplingTime,
    fullWellCapacity=camera_params["fullWellCapacity"],
    nBits=camera_params["nBits"],
    quantumEfficiency=camera_params["quantumEfficiency"],
    shotNoise=camera_params["shotNoise"],
    darkCurrent=camera_params["darkCurrent"],
    readoutNoise=camera_params["readoutNoise"],
    gain=camera_params["gain"],
    quantization_conversion=camera_params[
        "quantization_conversion"
    ],
    sensorType=camera_params["sensorType"],
    darkCalibration=camera_params["darkCalibration"],
    noiseFlag=noiseFlag,
    logger=logger,
    **camera_kwargs,
)

X_coord_map instance-attribute

X_coord_map = T

Y_coord_map instance-attribute

Y_coord_map = T

is_LGS instance-attribute

is_LGS = True

cube instance-attribute

cube = zeros([nSubap ** 2, npix_lenslet, npix_lenslet])

cube_flux instance-attribute

cube_flux = zeros(
    [nSubap**2, npix_lenslet, npix_lenslet], dtype=complex
)

phasor instance-attribute

phasor = exp(
    -(1j * pi * (npix_lenslet + 1) / npix_lenslet)
    * (xx + yy)
)

phasor_tiled instance-attribute

phasor_tiled = moveaxis(
    tile(phasor[:, :, None], nSubap**2), 2, 0
)

phasor_expanded instance-attribute

phasor_expanded = exp(
    -(1j * pi * (npix_lenslet + 1) / npix_lenslet)
    * (xx + yy)
)

phasor_expanded_tiled instance-attribute

phasor_expanded_tiled = moveaxis(
    tile(phasor_expanded[:, :, None], nSubap**2), 2, 0
)

norm_flux_map instance-attribute

norm_flux_map = (
    lightRatio
    * pupil_reflectivity_resized
    * samplingTime
    * (D / (nSubap * npix_lenslet)) ** 2
)

current_nPhoton instance-attribute

current_nPhoton = nPhoton

index_x instance-attribute

index_x = asarray(index_x)

index_y instance-attribute

index_y = asarray(index_y)

photon_per_subaperture_2D instance-attribute

photon_per_subaperture_2D = reshape(
    photon_per_subaperture, [nSubap, nSubap]
)

valid_subapertures instance-attribute

valid_subapertures = astype(bool)

valid_subapertures_1D instance-attribute

valid_subapertures_1D = reshape(
    valid_subapertures, [nSubap**2]
)

valid_slopes_maps instance-attribute

valid_slopes_maps = concatenate(
    (valid_subapertures, valid_subapertures)
)

nValidSubaperture instance-attribute

nValidSubaperture = int(sum(valid_subapertures))

nSignal instance-attribute

nSignal = 2 * nValidSubaperture

__init__

__init__(
    nSubap: float,
    telescope,
    src,
    lightRatio: float,
    plate_scale: float,
    fieldOfView: float,
    guardPx: int,
    fft_fieldOfView_oversampling: float = 0,
    use_brightest: int = 50,
    threshold_convolution: float = 0.05,
    unit_in_rad=False,
    noiseFlag: bool = False,
    logger=None,
    **kwargs,
)

Initialize a Shack-Hartmann Wavefront Sensor (WFS).

Parameters:

Name Type Description Default
nSubap float

Number of subapertures across the pupil diameter.

required
telescope Telescope

Telescope object to which the WFS is attached.

required
src Source

Source object (NGS or LGS).

required
lightRatio float

Threshold ratio to select valid subapertures based on flux.

required
plate_scale float

Plate scale of the WFS in [arcsec/px].

required
fieldOfView float

Field of view of the WFS in [arcsec].

required
guardPx int

Number of pixels between subapertures.

required
fft_fieldOfView_oversampling float

Extra FoV in [arcsec] that is taken for the FFT computation, in order to reduce wrapping effects.

0
use_brightest int

Picks the n brightest pixels as threshold for center-of-gravity spot detection.

50
threshold_convolution float

Cut-off threshold for Gaussian convolution.

0.05
unit_in_rad bool

Return slopes in radians if True, pixels otherwise.

False
noiseFlag bool

If True, the detector includes noise using the kwargs params/default config. By default, False.

False
logger Logger

Logger for WFS diagnostics.

None
**kwargs dict

Additional keyword arguments.

fullWellCapacity : int, optional Detector parameter. Full Well Capacity of pixels [e-]. Default, 60ke- nBits : int, optional Detector parameter. Bit depth for quantization. Default is 12, shall be >= 8 quantumEfficiency : float, optional Detector parameter. Quantum efficiency (0-1). Default is 0.64. shotNoise : bool, optional Detector parameter. Shot noise flag. Default 1. darkCurrent : float, optional Detector parameter. Dark current [e-]. Default 250e-/px/s. readoutNoise : float, optional Detector parameter. Readout noise [e-]. Default 60e-. gain : float, optional Detector parameter. Gain of the detector. Default is 1. quantization_conversion : float, optional. Detector parameter. Conversion gain to discretize the measurement [e-/px]. Default 0 --> adjust by well capacity. sensorType : str, optional Detector parameter. Sensor type ('CCD', 'CMOS', 'EMCCD'). Default is 'CCD'. darkCalibration : int, optional Detector parameter. Number of frames to calibrate the dark. Default 20. randomState : int, optional Detector parameter. Seed for the random number generator. Default is None. integrationTime : float, optional Detector parameter. Integration time for the detector [s]. Default is the sampling time.

{}

initialize_wfs

initialize_wfs(telescope, src)

Initialize the Shack-Hartmann WFS by measuring reference slopes and determining slope units.

Parameters:

Name Type Description Default
telescope Telescope

The telescope object providing phase and pupil info.

required
src Source

Source object for flux and wavelength reference.

required

Returns:

Type Description
None

centroid

centroid(image, use_brightest=50)

Compute center of gravity for subaperture spots.

Parameters:

Name Type Description Default
image ndarray

Subaperture image cube.

required
use_brightest float

Minimum intensity to include in centroid.

50

Returns:

Type Description
ndarray

X and Y centroids per subaperture.

initialize_flux

initialize_flux(src, norm_flux_map)

Initialize per-subaperture flux distribution.

Parameters:

Name Type Description Default
src Source

Light source object.

required
norm_flux_map ndarray

Normalized flux across telescope pupil.

required

Returns:

Type Description
None

get_psf

get_psf(phase, fwhm)

Get the electromagnetic field per subaperture based on input phase.

Parameters:

Name Type Description Default
phase ndarray

Wavefront phase in radians.

required
fwhm float

Full width at half maximum for the PSF in [px].

required

Returns:

Type Description
ndarray

Complex field per subaperture.

create_full_frame

create_full_frame(subaps)

Combine subaperture images into full detector frame.

Parameters:

Name Type Description Default
subaps ndarray

Subaperture spot images.

required

Returns:

Type Description
ndarray

Reconstructed full sensor image.

get_subaps

get_subaps(noisy_frame)

Extract individual lenslet spot images from full detector image.

Parameters:

Name Type Description Default
noisy_frame ndarray

2D detector frame.

required

Returns:

Type Description
ndarray

Subaperture cubes [nSubaps, width, height].

get_convolution_spot

get_convolution_spot(src)

Compute LGS spot convolution kernel based on sodium profile.

Parameters:

Name Type Description Default
src Source

Laser guide star source object.

required

Returns:

Type Description
None

wfs_integrate

wfs_integrate(ideal_frame, subaps, nPhoton)

Integrate the full detector image and compute valid slopes.

Parameters:

Name Type Description Default
ideal_frame ndarray

Full-frame ideal image.

required
subaps ndarray

Spot images per subaperture.

required

Returns:

Type Description
tuple

Slopes 1D, slopes 2D, and final noisy image.

wfs_measure

wfs_measure(phase_in, src)

Measure slopes from a wavefront phase using the SH-WFS.

Parameters:

Name Type Description Default
phase_in ndarray

Phase map input [radians].

required
src Source

Source object.

required

Returns:

Type Description
tuple

Slopes 1D, slopes 2D, and detector image.

print_properties

print_properties()

Print Shack-Hartmann configuration and diagnostic values.

Returns:

Type Description
None

setup_logging

setup_logging(logging_level=logging.WARNING)

__del__

__del__()