jnormcorre package

Subpackages

Submodules

jnormcorre.motion_correction module

class jnormcorre.motion_correction.FrameCorrector(template: ndarray, max_shifts: Tuple[int, int], strides: Tuple[int, int], overlaps: Tuple[int, int], max_deviation_rigid: int, min_mov: float | None = None, batching: int = 100)[source]

Bases: object

__init__(template: ndarray, max_shifts: Tuple[int, int], strides: Tuple[int, int], overlaps: Tuple[int, int], max_deviation_rigid: int, min_mov: float | None = None, batching: int = 100) None[source]

Standalone motion correction object, allowing users to register frames via rigid or piecewise rigid motion correction to a given template.

Parameters:
  • template (np.ndarray) – Shape (d1, d2) where d1 and d2 are the FOV dimensions

  • max_shifts (Tuple) – Two integers, specifying maximum shift in the two FOV dimensions (height, width)

  • strides (Tuple) – Two integers, used to specify patch dimensions for pwrigid registration

  • overlaps (Tuple) – Overlap b/w patches. strides[i] + overlaps[i] are the patch size dimensions.

  • max_deviation_rigid (int) – Specifies max number of pixels a patch can deviate from the rigid shifts.

  • min_mov (float) – The minimum value of the movie, if known.

  • batching (int) – Specifies how many frames we register at a time. Toggle this to avoid GPU OOM errors.

property batching
property pwrigid_function: Callable[[ndarray], Array | ndarray | bool_ | number | bool | int | float | complex]

The piecewise rigid registration function of this frame correction object

register_frames(frames: ndarray, pw_rigid: bool = False) ndarray[source]

Function to register a set of frames to this object’s template.

Parameters:
  • frames (np.ndarray) – dimensions (T, d1, d2), where T is the number of frames and d1, d2 are FOV dims

  • pw_rigid (bool) – Indicates whether we do piecewise rigid or rigid registration. Defaults to rigid.

Returns:

corrected_frames (np.array) – Dimensions (T, d1, d2). The registered output from the input (frames)

register_frames_and_transfer(target_frames: ndarray, reference_frames: ndarray, pw_rigid: bool = False) ndarray[source]

Function to register a set of frames to this object’s template.

Parameters:
  • target_frames (np.ndarray) – dimensions (T, d1, d2), where T is the number of frames and d1, d2 are FOV dims. Frames we want to ultimately register

  • reference_frames (np.ndarray) – dimensions (T, d1, d2), where T is number of frames and d1, d2 are FOV dims. We align these frames to the template to estimate shifts, and then apply these shifts to target_frames

  • pw_rigid (bool) – Indicates whether we do piecewise rigid or rigid registration. Defaults to False (rigid).

Returns:

corrected_frames (np.array) – Dimensions (T, d1, d2). The registered output from the input (frames)

property rigid_function: Callable[[ndarray], Array | ndarray | bool_ | number | bool | int | float | complex]

The rigid registration function of this frame correction object

property template: ndarray
class jnormcorre.motion_correction.MotionCorrect(lazy_dataset: lazy_data_loader, max_shifts: tuple[int, int] = (6, 6), frames_per_split: int = 1000, num_splits_to_process_rig: int | None = None, niter_rig: int = 1, pw_rigid: bool = False, strides: tuple[int, int] = (96, 96), overlaps: tuple[int, int] = (32, 32), max_deviation_rigid: int = 3, num_splits_to_process_els: int | None = None, niter_els: int = 1, min_mov: float | None = None, upsample_factor_grid: int = 4, bigtiff: bool = False)[source]

Bases: object

class implementing motion correction operations

__init__(lazy_dataset: lazy_data_loader, max_shifts: tuple[int, int] = (6, 6), frames_per_split: int = 1000, num_splits_to_process_rig: int | None = None, niter_rig: int = 1, pw_rigid: bool = False, strides: tuple[int, int] = (96, 96), overlaps: tuple[int, int] = (32, 32), max_deviation_rigid: int = 3, num_splits_to_process_els: int | None = None, niter_els: int = 1, min_mov: float | None = None, upsample_factor_grid: int = 4, bigtiff: bool = False) None[source]

Constructor class for motion correction operations

Parameters:
  • lazy_dataset (lazy_data_loader) – Lazy data loader for loading frames of the data

  • max_shifts (Tuple) – Two integers, specifying maximum shift in the two FOV dimensions (height, width)

  • frames_per_split (int) – Integer larger than 1. Number of frames we use to generate each local template.

  • num_splits_to_process_rig (int) – Number of splits we process per iteration of rigid motion correction

  • niter_rig (int) – Number of iterations of rigid motion correction

  • pw_rigid (bool) – Whether we additionally run piecewise rigid registration

  • strides (Tuple) – Two integers, used to specify patch dimensions for pwrigid registration

  • overlaps (Tuple) – Overlap b/w patches. strides[i] + overlaps[i] are the patch size dimensions.

  • max_deviation_rigid (int) – Specifies max number of pixels a patch can deviate from the rigid shifts.

  • num_splits_to_process_els (int) – Number of splits we process per iteration of pwrigid motion correction

  • niter_els – Number of iterations of piecewise rigid registration

  • min_mov (float) –

  • bigtiff (bool) – Indicates whether or not movie is saved as a bigtiff or regular tiff

motion_correct(template: ndarray | None = None, save_movie: bool | None = False) tuple[FrameCorrector, str][source]

General driver function which performs motion correction

Parameters:
  • template (ndarray) – Template provided by user for motion correction default

  • save_movie (bool) – Flag for saving motion corrected file(s) as memory mapped file(s)

Returns:
  • frame_corrector_obj (jnormcorre.motion_correction.frame_corrector) – Object for applying frame correction with final inferred template

  • target_file (str) – path to saved file

jnormcorre.motion_correction.apply_shifts_dft_fast_1(src_freq_in: Array | ndarray | bool_ | number | bool | int | float | complex, shift_a: Array | ndarray | bool_ | number | bool | int | float | complex, shift_b: Array | ndarray | bool_ | number | bool | int | float | complex, diffphase: Array | ndarray | bool_ | number | bool | int | float | complex) Array | ndarray | bool_ | number | bool | int | float | complex[source]

use the inverse dft to apply shifts :param src_freq_in: :type src_freq_in: jnp.array :param shift_a: :type shift_a: jnp.array :param shift_b: :type shift_b: jnp.array :param diffphase: :type diffphase: jnp.array

Returns:

Shifted image

jnormcorre.motion_correction.bin_median(mat: ndarray, window: int = 10, exclude_nans: bool = True)[source]

Compute median of 3D array in along axis 0 by binning values

Parameters:
  • mat (np.ndarray) –

  • window (int) –

Returns:

img (np.ndarray)

jnormcorre.motion_correction.calculate_splits(T: int, frames_per_split: int) list[source]

Function used to build a computation work plan for motion correction (decide which frames to run per split, etc.)

jnormcorre.motion_correction.ceil_max(a, b)[source]
jnormcorre.motion_correction.crop_image(img, x, y, length_1, length_2)[source]
jnormcorre.motion_correction.crop_image_vmap(img, x, y, length_1, length_2)

Vectorized version of crop_image. Takes similar arguments as crop_image but with additional array axes over which crop_image is mapped.

jnormcorre.motion_correction.fill_maxh(img, k)[source]
jnormcorre.motion_correction.fill_maxw(img, k)[source]
jnormcorre.motion_correction.fill_minh(img, k)[source]
jnormcorre.motion_correction.fill_minw(img, k)[source]
jnormcorre.motion_correction.first_value(a, b)[source]
jnormcorre.motion_correction.floor_min(a, b)[source]
jnormcorre.motion_correction.generate_template_chunk(arr: ndarray, batch_size: int = 250000) ndarray[source]
jnormcorre.motion_correction.get_freq_comps_jax(src_image: Array | ndarray | bool_ | number | bool | int | float | complex, target_image: Array | ndarray | bool_ | number | bool | int | float | complex) tuple[Array | ndarray | bool_ | number | bool | int | float | complex][source]

Routine to compute frequency components of two images

jnormcorre.motion_correction.get_indices(img, overlaps_0, overlaps_1, strides_0, strides_1)[source]
jnormcorre.motion_correction.get_patch_start_and_end_coords(x, y, strides_0, strides_1, overlaps_0, overlaps_1)[source]

When we run piecewise motion correction, we partition the FOV into overlapping patches, perform rigid alignment between these patches and the corresponding patches of the template. Piecewise rigid MC returns the rigid shifts for each of these patches. This function is a convenient way to access the top left and bottom right coordinates for each patch.

Parameters:
  • x (int) – First python dimension of FOV

  • y (int) – Second python dimension of FOV

  • strides_0 (int) – Patch stride in first dimension

  • strides_1 (int) – Patch stride in second dimension

  • overlaps_0 (int) – Patch overlaps in first dimension

  • overlaps_1 (int) – Patch overlaps in second dimension

Returns:
  • start_points (np.ndarray) – Shape (num_patches, 2). Each row is the top left coordinates of each patch.

  • end_points (np.ndarray) – Shape (num_patches, 2). Each row is the bottom right coordinates of a single patch.

Intended Usage of outputs:

img[start_points[0]:end_points[0], start_points[1]:end_points[1]] will give you the patch used here.

jnormcorre.motion_correction.get_patches_jax(img, overlaps_0, overlaps_1, strides_0, strides_1)[source]
jnormcorre.motion_correction.get_xy_grid(img, overlaps_0, overlaps_1, strides_0, strides_1)[source]
jnormcorre.motion_correction.load_split_heuristic(d1, d2, T)[source]

Heuristic for determining how many frames to register at a time (to avoid GPU OOM)

jnormcorre.motion_correction.nan_processing(arr: Array | ndarray | bool_ | number | bool | int | float | complex) Array | ndarray | bool_ | number | bool | int | float | complex[source]
jnormcorre.motion_correction.register_frames_to_template_pwrigid(img: Array | ndarray | bool_ | number | bool | int | float | complex, template: Array | ndarray | bool_ | number | bool | int | float | complex, strides_0: int, strides_1: int, overlaps_0: int, overlaps_1: int, max_shifts: Array | ndarray | bool_ | number | bool | int | float | complex, upsample_factor_fft: int, max_deviation_rigid: int, add_to_movie: Array | ndarray | bool_ | number | bool | int | float | complex) tuple[Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex]

Perform piecewise rigid motion correction iteration by (1) dividing the FOV in patches (2) motion correcting each patch separately (3) upsampling the motion correction vector field (4) stitching back together the corrected subpatches

Parameters:
  • img (np.ndarray) – Shape (T, x, y) Frames to register to template. T is number of frames, x and y spatial dims

  • template (np.ndarray) – Shape (x, y). The reference image

  • strides_0 (int) – The strides of the patches in which the FOV is subdivided along dimension 0.

  • strides_1 (int) – The strides of the patches in which the FOV is subdivided along dimension 1.

  • overlaps_0 (int) – Amount of pixel overlap between patches along dimension 0

  • overlaps_1 (int) – Amount of pixel overlap between patches along dimension 1

  • max_shifts (tuple) – Max shifts in x and y

  • upsample_factor_fft (int) – The resolution of fractional shifts

  • max_deviation_rigid (int) – Maximum deviation in shifts of each patch from the rigid shift (should not be large)

  • add_to_movie (np.array) – Constant offset to add to movie before registration to avoid negative values.

Returns:
  • new_img (jnp.array) – Shape (T, x, y), motion corrected version of img.

  • total_shifts (jnp.array) – Shape (T, num_patches, 2). For the i-th frame, we apply shifts to “num_patches” different patches. See below for more info.

In general, the coordinates of the k-th patch corresponding to total_shifts[i, k, :] are given this code

from jnormcorre import motion_correction
start, end = motion_correction.get_patch_start_and_end_coords(x, y, strides_0, strides_1,
            overlaps_0, overlaps_1)

They can be used as follows:

img_i[start[0]:end[0], start[1]:end[1]]
jnormcorre.motion_correction.register_frames_to_template_rigid(img: Array | ndarray | bool_ | number | bool | int | float | complex, template: Array | ndarray | bool_ | number | bool | int | float | complex, max_shifts: Array | ndarray | bool_ | number | bool | int | float | complex, add_to_movie: Array | ndarray | bool_ | number | bool | int | float | complex) tuple[Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex]

Performs rigid registration of a series of frames to a single template.

Parameters:
  • img (jnp.array) – Shape (T, x, y), frames we want to register. T is number of frames, x and y are spatial dims

  • template (jnp.array) – Shape (x, y). Template image

  • max_shifts (jnp.array) – Has 2 integers specifying max shift in both FOV dimensions

  • add_to_movie (jnp.array) – Scalar value in jnp.array for adding to each frame.

Returns:
  • aligned (jnp.array) – Shape (T, x, y). Aligned version of “img” to template.

  • shifts (jnp.array) – Shape (T, 2). Row i describes dimension 1 and dimension 2 shifts applied to ith frame

jnormcorre.motion_correction.register_to_template_and_transfer_pwrigid(img: Array | ndarray | bool_ | number | bool | int | float | complex, img_filtered: Array | ndarray | bool_ | number | bool | int | float | complex, template: Array | ndarray | bool_ | number | bool | int | float | complex, strides_0: int, strides_1: int, overlaps_0: int, overlaps_1: int, max_shifts: Array | ndarray | bool_ | number | bool | int | float | complex, upsample_factor_fft: int, max_deviation_rigid: int, add_to_movie: Array | ndarray | bool_ | number | bool | int | float | complex) tuple[Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex]

Here we estimate the piecewise rigid shifts needed to optimally align the image stack imgs_filtered to template. Then we apply those estimated shifts to the image stack`img`. This is useful in the context of 1p imaging, where we might want to estimated shifts from a high-pass filtered movie, or in dual color imaging, where we might want to use a brighter channel to estimate shifts that we apply to a dimmer one.

Perform piecewise rigid motion correction on 1p data by (1) dividing the FOV in patches (2) motion correcting each patch separately (3) upsampling the motion correction vector field (4) stiching back together the corrected subpatches

Parameters:
  • img (np.ndarray) – Shape (T, x, y) Frames to register to template. T is number of frames, x and y spatial dims

  • imgs_filtered (np.ndarray). Shape (T, x, y) –

  • template (np.ndarray) – Shape (x, y). The reference image

  • strides_0 (int) – The strides of the patches in which the FOV is subdivided along dimension 0.

  • strides_1 (int) – The strides of the patches in which the FOV is subdivided along dimension 1.

  • overlaps_0 (int) – Amount of pixel overlap between patches along dimension 0

  • overlaps_1 (int) – Amount of pixel overlap between patches along dimension 1

  • max_shifts (tuple) – Max shifts in x and y

  • upsample_factor_fft (int) – The resolution of fractional shifts

  • max_deviation_rigid (int) – Maximum deviation in shifts of each patch from the rigid shift (should not be large)

  • add_to_movie (np.array) – Constant offset to add to movie before registration to avoid negative values.

Returns:
  • new_img (jnp.array) – Shape (T, x, y), motion corrected version of img.

  • total_shifts (jnp.array) – Shape (T, num_patches, 2). For the i-th frame, we apply shifts to “num_patches” different patches. See below for more info.

In general, the coordinates of the k-th patch corresponding to total_shifts[i, k, :] are given this code

from jnormcorre import motion_correction
start, end = motion_correction.get_patch_start_and_end_coords(x, y, strides_0, strides_1,
            overlaps_0, overlaps_1)

They can be used as follows:

img_i[start[0]:end[0], start[1]:end[1]]
jnormcorre.motion_correction.register_to_template_and_transfer_rigid(img: Array | ndarray | bool_ | number | bool | int | float | complex, img_filtered: Array | ndarray | bool_ | number | bool | int | float | complex, template: Array | ndarray | bool_ | number | bool | int | float | complex, max_shifts: tuple[int, int], add_to_movie: Array | ndarray | bool_ | number | bool | int | float | complex) tuple[Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex]

This routine estimates the shifts needed to align one image stack (img_filtered) to a template, and applies those estimated shifts to img. This can be very useful for dual color imaging, 1p calcium imaging, and many other use cases.

Parameters:
  • img (np.array) – Shape (T, x, y), frames we want to register. T is number of frames, x and y are spatial dims

  • img_filtered (np.array). Shape (T, x, y) –

  • template (np.array) – Shape (x, y). Template image

  • max_shifts (np.array) – Has 2 integers specifying max shift in both FOV dimensions

  • add_to_movie (np.array) – Scalar value in jnp.array for adding to each frame.

Returns:
  • aligned (jnp.array) – Shape (T, x, y). Aligned version of “img” to template.

  • shifts (jnp.array) – Shape (T, 2). Row i describes dimension 1 and dimension 2 shifts applied to ith frame.

jnormcorre.motion_correction.register_translation_jax_full(src_image: Array | ndarray | bool_ | number | bool | int | float | complex, target_image: Array | ndarray | bool_ | number | bool | int | float | complex, upsample_factor: int, shifts_lb: Array | ndarray | bool_ | number | bool | int | float | complex, shifts_ub: Array | ndarray | bool_ | number | bool | int | float | complex, max_shifts=(10, 10)) tuple[Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex][source]

Estimates piecewise rigid shifts which would align target_image TO the src_image. Negate these to get shifts going from src_image to target. :param src_image: :type src_image: np.ndarray :param target_image: :type target_image: np.ndarray :param upsample_factor: :type upsample_factor: int :param shifts_lb: :type shifts_lb: ArrayLike :param shifts_ub: :type shifts_ub: ArrayLike

Returns:
  • shifts (np.ndarray). Shift vector (in pixels) – src_image.

  • src_freq (jnp.array)

  • phasediff (jnp.array) – zero if images are non-negative).

jnormcorre.motion_correction.register_translation_jax_simple(src_image: Array | ndarray | bool_ | number | bool | int | float | complex, target_image: Array | ndarray | bool_ | number | bool | int | float | complex, upsample_factor: int, max_shifts: tuple[int, int] = (10, 10)) tuple[Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex][source]
Finds optimal rigid shifts to register target_image (template) with src_image (input image). Negate

these shifts to get the optimal rigid transformation from src_image to template.

Parameters:
  • src_image (np.ndarray) –

  • target_image (np.ndarray) –

  • upsample_factor (int) –

  • max_shifts (tuple) –

Returns:
  • shifts (ndarray). Shift vector (in pixels) – src_image. Axis ordering is consistent with numpy (e.g. Z, Y, X)

  • sfr_freq (jnp.array)

  • phasediff (jnp.array) – zero if images are non-negative).

jnormcorre.motion_correction.regular_collate(batch)[source]
jnormcorre.motion_correction.return_identity(a, b)[source]
jnormcorre.motion_correction.return_identity_mins(in_var, k)[source]
jnormcorre.motion_correction.second_value(a, b)[source]
jnormcorre.motion_correction.subtract_values(a, b)[source]
jnormcorre.motion_correction.threshold_dim1(img: Array | ndarray | bool_ | number | bool | int | float | complex, ind: int) Array | ndarray | bool_ | number | bool | int | float | complex[source]
jnormcorre.motion_correction.threshold_dim2(img: Array | ndarray | bool_ | number | bool | int | float | complex, ind: int) Array | ndarray | bool_ | number | bool | int | float | complex[source]
jnormcorre.motion_correction.threshold_shifts_0_else(new_cross_corr, shift_ub, shift_lb)[source]
jnormcorre.motion_correction.threshold_shifts_0_if(new_cross_corr, shift_ub, shift_lb)[source]
jnormcorre.motion_correction.threshold_shifts_1_else(new_cross_corr, shift_ub, shift_lb)[source]
jnormcorre.motion_correction.threshold_shifts_1_if(new_cross_corr, shift_ub, shift_lb)[source]
class jnormcorre.motion_correction.tile_and_correct_dataset(param_list)[source]

Bases: object

Basic dataloading class for loading chunks of data. Written like this so that code can support prefetching from disk

__init__(param_list)[source]
jnormcorre.motion_correction.update_src_freq_flag(src_freq, flag)[source]
jnormcorre.motion_correction.update_src_freq_identity(src_freq)[source]
jnormcorre.motion_correction.update_src_freq_jax(src_freq)[source]
jnormcorre.motion_correction.verify_strides_and_overlaps(dim: int, stride: int, overlap: int) None[source]
jnormcorre.motion_correction.vmap_register_translation(src_image: Array | ndarray | bool_ | number | bool | int | float | complex, target_image: Array | ndarray | bool_ | number | bool | int | float | complex, upsample_factor: int, shifts_lb: Array | ndarray | bool_ | number | bool | int | float | complex, shifts_ub: Array | ndarray | bool_ | number | bool | int | float | complex, max_shifts=(10, 10)) tuple[Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex, Array | ndarray | bool_ | number | bool | int | float | complex]

Vectorized version of register_translation_jax_full. Takes similar arguments as register_translation_jax_full but with additional array axes over which register_translation_jax_full is mapped.

Original documentation:

Estimates piecewise rigid shifts which would align target_image TO the src_image. Negate these to get shifts going from src_image to target. Args:

src_image (np.ndarray). Input data/images. target_image (np.ndarray). Template. Must have same shape as src_image. upsample_factor (int). Upsampling which occurs to estimate the shifts shifts_lb (ArrayLike). Lower bound on the shifts which can be applied at each subpatch. shifts_ub (ArrayLike). Upper bound on the shifts which can be applied at each subpatch.

Returns:
shifts (np.ndarray). Shift vector (in pixels) required to register target_image with

src_image.

src_freq (jnp.array). Frequency domain representation of input image data. phasediff (jnp.array). Float value, global phase difference between the two images (should be

zero if images are non-negative).

jnormcorre.onephotonmethods module

jnormcorre.simulation module

class jnormcorre.simulation.SimData(frames, X, Y, n_blobs=10, noise_amplitude=1.0, blob_amplitude=1.0, max_drift=0.5, max_jitter=2.0, background_noise=1.0, shot_noise=0.1)[source]

Bases: object

__init__(frames, X, Y, n_blobs=10, noise_amplitude=1.0, blob_amplitude=1.0, max_drift=0.5, max_jitter=2.0, background_noise=1.0, shot_noise=0.1)[source]

Initialize the SimData object with the given parameters.

Parameters: - frames: Number of frames in the simulation.

NOTE: this parameter should NOT reflect the number of frames in a realistic dataset. Instead what we’d like to do here is take a base template image, apply some shifts, and quantify how well the alignment happens. Think of “frames” as the number of test cases. It probably should not be larger than, say, 100 frames

  • X, Y: Dimensions of the images.

  • n_blobs: Number of gaussian blobs (peaks or valleys) to add to the base image.

  • noise_amplitude: Amplitude of the noise in the base image.

  • blob_amplitude: Amplitude of the gaussian blobs.

  • max_drift: Maximum drift value or tuple for quadratic drift.

  • max_jitter: Maximum random jitter in the image per frame.

  • background_noise: Constant background noise level.

  • shot_noise: Frame-by-frame noise level.

calculate_padding()[source]

Calculate the necessary padding around the image to ensure that the entire field of view stays within the base image, even with maximum drift and jitter.

Returns: - Amount of padding needed.

generate_base_image(padding=0)[source]

Generate a base image consisting of a noise floor and random gaussian blobs.

Parameters: - padding: Additional space around the image to account for movement.

Returns: - Padded base image with noise and gaussian blobs.

generate_gaussian_blob(x, y, x0, y0, sigma, amplitude)[source]

Generate a 2D Gaussian blob at a given location with specified parameters.

Parameters: - x, y: Meshgrid for the image dimensions. - x0, y0: Center of the gaussian blob. - sigma: Standard deviation of the gaussian blob. - amplitude: Amplitude of the gaussian blob (can be negative for valleys).

Returns: - 2D numpy array representing the gaussian blob.

plot_overview(savefig=None)[source]

Plot an overview of the simulated data, showing the first, middle, and last frames, as well as the shifts in the x and y directions over time.

save(path)[source]

Save the simulated data to a .tiff file.

Parameters: - path: Destination path for the .tiff file.

simulate()[source]

Simulate a sequence of images with drift and jitter.

Returns: - Simulated data and list of shifts for each frame.

Module contents