def undulator(self, method, npixels_x, npixels_y, pixelsize_x, pixelsize_y, wavelength, sigma, m, m_x, m_y, propagation_distance, radius, show, image_source, apply_lens): wavefront = Wavefront2D.initialize_wavefront_from_range( x_min=-pixelsize_x * npixels_x / 2, x_max=pixelsize_x * npixels_x / 2, y_min=-pixelsize_y * npixels_y / 2, y_max=pixelsize_y * npixels_y / 2, number_of_points=(npixels_x, npixels_y), wavelength=wavelength) wavefront.set_spherical_wave(radius=radius) if image_source == False: X = wavefront.get_mesh_x() Y = wavefront.get_mesh_y() wavefront.rescale_amplitude( numpy.exp(-(X**2 + Y**2) / (2 * sigma**2)) ) # applichiamo intensita' con profilo gaussiano print("Input intensity: ", wavefront.get_intensity().sum()) if apply_lens == True: wavefront.apply_ideal_lens(focal_length_x=propagation_distance, focal_length_y=propagation_distance) print("Intensity after lens: ", wavefront.get_intensity().sum()) if method == 'fft': output_wf = propagate_2D_fresnel( wavefront, propagation_distance=propagation_distance) elif method == 'rescaling': output_wf = propagator2d_fourier_rescaling( wavefront, propagation_distance=propagation_distance, m=m) elif method == 'rescaling_xy': output_wf = propagator2d_fourier_rescaling_xy( wavefront, propagation_distance=propagation_distance, m_x=m_x, m_y=m_y) plot_undulator(output_wf, method=method, show=show) horizontal_profile_wf = line_image(wavefront.get_intensity(), horizontal_or_vertical='H') vertical_profile_wf = line_image(wavefront.get_intensity(), horizontal_or_vertical='V') horizontal_phase_profile_wf = line_image(wavefront.get_phase(), horizontal_or_vertical='H') if image_source == True: return wavefront.get_coordinate_x( ), horizontal_profile_wf, horizontal_phase_profile_wf
def propagation_to_image(wf,do_plot=do_plot,plot_title="Before lens",method='fft', propagation_distance=30.0,defocus_factor=1.0,propagation_steps=1,show=1): method_label = "fresnel (%s)"%method print("\n# ") print("# near field fresnel (%s) diffraction and focusing "%(method_label)) print("# ") # \ | / # * | | | * # / | \ # <------- d ---------------><--------- d -------> # d is propagation_distance print("Incident intensity: ",wf.get_intensity().sum()) # propagation downstream the lens to image plane for i in range(propagation_steps): if propagation_steps > 1: print(">>> Propagating step %d of %d; propagation_distance=%g m"%(i+1,propagation_steps, propagation_distance*defocus_factor/propagation_steps)) if method == 'fft': wf = propagate_2D_fresnel(wf, propagation_distance*defocus_factor/propagation_steps) elif method == 'convolution': wf = propagate_2D_fresnel_convolution(wf, propagation_distance*defocus_factor/propagation_steps) elif method == 'srw': wf = propagate_2D_fresnel_srw(wf, propagation_distance*defocus_factor/propagation_steps) elif method == 'fraunhofer': wf = propagate_2D_fraunhofer(wf, propagation_distance*defocus_factor/propagation_steps) else: raise Exception("Not implemented method: %s"%method) horizontal_profile = wf.get_intensity()[:,wf.size()[1]/2] horizontal_profile /= horizontal_profile.max() print("FWHM of the horizontal profile: %g um"%(1e6*line_fwhm(horizontal_profile)*wf.delta()[0])) vertical_profile = wf.get_intensity()[wf.size()[0]/2,:] vertical_profile /= vertical_profile.max() print("FWHM of the vertical profile: %g um"%(1e6*line_fwhm(vertical_profile)*wf.delta()[1])) if do_plot: from srxraylib.plot.gol import plot,plot_image plot_image(wf.get_intensity(),1e6*wf.get_coordinate_x(),1e6*wf.get_coordinate_y(), xtitle="X um",ytitle="Y um",title='intensity (%s)'%method,show=0) # plot_image(wf.get_amplitude(),wf.get_coordinate_x(),wf.get_coordinate_y(),title='amplitude (%s)'%method,show=0) plot_image(wf.get_phase(),1e6*wf.get_coordinate_x(),1e6*wf.get_coordinate_y(), xtitle="X um",ytitle="Y um",title='phase (%s)'%method,show=0) plot(wf.get_coordinate_x(),horizontal_profile, wf.get_coordinate_y(),vertical_profile, legend=['Horizontal profile','Vertical profile'],title="%s %s"%(plot_title,method),show=show) print("Output intensity: ",wf.get_intensity().sum()) return wf,wf.get_coordinate_x(),horizontal_profile
def propagation_to_image(wf,do_plot=do_plot,plot_title="Before lens",method='fft', propagation_distance=30.0,defocus_factor=1.0,propagation_steps=1,show=1): method_label = "fresnel (%s)"%method print("\n# ") print("# near field fresnel (%s) diffraction and focusing "%(method_label)) print("# ") # \ | / # * /users/pirro/Documents/workspace/syned | | | * # / | \ # <------- d ---------------><--------- d -------> # d is propagation_distance print("Incident intensity: ",wf.get_intensity().sum()) # propagation downstream the lens to image plane for i in range(propagation_steps): if propagation_steps > 1: print(">>> Propagating step %d of %d; propagation_distance=%g m"%(i+1,propagation_steps, propagation_distance*defocus_factor/propagation_steps)) if method == 'fft': wf = propagate_2D_fresnel(wf, propagation_distance*defocus_factor/propagation_steps) elif method == 'convolution': wf = propagate_2D_fresnel_convolution(wf, propagation_distance*defocus_factor/propagation_steps) elif method == 'srw': wf = propagate_2D_fresnel_srw(wf, propagation_distance*defocus_factor/propagation_steps) elif method == 'fraunhofer': wf = propagate_2D_fraunhofer(wf, propagation_distance*defocus_factor/propagation_steps) else: raise Exception("Not implemented method: %s"%method) horizontal_profile = wf.get_intensity()[:,int(wf.size()[1]/2)] horizontal_profile /= horizontal_profile.max() print("FWHM of the horizontal profile: %g um"%(1e6*line_fwhm(horizontal_profile)*wf.delta()[0])) vertical_profile = wf.get_intensity()[int(wf.size()[0]/2),:] vertical_profile /= vertical_profile.max() print("FWHM of the vertical profile: %g um"%(1e6*line_fwhm(vertical_profile)*wf.delta()[1])) if do_plot: from srxraylib.plot.gol import plot,plot_image plot_image(wf.get_intensity(),1e6*wf.get_coordinate_x(),1e6*wf.get_coordinate_y(), xtitle="X um (%d pixels)"%(wf.size()[0]),ytitle="Y um (%d pixels)",title='intensity (%s)'%method,show=False) plot_image(wf.get_phase(),1e6*wf.get_coordinate_x(),1e6*wf.get_coordinate_y(), xtitle="X um (%d pixels)"%(wf.size()[0]),ytitle="Y um (%d pixels)"%(wf.size[1]),title='phase (%s)'%method,show=False) plot(wf.get_coordinate_x(),horizontal_profile, wf.get_coordinate_y(),vertical_profile, legend=['Horizontal profile','Vertical profile'],title="%s %s"%(plot_title,method),show=show) print("Output intensity: ",wf.get_intensity().sum()) return wf,wf.get_coordinate_x(),horizontal_profile
# method = "fraunhofer" # method = "srw" method = "fft" if method == "fraunhofer": wf_rebinned = wf.rebin(4,10,4,15,keep_the_same_intensity=1,set_extrapolation_to_zero=1) wf_prop = propagate_2D_fraunhofer(wf_rebinned,propagation_distance=propagation_distance,shift_half_pixel=1) elif method == "srw": wf_prop = propagate_2D_fresnel_srw(wf,propagation_distance=propagation_distance,srw_autosetting=1) elif method == "fft": wf_rebinned = wf.rebin(4,10,4,15,keep_the_same_intensity=1,set_extrapolation_to_zero=1) plot_image(wf_rebinned.get_phase(), 1e6*wf_rebinned.get_coordinate_x(), 1e6*wf_rebinned.get_coordinate_y(), title="Rebinned phases",show=0) number_of_steps = 1 if number_of_steps == 1: wf_prop = propagate_2D_fresnel(wf_rebinned,propagation_distance=propagation_distance,shift_half_pixel=1) else: wf_prop = wf_rebinned for i in range(number_of_steps): print(">>> Propagating step %d or %d..."%(i+1,number_of_steps)) wf_prop = propagate_2D_fresnel(wf_prop,propagation_distance=propagation_distance/number_of_steps,shift_half_pixel=1) else: raise Exception("Undefined method") plot_image(wf_prop.get_intensity(),1e6*wf_prop.get_coordinate_x(),1e6*wf_prop.get_coordinate_y(), show=0, title="in-python propagated intensity at 35 m",xtitle="X [um]",ytitle="Y [um]",) wavefront_intensity_fwhm(wf_prop,prefix="In-python propagated wavefront",units="urad") #
def propagate_2D_fresnel(self, do_plot, method='fft', wavelength=1.24e-10, aperture_type='square', aperture_diameter=40e-6, pixelsize_x=1e-6, pixelsize_y=1e-6, npixels_x=1024, npixels_y=1024, propagation_distance=30.0, m=1, m_x=1, m_y=1, show=0): method_label = "fresnel (%s)" % method print( "\n# ") print("# 2D near field fresnel (%s) diffraction from a %s aperture " % (method_label, aperture_type)) print("# ") # wf = Wavefront2D.initialize_wavefront_from_steps(x_start=-pixelsize_x*npixels_x/2, # x_step=pixelsize_x, # y_start=-pixelsize_y*npixels_y/2, # y_step=pixelsize_y, # wavelength=wavelength, # number_of_points=(npixels_x,npixels_y)) wf = Wavefront2D.initialize_wavefront_from_range( x_min=-pixelsize_x * npixels_x / 2, x_max=pixelsize_x * npixels_x / 2, y_min=-pixelsize_y * npixels_y / 2, y_max=pixelsize_y * npixels_y / 2, number_of_points=(npixels_x, npixels_y), wavelength=wavelength) wf.set_plane_wave_from_complex_amplitude((1.0 + 0j)) if aperture_type == 'circle': wf.apply_pinhole(aperture_diameter / 2) elif aperture_type == 'square': wf.apply_slit(-aperture_diameter / 2, aperture_diameter / 2, -aperture_diameter / 2, aperture_diameter / 2) else: raise Exception("Not implemented! (accepted: circle, square)") if method == 'fft': wf1 = propagate_2D_fresnel(wf, propagation_distance) elif method == 'rescaling': wf1 = propagator2d_fourier_rescaling(wf, propagation_distance, m=m) elif method == 'rescaling_xy': wf1 = propagator2d_fourier_rescaling_xy(wf, propagation_distance, m_x=m_x, m_y=m_y) else: raise Exception("Not implemented method: %s" % method) if do_plot: from srxraylib.plot.gol import plot_image plot_image(wf.get_intensity(), 1e6 * wf.get_coordinate_x(), 1e6 * wf.get_coordinate_y(), title="aperture intensity (%s), Diameter=%5.1f um" % (aperture_type, 1e6 * aperture_diameter), xtitle="X [um]", ytitle="Y [um]", show=0) plot_image( wf1.get_intensity(), 1e6 * wf1.get_coordinate_x() / propagation_distance, 1e6 * wf1.get_coordinate_y() / propagation_distance, title= "Diffracted intensity (%s) by a %s slit of aperture %3.1f um" % (aperture_type, method_label, 1e6 * aperture_diameter), xtitle="X [urad]", ytitle="Y [urad]", show=0) # get the theoretical value angle_x = wf.get_coordinate_x() / propagation_distance intensity_theory = get_theoretical_diffraction_pattern( angle_x, aperture_type=aperture_type, aperture_diameter=aperture_diameter, wavelength=wavelength, normalization=True) intensity_calculated = wf1.get_intensity()[:, int(wf1.size()[1] / 2)] intensity_calculated /= intensity_calculated.max() if do_plot: from srxraylib.plot.gol import plot plot( wf1.get_coordinate_x() * 1e6 / propagation_distance, intensity_calculated, angle_x * 1e6, intensity_theory, legend=[ "%s H profile" % method_label, "Theoretical (far field)" ], legend_position=(0.60, 0.95), title= "%s diffraction of a %s slit of %3.1f um at wavelength of %3.1f A" % (method_label, aperture_type, aperture_diameter * 1e6, wavelength * 1e10), xtitle="X (urad)", ytitle="Intensity", xrange=[-20, 20], show=show) if method == 'rescaling_xy' and do_plot: angle_y = wf.get_coordinate_y() / propagation_distance intensity_calculated_v = wf1.get_intensity()[int(wf1.size()[1] / 2), :] intensity_calculated_v /= intensity_calculated_v.max() from srxraylib.plot.gol import plot plot( wf1.get_coordinate_y() * 1e6 / propagation_distance, intensity_calculated_v, angle_y * 1e6, intensity_theory, legend=[ "%s V profile" % method_label, "Theoretical (far field)" ], legend_position=(0.60, 0.95), title= "%s diffraction of a %s slit of %3.1f um at wavelength of %3.1f A" % (method_label, aperture_type, aperture_diameter * 1e6, wavelength * 1e10), xtitle="Y (urad)", ytitle="Intensity", xrange=[-20, 20], show=show) return wf1.get_coordinate_x( ) / propagation_distance, intensity_calculated, angle_x, intensity_theory
def propagation_with_lens(self,do_plot=do_plot,method='fft', wavelength=1.24e-10, pixelsize_x=1e-6,npixels_x=2000,pixelsize_y=1e-6,npixels_y=2000, propagation_distance=30.0,defocus_factor=1.0,propagation_steps=1,show=1): method_label = "fresnel (%s)"%method print("\n# ") print("# near field fresnel (%s) diffraction and focusing "%(method_label)) print("# ") # \ | / # * | | | * # / | \ # <------- d ---------------><--------- d -------> # d is propagation_distance # wf = Wavefront2D.initialize_wavefront_from_steps(x_start=-pixelsize_x*npixels_x/2, # x_step=pixelsize_x, # y_start=-pixelsize_y*npixels_y/2, # y_step=pixelsize_y, # wavelength=wavelength, # number_of_points=(npixels_x,npixels_y)) wf = Wavefront2D.initialize_wavefront_from_range(x_min=-pixelsize_x*npixels_x/2,x_max=pixelsize_x*npixels_x/2, y_min=-pixelsize_y*npixels_y/2,y_max=pixelsize_y*npixels_y/2, number_of_points=(npixels_x,npixels_y),wavelength=wavelength) spherical_or_plane_and_lens = 0 if spherical_or_plane_and_lens == 0: # set spherical wave at the lens entrance (radius=distance) wf.set_spherical_wave(complex_amplitude=1.0,radius=-propagation_distance) else: # apply lens that will focus at propagation_distance downstream the lens. # Note that the vertical is a bit defocused wf.set_plane_wave_from_complex_amplitude(1.0+0j) focal_length = propagation_distance # / 2 wf.apply_ideal_lens(focal_length,focal_length) print("Incident intensity: ",wf.get_intensity().sum()) # propagation downstream the lens to image plane for i in range(propagation_steps): if propagation_steps > 1: print(">>> Propagating step %d of %d; propagation_distance=%g m"%(i+1,propagation_steps, propagation_distance*defocus_factor/propagation_steps)) if method == 'fft': wf = propagate_2D_fresnel(wf, propagation_distance*defocus_factor/propagation_steps) elif method == 'convolution': wf = propagate_2D_fresnel_convolution(wf, propagation_distance*defocus_factor/propagation_steps) elif method == 'srw': wf = propagate_2D_fresnel_srw(wf, propagation_distance*defocus_factor/propagation_steps) elif method == 'fraunhofer': wf = propagate_2D_fraunhofer(wf, propagation_distance*defocus_factor/propagation_steps) else: raise Exception("Not implemented method: %s"%method) horizontal_profile = wf.get_intensity()[:,wf.size()[1]/2] horizontal_profile /= horizontal_profile.max() print("FWHM of the horizontal profile: %g um"%(1e6*line_fwhm(horizontal_profile)*wf.delta()[0])) vertical_profile = wf.get_intensity()[wf.size()[0]/2,:] vertical_profile /= vertical_profile.max() print("FWHM of the vertical profile: %g um"%(1e6*line_fwhm(vertical_profile)*wf.delta()[1])) if do_plot: from srxraylib.plot.gol import plot,plot_image plot_image(wf.get_intensity(),wf.get_coordinate_x(),wf.get_coordinate_y(),title='intensity (%s)'%method,show=0) # plot_image(wf.get_amplitude(),wf.get_coordinate_x(),wf.get_coordinate_y(),title='amplitude (%s)'%method,show=0) plot_image(wf.get_phase(),wf.get_coordinate_x(),wf.get_coordinate_y(),title='phase (%s)'%method,show=0) plot(wf.get_coordinate_x(),horizontal_profile, wf.get_coordinate_y(),vertical_profile, legend=['Horizontal profile','Vertical profile'],title="%s"%method,show=show) print("Output intensity: ",wf.get_intensity().sum()) return wf.get_coordinate_x(),horizontal_profile
def propagate_2D_fresnel(self,do_plot=do_plot,method='fft', wavelength=1.24e-10,aperture_type='square',aperture_diameter=40e-6, pixelsize_x=1e-6,pixelsize_y=1e-6,npixels_x=1024,npixels_y=1024, propagation_distance = 30.0,show=1): method_label = "fresnel (%s)"%method print("\n# ") print("# 2D near field fresnel (%s) diffraction from a %s aperture "%(method_label,aperture_type)) print("# ") # wf = Wavefront2D.initialize_wavefront_from_steps(x_start=-pixelsize_x*npixels_x/2, # x_step=pixelsize_x, # y_start=-pixelsize_y*npixels_y/2, # y_step=pixelsize_y, # wavelength=wavelength, # number_of_points=(npixels_x,npixels_y)) wf = Wavefront2D.initialize_wavefront_from_range(x_min=-pixelsize_x*npixels_x/2,x_max=pixelsize_x*npixels_x/2, y_min=-pixelsize_y*npixels_y/2,y_max=pixelsize_y*npixels_y/2, number_of_points=(npixels_x,npixels_y),wavelength=wavelength) wf.set_plane_wave_from_complex_amplitude((1.0+0j)) if aperture_type == 'circle': wf.apply_pinhole(aperture_diameter/2) elif aperture_type == 'square': wf.apply_slit(-aperture_diameter/2, aperture_diameter/2,-aperture_diameter/2, aperture_diameter/2) elif aperture_type == 'gaussian': X = wf.get_mesh_x() Y = wf.get_mesh_y() window = numpy.exp(- (X*X + Y*Y)/2/(aperture_diameter/2.35)**2) wf.rescale_amplitudes(window) else: raise Exception("Not implemented! (accepted: circle, square, gaussian)") if method == 'fft': wf1 = propagate_2D_fresnel(wf, propagation_distance) elif method == 'convolution': wf1 = propagate_2D_fresnel_convolution(wf, propagation_distance) elif method == 'srw': wf1 = propagate_2D_fresnel_srw(wf, propagation_distance) elif method == 'integral': wf1 = propagate_2D_integral(wf, propagation_distance) else: raise Exception("Not implemented method: %s"%method) if do_plot: from srxraylib.plot.gol import plot_image plot_image(wf.get_intensity(),1e6*wf.get_coordinate_x(),1e6*wf.get_coordinate_y(), title="aperture intensity (%s), Diameter=%5.1f um"% (aperture_type,1e6*aperture_diameter),xtitle="X [um]",ytitle="Y [um]", show=0) plot_image(wf1.get_intensity(), 1e6*wf1.get_coordinate_x()/propagation_distance, 1e6*wf1.get_coordinate_y()/propagation_distance, title="Diffracted intensity (%s) by a %s slit of aperture %3.1f um"% (aperture_type,method_label,1e6*aperture_diameter), xtitle="X [urad]",ytitle="Y [urad]", show=0) # get the theoretical value angle_x = wf1.get_coordinate_x() / propagation_distance intensity_theory = get_theoretical_diffraction_pattern(angle_x,aperture_type=aperture_type,aperture_diameter=aperture_diameter, wavelength=wavelength,normalization=True) intensity_calculated = wf1.get_intensity()[:,wf1.size()[1]/2] intensity_calculated /= intensity_calculated.max() if do_plot: from srxraylib.plot.gol import plot plot(wf1.get_coordinate_x()*1e6/propagation_distance,intensity_calculated, angle_x*1e6,intensity_theory, legend=["%s H profile"%method_label,"Theoretical (far field)"], legend_position=(0.95, 0.95), title="%s diffraction of a %s slit of %3.1f um at wavelength of %3.1f A"% (method_label,aperture_type,aperture_diameter*1e6,wavelength*1e10), xtitle="X (urad)", ytitle="Intensity",xrange=[-20,20], show=show) return wf1.get_coordinate_x()/propagation_distance,intensity_calculated,angle_x,intensity_theory
def propagation_with_lens(self, do_plot=do_plot, method='fft', wavelength=1.24e-10, pixelsize_x=1e-6, npixels_x=2000, pixelsize_y=1e-6, npixels_y=2000, propagation_distance=30.0, defocus_factor=1.0, propagation_steps=1, show=1): method_label = "fresnel (%s)" % method print( "\n# ") print("# near field fresnel (%s) diffraction and focusing " % (method_label)) print("# ") # \ | / # * | | | * # / | \ # <------- d ---------------><--------- d -------> # d is propagation_distance # wf = Wavefront2D.initialize_wavefront_from_steps(x_start=-pixelsize_x*npixels_x/2, # x_step=pixelsize_x, # y_start=-pixelsize_y*npixels_y/2, # y_step=pixelsize_y, # wavelength=wavelength, # number_of_points=(npixels_x,npixels_y)) wf = Wavefront2D.initialize_wavefront_from_range( x_min=-pixelsize_x * npixels_x / 2, x_max=pixelsize_x * npixels_x / 2, y_min=-pixelsize_y * npixels_y / 2, y_max=pixelsize_y * npixels_y / 2, number_of_points=(npixels_x, npixels_y), wavelength=wavelength) spherical_or_plane_and_lens = 0 if spherical_or_plane_and_lens == 0: # set spherical wave at the lens entrance (radius=distance) wf.set_spherical_wave(complex_amplitude=1.0, radius=-propagation_distance) else: # apply lens that will focus at propagation_distance downstream the lens. # Note that the vertical is a bit defocused wf.set_plane_wave_from_complex_amplitude(1.0 + 0j) focal_length = propagation_distance # / 2 wf.apply_ideal_lens(focal_length, focal_length) print("Incident intensity: ", wf.get_intensity().sum()) # propagation downstream the lens to image plane for i in range(propagation_steps): if propagation_steps > 1: print( ">>> Propagating step %d of %d; propagation_distance=%g m" % (i + 1, propagation_steps, propagation_distance * defocus_factor / propagation_steps)) if method == 'fft': wf = propagate_2D_fresnel( wf, propagation_distance * defocus_factor / propagation_steps) elif method == 'convolution': wf = propagate_2D_fresnel_convolution( wf, propagation_distance * defocus_factor / propagation_steps) elif method == 'srw': wf = propagate_2D_fresnel_srw( wf, propagation_distance * defocus_factor / propagation_steps) elif method == 'fraunhofer': wf = propagate_2D_fraunhofer( wf, propagation_distance * defocus_factor / propagation_steps) else: raise Exception("Not implemented method: %s" % method) horizontal_profile = wf.get_intensity()[:, int(wf.size()[1] / 2)] horizontal_profile /= horizontal_profile.max() print("FWHM of the horizontal profile: %g um" % (1e6 * line_fwhm(horizontal_profile) * wf.delta()[0])) vertical_profile = wf.get_intensity()[int(wf.size()[0] / 2), :] vertical_profile /= vertical_profile.max() print("FWHM of the vertical profile: %g um" % (1e6 * line_fwhm(vertical_profile) * wf.delta()[1])) if do_plot: from srxraylib.plot.gol import plot, plot_image plot_image(wf.get_intensity(), wf.get_coordinate_x(), wf.get_coordinate_y(), title='intensity (%s)' % method, show=0) # plot_image(wf.get_amplitude(),wf.get_coordinate_x(),wf.get_coordinate_y(),title='amplitude (%s)'%method,show=0) plot_image(wf.get_phase(), wf.get_coordinate_x(), wf.get_coordinate_y(), title='phase (%s)' % method, show=0) plot(wf.get_coordinate_x(), horizontal_profile, wf.get_coordinate_y(), vertical_profile, legend=['Horizontal profile', 'Vertical profile'], title="%s" % method, show=show) print("Output intensity: ", wf.get_intensity().sum()) return wf.get_coordinate_x(), horizontal_profile
(method_label)) print("# ") wf = Wavefront2D.initialize_wavefront_from_range( x_min=-pixelsize_x * npixels_x / 2, x_max=pixelsize_x * npixels_x / 2, y_min=-pixelsize_y * npixels_y / 2, y_max=pixelsize_y * npixels_y / 2, number_of_points=(npixels_x, npixels_y), wavelength=wavelength) wf.set_plane_wave_from_complex_amplitude((1.0 + 0j)) wf.apply_pinhole(aperture_diameter / 2, negative=True) wf1 = propagate_2D_fresnel(wf, propagation_distance) plot_image(wf.get_intensity(), 1e6 * wf.get_coordinate_x(), 1e6 * wf.get_coordinate_y(), title="intensity at screen/aperture plane, Diameter=%5.1f um" % (1e6 * aperture_diameter), xtitle="X [um]", ytitle="Y [um]", show=0) plot_image(wf1.get_intensity(), 1e6 * wf1.get_coordinate_x() / propagation_distance, 1e6 * wf1.get_coordinate_y() / propagation_distance, title="Diffracted intensity by a circular stop %3.1f um" % (1e6 * aperture_diameter),
elif method == "fft": wf_rebinned = wf.rebin(4, 10, 4, 15, keep_the_same_intensity=1, set_extrapolation_to_zero=1) plot_image(wf_rebinned.get_phase(), 1e6 * wf_rebinned.get_coordinate_x(), 1e6 * wf_rebinned.get_coordinate_y(), title="Rebinned phases", show=0) number_of_steps = 1 if number_of_steps == 1: wf_prop = propagate_2D_fresnel( wf_rebinned, propagation_distance=propagation_distance, shift_half_pixel=1) else: wf_prop = wf_rebinned for i in range(number_of_steps): print(">>> Propagating step %d or %d..." % (i + 1, number_of_steps)) wf_prop = propagate_2D_fresnel( wf_prop, propagation_distance=propagation_distance / number_of_steps, shift_half_pixel=1) else: raise Exception("Undefined method") plot_image(
def propagate_2D(calculation_parameters, input_parameters): shadow_oe = calculation_parameters.shadow_oe_end if calculation_parameters.do_ff_z and calculation_parameters.do_ff_x: global_phase_shift_profile = None if shadow_oe._oe.F_MOVE == 1 and shadow_oe._oe.X_ROT != 0.0: if input_parameters.ghy_calcType == 3 or input_parameters.ghy_calcType == 4: global_phase_shift_profile = calculation_parameters.w_mirr_2D_values elif input_parameters.ghy_calcType == 2: global_phase_shift_profile = ScaledMatrix.initialize_from_range(numpy.zeros((3, 3)), shadow_oe._oe.RWIDX2, shadow_oe._oe.RWIDX1, shadow_oe._oe.RLEN2, shadow_oe._oe.RLEN1) for x_index in range(global_phase_shift_profile.size_x()): global_phase_shift_profile.z_values[x_index, :] += global_phase_shift_profile.get_y_values()*numpy.sin(numpy.radians(-shadow_oe._oe.X_ROT)) elif input_parameters.ghy_calcType == 3 or input_parameters.ghy_calcType == 4: global_phase_shift_profile = calculation_parameters.w_mirr_2D_values # only tangential slopes if input_parameters.ghy_calcType == 3 or input_parameters.ghy_calcType == 4: rms_slope = hy_findrmsslopefromheight(ScaledArray(np_array=global_phase_shift_profile.z_values[int(global_phase_shift_profile.size_x()/2), :], scale=global_phase_shift_profile.get_y_values())) print("Using RMS slope = " + str(rms_slope)) # ------------------------------------------ # far field calculation # ------------------------------------------ focallength_ff = calculate_focal_length_ff_2D(calculation_parameters.ghy_x_min, calculation_parameters.ghy_x_max, calculation_parameters.ghy_z_min, calculation_parameters.ghy_z_max, input_parameters.ghy_npeak, calculation_parameters.gwavelength) if (input_parameters.ghy_calcType == 3 or input_parameters.ghy_calcType == 4) and rms_slope != 0: focallength_ff = min(focallength_ff,(calculation_parameters.ghy_z_max-calculation_parameters.ghy_z_min) / 16 / rms_slope ) #xshi changed elif input_parameters.ghy_calcType == 2 and not global_phase_shift_profile is None: focallength_ff = min(focallength_ff, input_parameters.ghy_distance*4) #TODO: PATCH to be found with a formula print("FF: calculated focal length: " + str(focallength_ff)) fftsize_x = int(calculate_fft_size(calculation_parameters.ghy_x_min, calculation_parameters.ghy_x_max, calculation_parameters.gwavelength, focallength_ff, input_parameters.ghy_fftnpts, factor=20)) fftsize_z = int(calculate_fft_size(calculation_parameters.ghy_z_min, calculation_parameters.ghy_z_max, calculation_parameters.gwavelength, focallength_ff, input_parameters.ghy_fftnpts, factor=20)) print("FF: creating plane wave begin, fftsize_x = " + str(fftsize_x) + ", fftsize_z = " + str(fftsize_z)) wavefront = Wavefront2D.initialize_wavefront_from_range(wavelength=calculation_parameters.gwavelength, number_of_points=(fftsize_x, fftsize_z), x_min=calculation_parameters.ghy_x_min, x_max=calculation_parameters.ghy_x_max, y_min=calculation_parameters.ghy_z_min, y_max=calculation_parameters.ghy_z_max) try: for i in range(0, len(wavefront.electric_field_array.x_coord)): for j in range(0, len(wavefront.electric_field_array.y_coord)): interpolated = calculation_parameters.wIray_2d.interpolate_value(wavefront.electric_field_array.x_coord[i], wavefront.electric_field_array.y_coord[j]) wavefront.electric_field_array.set_z_value(i, j, numpy.sqrt(0.0 if interpolated < 0 else interpolated)) except IndexError: raise Exception("Unexpected Error during interpolation: try reduce Number of bins for I(Tangential) histogram") wavefront.apply_ideal_lens(focallength_ff, focallength_ff) shadow_oe = calculation_parameters.shadow_oe_end if input_parameters.ghy_calcType == 3 or \ (input_parameters.ghy_calcType == 2 and not global_phase_shift_profile is None): print("FF: calculating phase shift due to Height Error Profile") phase_shifts = numpy.zeros(wavefront.size()) for index in range(0, phase_shifts.shape[0]): np_array = numpy.zeros(global_phase_shift_profile.shape()[1]) for j in range(0, len(np_array)): np_array[j] = global_phase_shift_profile.interpolate_value(wavefront.get_coordinate_x()[index], calculation_parameters.w_mirr_2D_values.get_y_value(j)) global_phase_shift_profile_z = ScaledArray.initialize_from_steps(np_array, global_phase_shift_profile.y_coord[0], global_phase_shift_profile.y_coord[1] - global_phase_shift_profile.y_coord[0]) phase_shifts[index, :] = get_mirror_phase_shift(wavefront.get_coordinate_y(), calculation_parameters.gwavelength, calculation_parameters.wangle_z, calculation_parameters.wl_z, global_phase_shift_profile_z) wavefront.add_phase_shifts(phase_shifts) elif input_parameters.ghy_calcType == 4: print("FF: calculating phase shift due to Height Error Profile") phase_shifts = numpy.zeros(wavefront.size()) for index in range(0, phase_shifts.shape[0]): global_phase_shift_profile_z = ScaledArray.initialize_from_steps(global_phase_shift_profile.z_values[index, :], global_phase_shift_profile.y_coord[0], global_phase_shift_profile.y_coord[1] - global_phase_shift_profile.y_coord[0]) phase_shifts[index, :] = get_grating_phase_shift(wavefront.get_coordinate_y(), calculation_parameters.gwavelength, calculation_parameters.wangle_z, calculation_parameters.wangle_ref_z, calculation_parameters.wl_z, global_phase_shift_profile_z) wavefront.add_phase_shifts(phase_shifts) elif input_parameters.ghy_calcType == 6: for w_mirr_2D_values in calculation_parameters.w_mirr_2D_values: phase_shift = get_crl_phase_shift(w_mirr_2D_values, input_parameters, calculation_parameters, [wavefront.get_coordinate_x(), wavefront.get_coordinate_y()]) wavefront.add_phase_shift(phase_shift) print("calculated plane wave: begin FF propagation (distance = " + str(focallength_ff) + ")") propagated_wavefront = propagator2D.propagate_2D_fresnel(wavefront, focallength_ff) print("dif_zp: begin calculation") imagesize_x = min(abs(calculation_parameters.ghy_x_max), abs(calculation_parameters.ghy_x_min)) * 2 imagesize_x = min(imagesize_x, input_parameters.ghy_npeak*2*0.88*calculation_parameters.gwavelength*focallength_ff/abs(calculation_parameters.ghy_x_max-calculation_parameters.ghy_x_min)) # TODO: this is a patch: to be rewritten if shadow_oe._oe.F_MOVE==1 and not shadow_oe._oe.Y_ROT==0: imagesize_x = max(imagesize_x, 8*(focallength_ff*numpy.tan(numpy.radians(numpy.abs(shadow_oe._oe.Y_ROT))) + numpy.abs(shadow_oe._oe.OFFX))) delta_x = propagated_wavefront.delta()[0] imagenpts_x = int(round(imagesize_x/delta_x/2) * 2 + 1) imagesize_z = min(abs(calculation_parameters.ghy_z_max), abs(calculation_parameters.ghy_z_min)) * 2 imagesize_z = min(imagesize_z, input_parameters.ghy_npeak*2*0.88*calculation_parameters.gwavelength*focallength_ff/abs(calculation_parameters.ghy_z_max-calculation_parameters.ghy_z_min)) # TODO: this is a patch: to be rewritten if shadow_oe._oe.F_MOVE==1 and not shadow_oe._oe.X_ROT==0: imagesize_z = max(imagesize_z, 8*(focallength_ff*numpy.tan(numpy.radians(numpy.abs(shadow_oe._oe.X_ROT))) + numpy.abs(shadow_oe._oe.OFFZ))) delta_z = propagated_wavefront.delta()[1] imagenpts_z = int(round(imagesize_z/delta_z/2) * 2 + 1) dif_xpzp = ScaledMatrix.initialize_from_range(numpy.ones((imagenpts_x, imagenpts_z)), min_scale_value_x = -(imagenpts_x - 1) / 2 * delta_x, max_scale_value_x =(imagenpts_x - 1) / 2 * delta_x, min_scale_value_y = -(imagenpts_z - 1) / 2 * delta_z, max_scale_value_y =(imagenpts_z - 1) / 2 * delta_z) for i in range(0, dif_xpzp.shape()[0]): for j in range(0, dif_xpzp.shape()[1]): dif_xpzp.set_z_value(i, j, numpy.absolute(propagated_wavefront.get_interpolated_complex_amplitude( dif_xpzp.x_coord[i], dif_xpzp.y_coord[j]))**2 ) dif_xpzp.set_scale_from_range(0, -(imagenpts_x - 1) / 2 * delta_x / focallength_ff, (imagenpts_x - 1) / 2 * delta_x / focallength_ff) dif_xpzp.set_scale_from_range(1, -(imagenpts_z - 1) / 2 * delta_z / focallength_ff, (imagenpts_z - 1) / 2 * delta_z / focallength_ff) calculation_parameters.dif_xpzp = dif_xpzp