def __init__(self, array: np.ndarray, wavelength: float, pixel_size: Tuple[float, float, float] = None, photons_flux: float = None): super().__init__(wavelength, array.shape, pixel_size, photons_flux) self.wavefront = Wavefront(array, wavelength=wavelength)
def _calculateWavefront(self) -> None: """Calculate a wavefront with gaussian intensity, then modulate the wavefront using a speckle pattern.""" sigma_x = self.width_dist[1] sigma_y = self.width_dist[0] nx = self.shape[-1] ny = self.shape[-2] x = np.arange(-nx // 2, nx // 2) * self.pixel_size[1] y = np.arange(-ny // 2, ny // 2) * self.pixel_size[0] xx, yy = np.meshgrid(x, y) intensity = utils.generalized2dGaussian(np.stack( (xx.flatten(), yy.flatten()), axis=1), amplitude=1, center_x=self.center_dist[0], center_y=self.center_dist[1], sigma_x=sigma_x, sigma_y=sigma_y, theta=self.theta, offset=0) amplitude = np.sqrt(intensity).astype('complex64').reshape(ny, nx) speckle = utils.getSpeckle((ny, nx), self.speckle_window_npix) wavefront_array = np.fft.fftshift(amplitude * speckle) scaling_factor = np.sqrt(self.n_photons / np.sum(np.abs(wavefront_array)**2)) #self.wavefront = self.wavefront.update(array=scaling_factor * wavefront_array) self.wavefront = Wavefront(scaling_factor * wavefront_array, wavelength=self.wavelength, pixel_size=self.pixel_size) self._propagateWavefront()
def _calculateWavefront(self) -> None: """Calculate the probe wavefront with constant phase and with a gaussian intensity. Propagate the wavefront.""" sigma_x = self.width_dist[1] sigma_y = self.width_dist[0] nx = self.shape[-1] ny = self.shape[-2] x = np.arange(-nx // 2, nx // 2) * self.pixel_size[1] y = np.arange(-ny // 2, ny // 2) * self.pixel_size[0] xx, yy = np.meshgrid(x, y) xdata = np.stack((xx.flatten(), yy.flatten()), axis=1) intensity = utils.generalized2dGaussian(xdata, amplitude=1, center_x=self.center_dist[1], center_y=self.center_dist[0], sigma_x=sigma_x, sigma_y=sigma_y, theta=self.theta, offset=0).reshape((ny, nx)) scaling_factor = np.sqrt(self.n_photons / intensity.sum()) wavefront_array = scaling_factor * np.sqrt(intensity).astype( 'complex64') wavefront_array = np.fft.fftshift(np.reshape(wavefront_array, (ny, nx))) #self.wavefront = self.wavefront.update(array=wavefront_array) self.wavefront = Wavefront(wavefront_array, wavelength=self.wavelength, pixel_size=self.pixel_size) self._propagateWavefront()
def _calculateWavefront(self) -> None: """Calculating the airy pattern then propagating it by `defocus_dist`.""" if self.width_dist[0] > 0: logger.warning( "Warning: if width at the focus is supplied, " + "any supplied focal_length and aperture radius are ignored.") self.aperture_radius = None self.focal_length = None # Assuming resolution equal to pixel pitch and focal length of 10.0 m. focal_length = 10.0 focus_radius = self.width_dist[0] / 2 # note that jinc(1,1) = 1.22 * np.pi aperture_radius = (self.wavelength * 1.22 * np.pi * focal_length / 2 / np.pi / focus_radius) else: if None in [self.aperture_radius, self.focal_length]: e = ValueError( 'Either focus_radius_npix or BOTH aperture_radius and focal_length must be supplied.' ) logger.error(e) raise e aperture_radius = self.aperture_radius focal_length = self.focal_length npix_oversampled = max( self.oversampling_npix, self.shape[-1]) if self.oversampling else self.shape[0] pixel_pitch_aperture = self.wavelength * focal_length / ( npix_oversampled * self.pixel_size[0]) x = np.arange(-npix_oversampled // 2, npix_oversampled // 2) * pixel_pitch_aperture r = np.sqrt(x**2 + x[:, np.newaxis]**2).astype('float32') circ_wavefront = np.zeros(r.shape) circ_wavefront[r < aperture_radius] = 1.0 circ_wavefront[r == aperture_radius] = 0.5 probe_vals = np.fft.fftshift( np.fft.fft2(np.fft.fftshift(circ_wavefront), norm='ortho')) n1 = npix_oversampled // 2 - self.shape[0] // 2 n2 = npix_oversampled // 2 + self.shape[1] // 2 scaling_factor = np.sqrt(self.n_photons / np.sum(np.abs(probe_vals)**2)) wavefront_array = probe_vals[n1:n2, n1:n2].astype( 'complex64') * scaling_factor wavefront_array = np.fft.fftshift(wavefront_array) #self.wavefront = self.wavefront.update(array=wavefront_array) self.wavefront = Wavefront(wavefront_array, wavelength=self.wavelength, pixel_size=self.pixel_size) self._propagateWavefront()
def __init__(self, wavefront_array: np.ndarray, wavelength: float, pixel_size: Tuple[float, float], defocus_dist: float = 0) -> None: super().__init__(wavelength=wavelength, pixel_size=pixel_size, shape=wavefront_array.shape, n_photons=np.sum(np.abs(wavefront_array)**2), defocus_dist=defocus_dist) #self.wavefront = self.wavefront.update(array = wavefront_array.copy()) self.wavefront = Wavefront(wavefront_array, wavelength=self.wavefront.wavelength, pixel_size=self.wavefront.pixel_size) self._calculateWavefront()
def __init__(self, wavelength: float, pixel_size: Tuple[float, ...], shape: Tuple[int, ...], n_photons: float, defocus_dist: float = 0, center_dist: Tuple[float, float] = (0, 0), width_dist: Tuple[float, float] = (0, 0), center_npix: Tuple[int, int] = None, width_npix: Tuple[int, int] = None, check_propagation_with_gaussian_fit: bool = False, apodize: bool = False) -> None: self.wavelength = wavelength self.shape = shape self.pixel_size = pixel_size self.n_photons = n_photons self.defocus_dist = defocus_dist self.center_dist = center_dist self.width_dist = width_dist self.apodize = apodize if center_npix is not None: logger.warning( 'If center_npix is supplied, then any supplied center_dist is ignored.' ) self.center_npix = center_npix self.center_dist = np.array(center_npix) * np.array( self.pixel_size) if width_npix is not None: logger.warning( 'If width_npix is supplied, then any supplied width_dist is ignored.' ) self.width_npix = width_npix self.width_dist = np.array(width_npix) * np.array(self.pixel_size) #wavefront_array = np.zeros((npix, npix), dtype='complex64') #self.wavefront = propagators.Wavefront(wavefront_array, self.wavefront = Wavefront(np.zeros(shape), wavelength=wavelength, pixel_size=pixel_size) self.photons_flux = n_photons / (shape[-1] * shape[-2]) self.check_propagation_with_gaussian_fit = check_propagation_with_gaussian_fit
def _calculateWavefront(self) -> None: """Calculates and propagates the exit wave from a rectangular aperture of the supplied dimensions.""" nx = self.shape[-1] ny = self.shape[-2] x = np.arange(-nx // 2, nx // 2) * self.pixel_size[1] y = np.arange(-ny // 2, ny // 2)[:, np.newaxis] * self.pixel_size[0] xarr = np.where( np.abs(x - self.center_dist[1]) <= self.width_dist[1] / 2, 1, 0) yarr = np.where( np.abs(y - self.center_dist[0]) <= self.width_dist[0] / 2, 1, 0) array = np.fft.fftshift((xarr * yarr).astype('complex64')) scaling_factor = np.sqrt(self.n_photons / (np.abs(array)**2).sum()) #self.wavefront = self.wavefront.update(array = scaling_factor * array) self.wavefront = Wavefront(scaling_factor * array, wavelength=self.wavelength, pixel_size=self.pixel_size) self._propagateWavefront()
def _calculateWavefront(self): """Calculates and propagates the exit wave from a circular aperture of the supplied radius. """ a = self.width_dist[1] / 2 b = self.width_dist[0] / 2 nx = self.shape[1] ny = self.shape[0] x = np.arange(-nx // 2, nx // 2) * self.pixel_size[1] y = np.arange(-ny // 2, ny // 2)[:, np.newaxis] * self.pixel_size[0] lhs = b**2 * (x - self.center_dist[1])**2 + a**2 * ( y - self.center_dist[0])**2 rhs = a**2 * b**2 wavefront_array = np.zeros(lhs.shape, dtype='complex64') wavefront_array[lhs <= rhs] = 1.0 wavefront_array = np.fft.fftshift(wavefront_array) scaling_factor = np.sqrt(self.n_photons / (np.abs(wavefront_array)**2).sum()) #self.wavefront = self.wavefront.update(array=scaling_factor * wavefront_array) self.wavefront = Wavefront(scaling_factor * wavefront_array, wavelength=self.wavelength, pixel_size=self.pixel_size) self._propagateWavefront()