Ejemplo n.º 1
0
 def initialize_wavefront_from_range(cls, x_min=0.0, x_max=0.0, number_of_points=1000, wavelength=1e-10):
     return Wavefront1D(
         wavelength,
         ScaledArray.initialize_from_range(
             np_array=numpy.full(number_of_points, (1.0 + 0.0j), dtype=complex),
             min_scale_value=x_min,
             max_scale_value=x_max,
         ),
     )
Ejemplo n.º 2
0
 def initialize_wavefront_from_range(cls,
                                     x_min=0.0,
                                     x_max=0.0,
                                     number_of_points=1000,
                                     wavelength=1e-10):
     return Wavefront1D(
         wavelength,
         ScaledArray.initialize_from_range(np_array=numpy.full(
             number_of_points, (1.0 + 0.0j), dtype=complex),
                                           min_scale_value=x_min,
                                           max_scale_value=x_max))
Ejemplo n.º 3
0
    def initialize_wavefront_from_range(cls,
                                        x_min=0.0,
                                        x_max=0.0,
                                        number_of_points=1000,
                                        wavelength=1e-10,
                                        polarization=Polarization.SIGMA):

        sA = ScaledArray.initialize_from_range(np_array=numpy.full(
            number_of_points, (1.0 + 0.0j), dtype=complex),
                                               min_scale_value=x_min,
                                               max_scale_value=x_max)

        if ((polarization == Polarization.PI)
                or (polarization == Polarization.TOTAL)):
            sA_pi = ScaledArray.initialize_from_range(np_array=numpy.full(
                number_of_points, (0.0 + 0.0j), dtype=complex),
                                                      min_scale_value=x_min,
                                                      max_scale_value=x_max)
        else:
            sA_pi = None
        return GenericWavefront1D(wavelength, sA, sA_pi)
Ejemplo n.º 4
0
def calculate_function_average_value(function, x_min, x_max, sampling=100):
    sampled_function = ScaledArray.initialize_from_range(np.zeros(sampling), x_min, x_max)
    sampled_function.np_array = function(sampled_function.scale)

    return np.average(sampled_function.np_array)
Ejemplo n.º 5
0
    def test_ScaledArray(self,do_plot=do_plot):



        #
        # ScaledArray.initialize + set_scale_from_steps
        #
        test_array = numpy.arange(15.0, 18.8, 0.2)


        print("\nTesting ScaledArray.initialize + set_scale_from_steps...")


        scaled_array = ScaledArray.initialize(test_array)
        scaled_array.set_scale_from_steps(test_array[0],0.2)

        print("Using array: ",test_array)
        print("Stored array: ",scaled_array.get_values())

        print("Using array: ",test_array)
        print("Stored abscissas: ",scaled_array.get_abscissas())

        numpy.testing.assert_almost_equal(test_array,scaled_array.get_values(),11)
        numpy.testing.assert_almost_equal(test_array,scaled_array.get_abscissas(),11)
        self.assertAlmostEqual(0.2,scaled_array.delta(),11)
        self.assertAlmostEqual(15.0,scaled_array.offset(),11)

        x_in =   (18.80,16.22,22.35)
        x_good = (18.80,16.22,18.8)

        for i,x in enumerate(x_in):
            print("interpolated at %3.2f is: %3.2f (must give %3.2f)"%( x,scaled_array.interpolate_value(x), x_good[i] ))
            self.assertAlmostEqual(scaled_array.interpolate_value(x), x_good[i], 2)


        #
        # ScaledArray.initialize + set_scale_from_range ; interpolate vectorized
        #
        print("\nTesting ScaledArray.initialize + set_scale_from_range ; interpolate vectorized...")
        scaled_array = ScaledArray.initialize(test_array)
        scaled_array.set_scale_from_range(test_array[0],test_array[-1])

        x_in =   (18.80,16.22,22.35)
        x_good = (18.80,16.22,18.8)

        for i,x in enumerate(x_in):
            print("interpolated at %3.2f is: %3.2f (must give %3.2f)"%( x,scaled_array.interpolate_value(x), x_good[i] ))
            self.assertAlmostEqual(scaled_array.interpolate_value(x), x_good[i], 2)


        #
        # ScaledArray.initialize_from_steps
        #
        print("\nTesting ScaledArray.initialize_from_steps...")
        scaled_array = ScaledArray.initialize_from_steps(test_array, test_array[0], 0.2)

        x_in =   (18.80,16.22,22.35)
        x_good = (18.80,16.22,18.8)

        for i,x in enumerate(x_in):
            print("interpolated at %3.2f is: %3.2f (must give %3.2f)"%( x,scaled_array.interpolate_value(x), x_good[i] ))
            self.assertAlmostEqual(scaled_array.interpolate_value(x), x_good[i], 2)

        #
        # ScaledArray.initialize_from_steps
        #
        print("\nTesting ScaledArray.initialize_from_range...")
        scaled_array = ScaledArray.initialize_from_range(test_array,test_array[0], test_array[-1])

        x_in =   (18.80,16.22,22.35)
        x_good = (18.80,16.22,18.8)

        for i,x in enumerate(x_in):
            print("interpolated at %3.2f is: %3.2f (must give %3.2f)"%( x,scaled_array.interpolate_value(x), x_good[i] ))
            self.assertAlmostEqual(scaled_array.interpolate_value(x), x_good[i], 2)


        #
        # interpolator
        #
        print("\nTesting interpolator...")
        x = numpy.arange(-5.0, 18.8, 3)
        y = x**2

        scaled_array = ScaledArray.initialize_from_range(y,x[0],x[-1])

        print("for interpolation; x=",x)
        print("for interpolation; offset, delta:=",scaled_array.offset(),scaled_array.delta())
        print("for interpolation; abscissas:=",scaled_array.get_abscissas())

        x1 = numpy.concatenate( ( numpy.arange(-6, -4, 0.1) , [0], numpy.arange(11, 20.0, 0.1) ) )

        y1 = scaled_array.interpolate_values(x1)

        if do_plot:
            from srxraylib.plot.gol import plot
            plot(x,y,x1,y1,legend=["Data",'Interpolated'],legend_position=[0.4,0.8],
                 marker=['','o'],linestyle=['-',''],xrange=[-6,21],yrange=[-5,375])

        for i in range(len(x1)):
            y2 = x1[i]**2

            if x1[i] <= x[0]:
                y2 = y[0]

            if x1[i] >= x[-1]:
                y2 = y[-1]

            print("   interpolated at x=%g is: %g (expected: %g)"%(x1[i],y1[i],y2))
            self.assertAlmostEqual(1e-3*y1[i], 1e-3*y2, 2)


        # interpolate on same grid
        print("\nTesting interpolation on the same grid...")



        y1 = scaled_array.interpolate_values(scaled_array.get_abscissas())
        if do_plot:
            from srxraylib.plot.gol import plot
            plot(scaled_array.get_abscissas(),scaled_array.get_values(),
                 scaled_array.get_abscissas(),y1,legend=["Data",'Interpolated on same grid'],legend_position=[0.4,0.8],
                 marker=['','o'],linestyle=['-',''])

        numpy.testing.assert_almost_equal(scaled_array.get_values(),y1,5)
Ejemplo n.º 6
0
def propagate_1D_x_direction(calculation_parameters, input_parameters):

    scale_factor = 1.0

    shadow_oe = calculation_parameters.shadow_oe_end

    global_phase_shift_profile = None

    if shadow_oe._oe.F_MOVE == 1 and shadow_oe._oe.Y_ROT != 0.0:
        if input_parameters.ghy_calcType == 3 or input_parameters.ghy_calcType == 4:
            global_phase_shift_profile = calculation_parameters.w_mirror_lx
        elif input_parameters.ghy_calcType == 2:
            global_phase_shift_profile = ScaledArray.initialize_from_range(numpy.zeros(3), shadow_oe._oe.RWIDX2, shadow_oe._oe.RWIDX1)

        global_phase_shift_profile.set_values(global_phase_shift_profile.get_values() +
                                              global_phase_shift_profile.get_abscissas()*numpy.sin(numpy.radians(-shadow_oe._oe.Y_ROT)))
    elif input_parameters.ghy_calcType == 3 or input_parameters.ghy_calcType == 4:
        global_phase_shift_profile = calculation_parameters.w_mirror_lx

    if input_parameters.ghy_calcType == 3 or input_parameters.ghy_calcType == 4:
        rms_slope = hy_findrmsslopefromheight(global_phase_shift_profile)

        print("Using RMS slope = " + str(rms_slope))

        average_incident_angle = numpy.radians(90-calculation_parameters.shadow_oe_end._oe.T_INCIDENCE)*1e3
        average_reflection_angle = numpy.radians(90-calculation_parameters.shadow_oe_end._oe.T_REFLECTION)*1e3

        if calculation_parameters.beam_not_cut_in_x:
            dp_image = numpy.std(calculation_parameters.xx_focal_ray)/input_parameters.ghy_focallength
            dp_se = 2 * rms_slope * numpy.sin(average_incident_angle/1e3)	# different in x and z
            dp_error = calculation_parameters.gwavelength/2/(calculation_parameters.ghy_x_max-calculation_parameters.ghy_x_min)

            scale_factor = max(1, 5*min(dp_error/dp_image, dp_error/dp_se))

    # ------------------------------------------
    # far field calculation
    # ------------------------------------------
    if calculation_parameters.do_ff_x:
        focallength_ff = calculate_focal_length_ff(calculation_parameters.ghy_x_min,
                                                   calculation_parameters.ghy_x_max,
                                                   input_parameters.ghy_npeak,
                                                   calculation_parameters.gwavelength)

        if input_parameters.ghy_calcType == 3:
            if not (rms_slope == 0.0 or average_incident_angle == 0.0):
                focallength_ff = min(focallength_ff,(calculation_parameters.ghy_x_max-calculation_parameters.ghy_x_min) / 16 / rms_slope / numpy.sin(average_incident_angle / 1e3))#xshi changed
        elif input_parameters.ghy_calcType == 4:
            if not (rms_slope == 0.0 or average_incident_angle == 0.0):
                focallength_ff = min(focallength_ff,(calculation_parameters.ghy_x_max-calculation_parameters.ghy_x_min) / 8 / rms_slope / (numpy.sin(average_incident_angle / 1e3) + numpy.sin(average_reflection_angle / 1e3)))#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

        fftsize = int(scale_factor * calculate_fft_size(calculation_parameters.ghy_x_min,
                                                        calculation_parameters.ghy_x_max,
                                                        calculation_parameters.gwavelength,
                                                        focallength_ff,
                                                        input_parameters.ghy_fftnpts))
        
        print("FF: creating plane wave begin, fftsize = " +  str(fftsize))

        wavefront = Wavefront1D.initialize_wavefront_from_range(wavelength=calculation_parameters.gwavelength,
                                                                number_of_points=fftsize,
                                                                x_min=scale_factor * calculation_parameters.ghy_x_min,
                                                                x_max=scale_factor * calculation_parameters.ghy_x_max)

        if scale_factor == 1.0:
            try:
                wavefront.set_plane_wave_from_complex_amplitude(numpy.sqrt(calculation_parameters.wIray_x.interpolate_values(wavefront.get_abscissas())))
            except IndexError:
                raise Exception("Unexpected Error during interpolation: try reduce Number of bins for I(Sagittal) histogram")

        wavefront.apply_ideal_lens(focallength_ff)

        if input_parameters.ghy_calcType == 3 or \
                (input_parameters.ghy_calcType == 2 and not global_phase_shift_profile is None):
           wavefront.add_phase_shifts(get_mirror_phase_shift(wavefront.get_abscissas(),
                                                             calculation_parameters.gwavelength,
                                                             calculation_parameters.wangle_x,
                                                             calculation_parameters.wl_x,
                                                             global_phase_shift_profile))
        elif input_parameters.ghy_calcType == 4:
           wavefront.add_phase_shifts(get_grating_phase_shift(wavefront.get_abscissas(),
                                                              calculation_parameters.gwavelength,
                                                              calculation_parameters.wangle_x,
                                                              calculation_parameters.wangle_ref_x,
                                                              calculation_parameters.wl_x,
                                                              global_phase_shift_profile))

        print("calculated plane wave: begin FF propagation (distance = " +  str(focallength_ff) + ")")

        propagated_wavefront = propagator.propagate_1D_fresnel(wavefront, focallength_ff)

        print("dif_xp: begin calculation")

        shadow_oe = calculation_parameters.shadow_oe_end

        imagesize = min(abs(calculation_parameters.ghy_x_max), abs(calculation_parameters.ghy_x_min)) * 2
        # 2017-01 Luca Rebuffi
        imagesize = min(imagesize,
                        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 = max(imagesize, 8*(focallength_ff*numpy.tan(numpy.radians(numpy.abs(shadow_oe._oe.Y_ROT))) + numpy.abs(shadow_oe._oe.OFFX)))

        imagenpts = int(round(imagesize / propagated_wavefront.delta() / 2) * 2 + 1)

        dif_xp = ScaledArray.initialize_from_range(numpy.ones(propagated_wavefront.size()),
                                                   -(imagenpts - 1) / 2 * propagated_wavefront.delta(),
                                                   (imagenpts - 1) / 2 * propagated_wavefront.delta())


        dif_xp.np_array = numpy.absolute(propagated_wavefront.get_interpolated_complex_amplitudes(dif_xp.scale))**2

        dif_xp.set_scale_from_range(-(imagenpts - 1) / 2 * propagated_wavefront.delta() / focallength_ff,
                                    (imagenpts - 1) / 2 * propagated_wavefront.delta() / focallength_ff)

        calculation_parameters.dif_xp = dif_xp

    # ------------------------------------------
    # near field calculation
    # ------------------------------------------
    if input_parameters.ghy_nf >= 1 and input_parameters.ghy_calcType > 1:  # near field calculation
        focallength_nf = input_parameters.ghy_focallength

        fftsize = int(scale_factor * calculate_fft_size(calculation_parameters.ghy_x_min,
                                                        calculation_parameters.ghy_x_max,
                                                        calculation_parameters.gwavelength,
                                                        numpy.abs(focallength_nf),
                                                        input_parameters.ghy_fftnpts))

        print("NF: creating plane wave begin, fftsize = " +  str(fftsize))

        wavefront = Wavefront1D.initialize_wavefront_from_range(wavelength=calculation_parameters.gwavelength,
                                                                number_of_points=fftsize,
                                                                x_min=scale_factor*calculation_parameters.ghy_x_min,
                                                                x_max=scale_factor*calculation_parameters.ghy_x_max)

        if scale_factor == 1.0:
            try:
                wavefront.set_plane_wave_from_complex_amplitude(numpy.sqrt(calculation_parameters.wIray_x.interpolate_values(wavefront.get_abscissas())))
            except IndexError:
                raise Exception("Unexpected Error during interpolation: try reduce Number of bins for I(Sagittal) histogram")

        wavefront.apply_ideal_lens(focallength_nf)

        if input_parameters.ghy_calcType == 3 or \
                (input_parameters.ghy_calcType == 2 and not global_phase_shift_profile is None):
           wavefront.add_phase_shifts(get_mirror_phase_shift(wavefront.get_abscissas(),
                                                             calculation_parameters.gwavelength,
                                                             calculation_parameters.wangle_x,
                                                             calculation_parameters.wl_x,
                                                             global_phase_shift_profile))
        elif input_parameters.ghy_calcType == 4:
           wavefront.add_phase_shifts(get_grating_phase_shift(wavefront.get_abscissas(),
                                                              calculation_parameters.gwavelength,
                                                              calculation_parameters.wangle_x,
                                                              calculation_parameters.wangle_ref_x,
                                                              calculation_parameters.wl_x,
                                                              global_phase_shift_profile))

        print("calculated plane wave: begin NF propagation (distance = " + str(input_parameters.ghy_distance) + ")")

        propagated_wavefront = propagator.propagate_1D_fresnel(wavefront, input_parameters.ghy_distance)

        # ghy_npeak in the wavefront propagation image
        imagesize = (input_parameters.ghy_npeak * 2 * 0.88 * calculation_parameters.gwavelength * numpy.abs(focallength_nf) / abs(calculation_parameters.ghy_x_max - calculation_parameters.ghy_x_min))
        imagesize = max(imagesize,
                        2 * abs((calculation_parameters.ghy_x_max - calculation_parameters.ghy_x_min) * (input_parameters.ghy_distance - numpy.abs(focallength_nf))) / numpy.abs(focallength_nf))

        if input_parameters.ghy_calcType == 3:
            imagesize = max(imagesize,
                            16 * rms_slope * numpy.abs(focallength_nf) * numpy.sin(average_incident_angle / 1e3))
        elif input_parameters.ghy_calcType == 4:
            imagesize = max(imagesize,
                            8 * rms_slope * numpy.abs(focallength_nf) * (numpy.sin(average_incident_angle / 1e3) + numpy.sin(average_reflection_angle / 1e3)))

        # TODO: this is a patch: to be rewritten
        if shadow_oe._oe.F_MOVE==1 and not shadow_oe._oe.Y_ROT==0:
            imagesize = max(imagesize, 8*(input_parameters.ghy_distance*numpy.tan(numpy.radians(numpy.abs(shadow_oe._oe.Y_ROT))) + numpy.abs(shadow_oe._oe.OFFX)))

        imagenpts = int(round(imagesize / propagated_wavefront.delta() / 2) * 2 + 1)

        print("dif_x: begin calculation")

        dif_x = ScaledArray.initialize_from_range(numpy.ones(imagenpts),
                                                  -(imagenpts - 1) / 2 * propagated_wavefront.delta(),
                                                  (imagenpts - 1) / 2 * propagated_wavefront.delta())

        dif_x.np_array *= numpy.absolute(propagated_wavefront.get_interpolated_complex_amplitudes(dif_x.scale))**2

        calculation_parameters.dif_x = dif_x