def testCalculateDiffraction(self): res = {} for geometry_type in GeometryType.allGeometryTypes(): effective_asymmetry = 0.0 if geometry_type == LaueDiffraction( ) or geometry_type == LaueTransmission(): effective_asymmetry = 90.0 * numpy.pi / 180 diffraction_setup = DiffractionSetupSweeps( geometry_type, "Si", thickness=128 * 1e-6, miller_h=1, miller_k=1, miller_l=1, asymmetry_angle=effective_asymmetry, azimuthal_angle=0.0, energy_min=8174, energy_max=8174, energy_points=1, angle_deviation_min=-20.0e-6, angle_deviation_max=20e-6, angle_deviation_points=5) diffraction = Diffraction() res[geometry_type] = diffraction.calculateDiffraction( diffraction_setup)
def testCalculateBraggTransmission(self): diffraction_setup = DiffractionSetupSweeps(BraggTransmission(), "Si", thickness=7 * 1e-6, miller_h=1, miller_k=1, miller_l=1, asymmetry_angle= -5*numpy.pi/180, azimuthal_angle=0.0, energy_min=10174, energy_max=10174, energy_points=1, angle_deviation_min= -20.0e-6, angle_deviation_max=20e-6, angle_deviation_points=5) diffraction = Diffraction() res = diffraction.calculateDiffraction(diffraction_setup) s_intensity_fraction=[0.6226567465900791, 0.6438109466925752, 0.6414813069615722, 0.5966674813771604, 0.45178497063185913] s_phase=[2.286827125757465, 2.11586718740292, 1.8761281776985377, 1.444935411854202, -0.015769881275207204] p_intensity_fraction=[0.6287809489878944, 0.6436830110383608, 0.6260332041734042, 0.5556946212761588, 0.4666570232587092] p_phase=[2.4244705128134725, 2.2877506323333496, 2.093850209325308, 1.7465537434885796, 0.8969740263938913] self.assertDiffractionResult(10174, s_intensity_fraction, s_phase, p_intensity_fraction, p_phase, res)
def testCalculatePsiFromStructureFactor(self): diffraction = Diffraction() crystal = xraylib.Crystal_GetCrystal("Si") photon_in = Photon(8000, Vector(-1, 0, -1)) structure_factor = 113.581288 + 1.763808j unitcell_volume = crystal['volume'] * 10**-30 psi = diffraction._calculatePsiFromStructureFactor( unitcell_volume, photon_in, structure_factor) self.assertAlmostEqual(psi.real, -1.527826e-5) self.assertAlmostEqual(psi.imag, -2.372566e-7)
def testCalculateLaueTransmission(self): diffraction_setup = DiffractionSetupSweeps(LaueTransmission(), "Si", thickness=100 * 1e-6, miller_h=1, miller_k=1, miller_l=1, asymmetry_angle=90*numpy.pi/180, azimuthal_angle=0.0, energy_min=10000, energy_max=10000, energy_points=1, angle_deviation_min= -20.0e-6, angle_deviation_max=20.0e-6, angle_deviation_points=5) diffraction = Diffraction() res = diffraction.calculateDiffraction(diffraction_setup)
def testAsPlotData1D(self): diffraction_setup = DiffractionSetupSweeps( BraggDiffraction(), "Si", thickness=0.0100 * 1e-2, miller_h=1, miller_k=1, miller_l=1, asymmetry_angle=3 * numpy.pi / 180, azimuthal_angle=3 * numpy.pi / 180, energy_min=10000, energy_max=10000, energy_points=1, angle_deviation_min=-100.0e-6, angle_deviation_max=100e-6, angle_deviation_points=50) diffraction = Diffraction() res = diffraction.calculateDiffraction(diffraction_setup)
def calculate_standard_interface(): # Create a diffraction setup. print("\nCreating a diffraction setup...") diffraction_setup = DiffractionSetupSweeps( geometry_type=BraggDiffraction(), # GeometryType object crystal_name="Si", # string thickness=1e-2, # meters miller_h=1, # int miller_k=1, # int miller_l=1, # int asymmetry_angle= 0, #10.0*numpy.pi/180., # radians azimuthal_angle=0.0, # radians energy_min=8000.0, # eV energy_max=8000.0, # eV energy_points=1, # int angle_deviation_min=-100e-6, # radians angle_deviation_max=100e-6, # radians angle_deviation_points=500) # int # Create a Diffraction object. diffraction = Diffraction() # Create a DiffractionResult object holding the results of the diffraction calculations. print("\nCalculating the diffraction results...") diffraction_result = diffraction.calculateDiffraction(diffraction_setup) # # Now the Mueller/Stokes calculation from the diffraction results # mueller_diffraction = MuellerDiffraction( diffraction_result, StokesVector([1, 0, 1, 0]), inclination_angle=0.0) #np.pi*45/180) # Create a MullerResult object. print("\nCalculating the Stokes vector...") mueller_result = mueller_diffraction.calculate_stokes() return mueller_result
def calculate_laue_monochromator(energy_setup=8000.0,energies=numpy.linspace(7990,8010,200)): diffraction_setup_r = DiffractionSetup(geometry_type=LaueDiffraction(), # GeometryType object crystal_name="Si", # string thickness=10e-6, # meters miller_h=1, # int miller_k=1, # int miller_l=1, # int asymmetry_angle=numpy.pi/2, # 10.0*numpy.pi/180., # radians azimuthal_angle=0.0) # radians # int diffraction = Diffraction() scan = numpy.zeros_like(energies) r = numpy.zeros_like(energies) for i in range(energies.size): # # gets Bragg angle needed to create deviation's scan # energy = energies[i] bragg_angle = diffraction_setup_r.angleBragg(energy_setup) print("Bragg angle for E=%f eV is %f deg" % (energy, bragg_angle * 180.0 / numpy.pi)) # Create a Diffraction object (the calculator) deviation = 0.0 # angle_deviation_min + ia * angle_step angle = deviation + numpy.pi / 2 + bragg_angle # calculate the components of the unitary vector of the incident photon scan # Note that diffraction plane is YZ yy = numpy.cos(angle) zz = - numpy.abs(numpy.sin(angle)) photon = Photon(energy_in_ev=energy,direction_vector=Vector(0.0,yy,zz)) # perform the calculation coeffs_r = diffraction.calculateDiffractedComplexAmplitudes(diffraction_setup_r, photon) scan[i] = energy r[i] = numpy.abs( coeffs_r['S'].complexAmplitude() )**4 return scan,r
def testCalculateBraggDiffraction(self): diffraction_setup = DiffractionSetupSweeps(BraggDiffraction(), "Si", thickness=0.0100 * 1e-2, miller_h=1, miller_k=1, miller_l=1, asymmetry_angle=3*numpy.pi/180, azimuthal_angle=0.0, energy_min=10000, energy_max=10000, energy_points=1, angle_deviation_min= -20.0e-6, angle_deviation_max=20e-6, angle_deviation_points=5) diffraction = Diffraction() res = diffraction.calculateDiffraction(diffraction_setup) # s_intensity_fraction=[0.017519141613069177, 0.0321954521714361, 0.07981125895068454, 0.920965084591721, 0.9417181994525138] # s_phase=[-0.745427562155594, -0.8048350757616735, -0.7441070552657782, -1.0347178161614214, -2.353510138419943] # p_intensity_fraction=[0.014173087736472335, 0.025303154305706777, 0.06615101317795873, 0.5244213525516417, 0.9369357917670563] # p_phase=[-0.793312359389805, -0.7582549664194022, -0.750381901971316, -0.8168058020223106, -2.353282699138147] # TODO: check correctness of phases!! s_intensity_fraction = [ 0.01726512, 0.03246927, 0.07909485, 0.92019219, 0.9417577 ] s_phase = [ 2.39724121, 2.3388142 , 2.39913351, 2.10984245, 0.78904046] p_intensity_fraction = [ 0.01433174, 0.02517142, 0.06566106, 0.52116638, 0.93697839] p_phase = [ 2.34537175, 2.37937306, 2.39282075, 2.32528928, 0.78934907] self.assertDiffractionResult(10000, s_intensity_fraction, s_phase, p_intensity_fraction, p_phase, res)
def calculate_with_crystalpy( bragg_or_laue=0, # diffracted_or_transmitted=0, # crystal_name="Si", # string thickness=1e-2, # meters miller_h=1, # int miller_k=1, # int miller_l=1, # int asymmetry_angle=0.0, # radians energy=8000.0, # eV angle_deviation_min=-100e-6, # radians angle_deviation_max=100e-6, # radians angle_deviation_points=500, method=0, # 0=crystalpy input, 1=shadow4 preprocessor file ): if bragg_or_laue == 0: if diffracted_or_transmitted == 0: geometry_type = BraggDiffraction() elif diffracted_or_transmitted == 1: geometry_type = BraggTransmission() else: raise Exception("Bad geometry type") elif bragg_or_laue == 1: if diffracted_or_transmitted == 0: geometry_type = LaueDiffraction() elif diffracted_or_transmitted == 1: geometry_type = LaueTransmission() else: raise Exception("Bad geometry type") else: raise Exception("Bad geometry type") # Create a diffraction setup. # print("\nCreating a diffraction setup...") if method == 0: diffraction_setup = DiffractionSetup(geometry_type=geometry_type, crystal_name=crystal_name, thickness=thickness, miller_h=miller_h, miller_k=miller_k, miller_l=miller_l, asymmetry_angle=asymmetry_angle, azimuthal_angle=0.0) else: create_bragg_preprocessor_file_v1(interactive=False, DESCRIPTOR=crystal_name, H_MILLER_INDEX=miller_h, K_MILLER_INDEX=miller_k, L_MILLER_INDEX=miller_l, TEMPERATURE_FACTOR=1.0, E_MIN=5000.0, E_MAX=15000.0, E_STEP=100.0, SHADOW_FILE="bragg_xop.dat") diffraction_setup = DiffractionSetupShadowPreprocessor( geometry_type=geometry_type, crystal_name=crystal_name, thickness=thickness, miller_h=miller_h, miller_k=miller_k, miller_l=miller_l, asymmetry_angle=asymmetry_angle, azimuthal_angle=0.0, preprocessor_file="bragg_xop.dat") angle_step = (angle_deviation_max - angle_deviation_min) / angle_deviation_points # # gets Bragg angle needed to create deviation's scan # bragg_angle = diffraction_setup.angleBragg(energy) # print("Bragg angle for E=%f eV is %f deg"%(energy,bragg_angle*180.0/numpy.pi)) # Create a Diffraction object (the calculator) diffraction = Diffraction() # initialize arrays for storing outputs deviations = numpy.zeros(angle_deviation_points) intensityS = numpy.zeros(angle_deviation_points) intensityP = numpy.zeros(angle_deviation_points) for ia in range(angle_deviation_points): deviation = angle_deviation_min + ia * angle_step # angle = deviation + bragg_angle + asymmetry_angle # # calculate the components of the unitary vector of the incident photon scan # # Note that diffraction plane is YZ # yy = numpy.cos(angle) # zz = - numpy.abs(numpy.sin(angle)) # photon = Photon(energy_in_ev=energy,direction_vector=Vector(0.0,yy,zz)) k_unitary = diffraction_setup.incomingPhotonDirection( energy, deviation) # or equivalently # k_0_unitary = diffraction_setup.incomingPhotonDirection(energy, 0.0) # k_unitary = k_0_unitary.rotateAroundAxis( Vector(1.0,0.0,0.0), -deviation) photon = Photon(energy_in_ev=energy, direction_vector=k_unitary) # perform the calculation coeffs = diffraction.calculateDiffractedComplexAmplitudes( diffraction_setup, photon) # store results deviations[ia] = deviation intensityS[ia] = coeffs['S'].intensity() intensityP[ia] = coeffs['P'].intensity() return deviations, intensityS, intensityP
def calculate_with_polarized_photon(method=0): # Create a diffraction setup. print("\nCreating a diffraction setup...") diffraction_setup = DiffractionSetup( geometry_type=BraggDiffraction(), # GeometryType object crystal_name="Si", # string thickness=1e-2, # meters miller_h=1, # int miller_k=1, # int miller_l=1, # int asymmetry_angle= 0, #10.0*numpy.pi/180., # radians azimuthal_angle=0.0) # radians # int energy = 8000.0 # eV angle_deviation_min = -100e-6 # radians angle_deviation_max = 100e-6 # radians angle_deviation_points = 500 angle_step = (angle_deviation_max - angle_deviation_min) / angle_deviation_points bunch_in = PolarizedPhotonBunch() bragg_angle = diffraction_setup.angleBragg(energy) print("Bragg angle for E=%f eV is %f deg" % (energy, bragg_angle * 180.0 / numpy.pi)) # Create a Diffraction object. diffraction = Diffraction() # # get wavevector with incident direction matching Bragg angle # K0 = diffraction_setup.getK0(energy) K0unitary = K0.getNormalizedVector() print("K0", K0.components()) # method = 0 # diffraction for individual photons # method = 1 # diffraction for bunch ZZ = numpy.zeros(angle_deviation_points) if method == 0: bunch_out = PolarizedPhotonBunch() for ia in range(angle_deviation_points): deviation = angle_deviation_min + ia * angle_step # angle = deviation + bragg_angle # yy = numpy.cos(angle) # zz = - numpy.abs(numpy.sin(angle)) # photon = PolarizedPhoton(energy_in_ev=energy,direction_vector=Vector(0.0,yy,zz), # stokes_vector=StokesVector([1,0,1,0])) # minus sign in angle is to perform cw rotation when deviation increses Vin = K0unitary.rotateAroundAxis(Vector(1, 0, 0), -deviation) photon = PolarizedPhoton(energy_in_ev=energy, direction_vector=Vin, stokes_vector=StokesVector([1, 0, 1, 0])) photon_out = diffraction.calculateDiffractedPolarizedPhoton( diffraction_setup, incoming_polarized_photon=photon, inclination_angle=0.0) bunch_out.addPhoton(photon_out) ZZ[ia] = angle_deviation_min + ia * angle_step elif method == 1: # diffraction for bunch for ia in range(angle_deviation_points): deviation = angle_deviation_min + ia * angle_step # angle = deviation + bragg_angle # yy = numpy.cos(angle) # zz = - numpy.abs(numpy.sin(angle)) # photon = PolarizedPhoton(energy_in_ev=energy,direction_vector=Vector(0.0,yy,zz), # stokes_vector=StokesVector([1,0,1,0])) # minus sign in angle is to perform cw rotation when deviation increses Vin = K0unitary.rotateAroundAxis(Vector(1, 0, 0), -deviation) photon = PolarizedPhoton(energy_in_ev=energy, direction_vector=Vin, stokes_vector=StokesVector([1, 0, 1, 0])) bunch_in.addPhoton(photon) ZZ[ia] = angle_deviation_min + ia * angle_step bunch_out = diffraction.calculateDiffractedPolarizedPhotonBunch( diffraction_setup, bunch_in, 0.0) bunch_out_dict = bunch_out.toDictionary() plot(1e6 * ZZ, bunch_out_dict["s0"], 1e6 * ZZ, bunch_out_dict["s1"], legend=["S0", "S1"], xtitle="theta - thetaB [urad]", title="Polarized reflectivity calculation using method %d" % method)
def calculate_external_Crystal(GEOMETRY_TYPE, CRYSTAL_NAME, THICKNESS, MILLER_H, MILLER_K, MILLER_L, ASYMMETRY_ANGLE, AZIMUTHAL_ANGLE, incoming_bunch, INCLINATION_ANGLE, DUMP_TO_FILE, FILE_NAME="tmp.dat"): # Create a GeometryType object: # Bragg diffraction = 0 # Bragg transmission = 1 # Laue diffraction = 2 # Laue transmission = 3 if GEOMETRY_TYPE == 0: GEOMETRY_TYPE_OBJECT = BraggDiffraction() elif GEOMETRY_TYPE == 1: GEOMETRY_TYPE_OBJECT = BraggTransmission() elif GEOMETRY_TYPE == 2: GEOMETRY_TYPE_OBJECT = LaueDiffraction() elif GEOMETRY_TYPE == 3: GEOMETRY_TYPE_OBJECT = LaueTransmission() else: raise Exception("Crystal: The geometry type could not be interpreted!\n") # Create a diffraction setup. # At this stage I translate angles in radians, energy in eV and all other values in SI units. print("Crystal: Creating a diffraction setup...\n") diffraction_setup = DiffractionSetup(geometry_type=GEOMETRY_TYPE_OBJECT, # GeometryType object crystal_name=str(CRYSTAL_NAME), # string thickness=float(THICKNESS) * 1e-2, # meters miller_h=int(MILLER_H), # int miller_k=int(MILLER_K), # int miller_l=int(MILLER_L), # int asymmetry_angle=float(ASYMMETRY_ANGLE) / 180 * np.pi, # radians azimuthal_angle=float(AZIMUTHAL_ANGLE) / 180 * np.pi) # radians # incoming_photons=incoming_bunch) # Create a Diffraction object. diffraction = Diffraction() # Create a PolarizedPhotonBunch object holding the results of the diffraction calculations. print("Crystal: Calculating the outgoing photons...\n") outgoing_bunch = diffraction.calculateDiffractedPolarizedPhotonBunch(diffraction_setup, incoming_bunch, INCLINATION_ANGLE) # Check that the result of the calculation is indeed a PolarizedPhotonBunch object. if not isinstance(outgoing_bunch, PolarizedPhotonBunch): raise Exception("Crystal: Expected PolarizedPhotonBunch as a result, found {}!\n".format(type(outgoing_bunch))) # Dump data to file if requested. if DUMP_TO_FILE == 0: print("Crystal: Writing data in {file}...\n".format(file=FILE_NAME)) with open(FILE_NAME, "w") as file: try: file.write("#S 1 photon bunch\n" "#N 8\n" "#L Energy [eV] Vx Vy Vz S0 S1 S2 S3\n") file.write(outgoing_bunch.toString()) file.close() print("File written to disk: %s"%FILE_NAME) except: raise Exception("Crystal: The data could not be dumped onto the specified file!\n") return outgoing_bunch
def calculate_external_CrystalCalculator(GEOMETRY_TYPE, CRYSTAL_NAME, THICKNESS, MILLER_H, MILLER_K, MILLER_L, ASYMMETRY_ANGLE, AZIMUTHAL_ANGLE, ENERGY_POINTS, ENERGY_MIN, ENERGY_MAX, ANGLE_DEVIATION_POINTS, ANGLE_DEVIATION_MIN, ANGLE_DEVIATION_MAX, STOKES_S0, STOKES_S1, STOKES_S2, STOKES_S3, INCLINATION_ANGLE, DUMP_TO_FILE, FILE_NAME="tmp.dat"): # Create a GeometryType object: # Bragg diffraction = 0 # Bragg transmission = 1 # Laue diffraction = 2 # Laue transmission = 3 if GEOMETRY_TYPE == 0: GEOMETRY_TYPE_OBJECT = BraggDiffraction() elif GEOMETRY_TYPE == 1: GEOMETRY_TYPE_OBJECT = BraggTransmission() elif GEOMETRY_TYPE == 2: GEOMETRY_TYPE_OBJECT = LaueDiffraction() elif GEOMETRY_TYPE == 3: GEOMETRY_TYPE_OBJECT = LaueTransmission() else: raise Exception( "CrystalCalculator: The geometry type could not be interpreted!" ) # Create a diffraction setup. # At this stage I translate angles in radians, energy in eV and all other values in SI units. print("CrystalCalculator: Creating a diffraction setup...\n") if ENERGY_POINTS == 1: if ENERGY_MIN != ENERGY_MAX: raise Exception( "CrystalCalculator: Finite energy range with only one sampled value!" ) diffraction_setup = DiffractionSetupSweeps( geometry_type=GEOMETRY_TYPE_OBJECT, # GeometryType object crystal_name=str(CRYSTAL_NAME), # string thickness=float(THICKNESS) * 1e-2, # meters miller_h=int(MILLER_H), # int miller_k=int(MILLER_K), # int miller_l=int(MILLER_L), # int asymmetry_angle=float(ASYMMETRY_ANGLE) / 180 * np.pi, # radians azimuthal_angle=float(AZIMUTHAL_ANGLE) / 180 * np.pi, # radians energy_min=float(ENERGY_MIN), # eV energy_max=float(ENERGY_MAX), # eV energy_points=int(ENERGY_POINTS), # int angle_deviation_min=float(ANGLE_DEVIATION_MIN) * 1e-6, # radians angle_deviation_max=float(ANGLE_DEVIATION_MAX) * 1e-6, # radians angle_deviation_points=int(ANGLE_DEVIATION_POINTS)) # int # Create a Diffraction object. diffraction = Diffraction() # Create a DiffractionResult object holding the results of the diffraction calculations. print("CrystalCalculator: Calculating the diffraction results...\n") diffraction_result = diffraction.calculateDiffraction( diffraction_setup) # Create a StokesVector object. incoming_stokes_vector = StokesVector( [STOKES_S0, STOKES_S1, STOKES_S2, STOKES_S3]) # Create a MuellerDiffraction object. mueller_diffraction = MuellerDiffraction( diffraction_result, incoming_stokes_vector, float(INCLINATION_ANGLE) * np.pi / 180) # Create a MullerResult object. print("CrystalCalculator: Calculating the Stokes vector...\n") mueller_result = mueller_diffraction.calculate_stokes() # Create the data to output. output_data = MailingBox(diffraction_result, mueller_result) # Dump data to file if requested. if DUMP_TO_FILE == 1: print("CrystalCalculator: Writing data in {file}...\n".format( file=FILE_NAME)) with open(FILE_NAME, "w") as file: try: file.write( "VALUES:\n\n" "geometry type: {geometry_type}\n" "crystal name: {crystal_name}\n" "thickness: {thickness}\n" "miller H: {miller_h}\n" "miller K: {miller_k}\n" "miller L: {miller_l}\n" "asymmetry angle: {asymmetry_angle}\n" "azimuthal angle: {azimuthal_angle}\n" "energy points: {energy_points}\n" "energy minimum: {energy_min}\n" "energy maximum: {energy_max}\n" "deviation angle points: {angle_deviation_points}\n" "deviation angle minimum: {angle_deviation_min}\n" "deviation angle maximum: {angle_deviation_max}\n" "inclination angle: {inclination_angle}\n" "incoming Stokes vector: {incoming_stokes_vector}\n\n" "RESULTS:\n\n" "S-Polarization:\n" "Intensity: {s_intensity}\n" "Phase: {s_phase}\n\n" "P-Polarization:\n" "Intensity: {p_intensity}\n" "Phase: {p_phase}\n\n" "SP-Difference:\n" "Intensity: {sp_intensity}\n" "Phase: {sp_phase}\n\n" "Stokes vector:\n" "S0: {s0}\n" "S1: {s1}\n" "S2: {s2}\n" "S3: {s3}\n\n" "Degree of circular polarization: {pol_degree}".format( geometry_type=GEOMETRY_TYPE_OBJECT.description(), crystal_name=CRYSTAL_NAME, thickness=THICKNESS, miller_h=MILLER_H, miller_k=MILLER_K, miller_l=MILLER_L, asymmetry_angle=ASYMMETRY_ANGLE, azimuthal_angle=AZIMUTHAL_ANGLE, energy_points=ENERGY_POINTS, energy_min=ENERGY_MIN, energy_max=ENERGY_MAX, angle_deviation_points=ANGLE_DEVIATION_POINTS, angle_deviation_min=ANGLE_DEVIATION_MIN, angle_deviation_max=ANGLE_DEVIATION_MAX, inclination_angle=INCLINATION_ANGLE, incoming_stokes_vector=incoming_stokes_vector. components(), s_intensity=diffraction_result.sIntensityByEnergy( ENERGY_MIN), s_phase=diffraction_result.sPhaseByEnergy( ENERGY_MIN, deg=True), p_intensity=diffraction_result.pIntensityByEnergy( ENERGY_MIN), p_phase=diffraction_result.pPhaseByEnergy( ENERGY_MIN, deg=True), sp_intensity=diffraction_result. differenceIntensityByEnergy(ENERGY_MIN), sp_phase=diffraction_result. differencePhaseByEnergy(ENERGY_MIN, deg=True), s0=mueller_result.s0_by_energy(ENERGY_MIN), s1=mueller_result.s1_by_energy(ENERGY_MIN), s2=mueller_result.s2_by_energy(ENERGY_MIN), s3=mueller_result.s3_by_energy(ENERGY_MIN), pol_degree=mueller_result. polarization_degree_by_energy(ENERGY_MIN))) file.close() print("File written to disk: %s" % FILE_NAME) except: raise Exception( "CrystalCalculator: The data could not be dumped onto the specified file!" ) return output_data
def testConstructor(self): diffraction = Diffraction() self.assertIsInstance(diffraction, Diffraction)
def calculate_with_crystalpy( bragg_or_laue=0, # diffracted_or_transmitted=0, # crystal_name="Si", # string thickness=1e-2, # meters miller_h=1, # int miller_k=1, # int miller_l=1, # int asymmetry_angle=0.0, # radians energy=8000.0, # eV angle_deviation_min=-100e-6, # radians angle_deviation_max=100e-6, # radians angle_deviation_points=500, ): if bragg_or_laue == 0: if diffracted_or_transmitted == 0: geometry_type = BraggDiffraction() elif diffracted_or_transmitted == 1: geometry_type = BraggTransmission() else: raise Exception("Bad geometry type") elif bragg_or_laue == 1: if diffracted_or_transmitted == 0: geometry_type = LaueDiffraction() elif diffracted_or_transmitted == 1: geometry_type = LaueTransmission() else: raise Exception("Bad geometry type") else: raise Exception("Bad geometry type") # Create a diffraction setup. print("\nCreating a diffraction setup...") diffraction_setup = DiffractionSetup(geometry_type=geometry_type, crystal_name=crystal_name, thickness=thickness, miller_h=miller_h, miller_k=miller_k, miller_l=miller_l, asymmetry_angle=asymmetry_angle, azimuthal_angle=0.0) # energy = 8000.0 # eV # angle_deviation_min = -100e-6 # radians # angle_deviation_max = 100e-6 # radians # angle_deviation_points = 500 angle_step = (angle_deviation_max - angle_deviation_min) / angle_deviation_points # # gets Bragg angle needed to create deviation's scan # bragg_angle = diffraction_setup.angleBragg(energy) print("Bragg angle for E=%f eV is %f deg" % (energy, bragg_angle * 180.0 / numpy.pi)) # Create a Diffraction object (the calculator) diffraction = Diffraction() # initialize arrays for storing outputs deviations = numpy.zeros(angle_deviation_points) intensityS = numpy.zeros(angle_deviation_points) intensityP = numpy.zeros(angle_deviation_points) k_0_unitary = diffraction_setup.incomingPhotonDirection(energy, 0.0) # photon_0 = Photon(energy_in_ev=energy,direction_vector=k_0_unitary) # k_H_unitary = diffraction_setup._ # print(">>>>>>>>>>>>>>>>>>>>>>>>k_0: ",k_0_unitary._components ) # plot_crystal_sketch(k_0_unitary,k_0_unitary,) for ia in range(angle_deviation_points): deviation = angle_deviation_min + ia * angle_step # angle = deviation + bragg_angle + asymmetry_angle # # calculate the components of the unitary vector of the incident photon scan # # Note that diffraction plane is YZ # yy = numpy.cos(angle) # zz = - numpy.abs(numpy.sin(angle)) # photon = Photon(energy_in_ev=energy,direction_vector=Vector(0.0,yy,zz)) k_unitary = diffraction_setup.incomingPhotonDirection( energy, deviation) # or equivalently # k_0_unitary = diffraction_setup.incomingPhotonDirection(energy, 0.0) # k_unitary = k_0_unitary.rotateAroundAxis( Vector(1.0,0.0,0.0), -deviation) photon = Photon(energy_in_ev=energy, direction_vector=k_unitary) # perform the calculation coeffs = diffraction.calculateDiffractedComplexAmplitudes( diffraction_setup, photon) # store results deviations[ia] = deviation intensityS[ia] = coeffs['S'].intensity() intensityP[ia] = coeffs['P'].intensity() # print(">>>>>>>>>>>>>>>>>>>>>>>>k_0: ",k_0_unitary._components,k_0_unitary.getNormalizedVector()._components ) return deviations, intensityS, intensityP
def testCheckSetup(self): diffraction = Diffraction() diffraction_setup = DiffractionSetupSweeps( BraggDiffraction(), "Si", thickness=128 * 1e-6, miller_h=1, miller_k=1, miller_l=1, asymmetry_angle=0, azimuthal_angle=0.0, energy_min=8174, energy_max=8174, energy_points=1, angle_deviation_min=-20.0e-6, angle_deviation_max=20e-6, angle_deviation_points=5) angle_bragg = 0.19902705045 F_0 = 113.581288 + 1.763808j F_H = 43.814631 - 42.050823J F_H_bar = 42.050823 + 43.814631j # Test possible setup. diffraction._checkSetup(diffraction_setup, angle_bragg, F_0, F_H, F_H_bar) # Test impossible Bragg reflection. diffraction_setup._asymmetry_angle = 45 * numpy.pi / 180 self.assertRaises(ReflectionImpossibleException, diffraction._checkSetup, diffraction_setup, angle_bragg, F_0, F_H, F_H_bar) diffraction_setup._geometry_type = BraggTransmission() self.assertRaises(ReflectionImpossibleException, diffraction._checkSetup, diffraction_setup, angle_bragg, F_0, F_H, F_H_bar) # Test impossible Laue reflection. diffraction_setup._asymmetry_angle = 10 * numpy.pi / 180 diffraction_setup._geometry_type = LaueDiffraction() self.assertRaises(TransmissionImpossibleException, diffraction._checkSetup, diffraction_setup, angle_bragg, F_0, F_H, F_H_bar) diffraction_setup._geometry_type = LaueTransmission() self.assertRaises(TransmissionImpossibleException, diffraction._checkSetup, diffraction_setup, angle_bragg, F_0, F_H, F_H_bar) # Test forbidden reflection diffraction_setup._geometry_type = BraggDiffraction() diffraction_setup._asymmetry_angle = 0 # ... for F_0. self.assertRaises(StructureFactorF0isZeroException, diffraction._checkSetup, diffraction_setup, angle_bragg, 0.0, F_H, F_H_bar) # ... for F_H. self.assertRaises(StructureFactorFHisZeroException, diffraction._checkSetup, diffraction_setup, angle_bragg, F_0, 0.0, F_H_bar) self.assertRaises(StructureFactorFHisZeroException, diffraction._checkSetup, diffraction_setup, angle_bragg, F_0, float('nan') * 1j, F_H_bar) # ... for F_H_bar. self.assertRaises(StructureFactorFHbarIsZeroException, diffraction._checkSetup, diffraction_setup, angle_bragg, F_0, F_H, 0.0) self.assertRaises(StructureFactorFHbarIsZeroException, diffraction._checkSetup, diffraction_setup, angle_bragg, F_0, F_H, float('nan') * 1j)
def calculate_simple_diffraction_energy_scan_accelerated(): # Create a diffraction setup. print("\nCreating a diffraction setup...") diffraction_setup = DiffractionSetup( geometry_type=BraggDiffraction(), # GeometryType object crystal_name="Si", # string thickness=1e-2, # meters miller_h=1, # int miller_k=1, # int miller_l=1, # int asymmetry_angle= 0, #10.0*numpy.pi/180., # radians azimuthal_angle=0.0) # radians # int import socket if socket.getfqdn().find("esrf") >= 0: dx = DabaxXraylib( dabax_repository="http://ftp.esrf.fr/pub/scisoft/DabaxFiles/") else: dx = DabaxXraylib() diffraction_setup_dabax = DiffractionSetupDabax( geometry_type=BraggDiffraction(), # GeometryType object crystal_name="Si", # string thickness=1e-2, # meters miller_h=1, # int miller_k=1, # int miller_l=1, # int asymmetry_angle= 0, #10.0*numpy.pi/180., # radians azimuthal_angle=0.0, dabax=dx) # radians energy = 8000.0 # eV angle_deviation_min = -100e-6 # radians angle_deviation_max = 100e-6 # radians angle_deviation_points = 50 angle_step = (angle_deviation_max - angle_deviation_min) / angle_deviation_points # # gets Bragg angle needed to create deviation's scan # bragg_angle_corrected = diffraction_setup.angleBraggCorrected(energy) print("Bragg angle corrected for E=%f eV is %f deg" % (energy, bragg_angle_corrected * 180.0 / numpy.pi)) DeltaE = energy * 1e-4 npoints = 100 energies = numpy.linspace(energy - 3 * DeltaE, energy + 3 * DeltaE, npoints) # Create a Diffraction object (the calculator) diffraction = Diffraction() diffraction_dabax = Diffraction() # initialize arrays for storing outputs intensityS = numpy.zeros(npoints) intensityP = numpy.zeros(npoints) intensityS_dabax = numpy.zeros(npoints) intensityP_dabax = numpy.zeros(npoints) t0 = time.time() for ia in range(npoints): # calculate the components of the unitary vector of the incident photon scan # Note that diffraction plane is YZ yy = numpy.cos(bragg_angle_corrected) zz = -numpy.abs(numpy.sin(bragg_angle_corrected)) photon = Photon(energy_in_ev=energies[ia], direction_vector=Vector(0.0, yy, zz)) # perform the calculation coeffs = diffraction.calculateDiffractedComplexAmplitudes( diffraction_setup, photon) # store results intensityS[ia] = coeffs['S'].intensity() intensityP[ia] = coeffs['P'].intensity() COOR = [] ENER = [] for ia in range(npoints): # calculate the components of the unitary vector of the incident photon scan # Note that diffraction plane is YZ yy = numpy.cos(bragg_angle_corrected) zz = -numpy.abs(numpy.sin(bragg_angle_corrected)) COOR.append([0.0, yy, zz]) ENER.append(energies[ia]) t1 = time.time() Psi_0, Psi_H, Psi_H_bar = diffraction_setup_dabax.psiAll(ENER) for ia in range(npoints): # perform the calculation incoming_photon = Photon(energy_in_ev=ENER[ia], direction_vector=Vector( COOR[ia][0], COOR[ia][1], COOR[ia][2])) energy = ENER[ia] # psi_0, psi_H, psi_H_bar = diffraction_setup_dabax.psiAll(energy) psi_0, psi_H, psi_H_bar = Psi_0[ia], Psi_H[ia], Psi_H_bar[ia] # Create PerfectCrystalDiffraction instance. perfect_crystal = PerfectCrystalDiffraction( geometry_type=diffraction_setup_dabax.geometryType(), bragg_normal=diffraction_setup_dabax.normalBragg(), surface_normal=diffraction_setup_dabax.normalSurface(), bragg_angle=diffraction_setup_dabax.angleBragg(energy), psi_0=psi_0, psi_H=psi_H, psi_H_bar=psi_H_bar, thickness=diffraction_setup_dabax.thickness(), d_spacing=diffraction_setup_dabax.dSpacing() * 1e-10) complex_amplitudes = perfect_crystal.calculateDiffraction( incoming_photon) intensityS_dabax[ia] = complex_amplitudes['S'].intensity( ) # 0.0 # coeffs_dabax['S'].intensity() intensityP_dabax[ia] = complex_amplitudes['P'].intensity( ) # 0.0 # coeffs_dabax['P'].intensity() t2 = time.time() # plot results import matplotlib.pylab as plt plt.plot(energies, intensityS) plt.plot(energies, intensityP) plt.plot(energies, intensityS_dabax) plt.plot(energies, intensityP_dabax) plt.xlabel("photon energy [eV]") plt.ylabel("Reflectivity") plt.legend([ "Sigma-polarization XRAYLIB", "Pi-polarization XRAYLIB", "Sigma-polarization DABAX", "Pi-polarization DABAX" ]) plt.show() print("Total time, Time per points XRAYLIB: ", t1 - t0, (t1 - t0) / npoints) print("Total time, Time per points DABAX: ", t2 - t1, (t2 - t1) / npoints)
miller_h=int(values.miller_h), # int miller_k=int(values.miller_k), # int miller_l=int(values.miller_l), # int asymmetry_angle=float(values.asymmetry_angle) / 180 * np.pi, # radians azimuthal_angle=float(values.azimuthal_angle) / 180 * np.pi, # radians energy_min=float(values.energy_min) * 1e3, # eV energy_max=float(values.energy_max) * 1e3, # eV energy_points=int(values.energy_points), # int angle_deviation_min=float(values.angle_deviation_min) * 1e-6, # radians angle_deviation_max=float(values.angle_deviation_max) * 1e-6, # radians angle_deviation_points=int(values.angle_deviation_points)) # int # Create a Diffraction object. diffraction = Diffraction() # Create a DiffractionResult object holding the results of the diffraction calculations. print("\nCalculating the diffraction results...") diffraction_result = diffraction.calculateDiffraction(diffraction_setup) # Create a PlotData1D object. print("\nCreating the diffraction profile plots...") plot_1d = plot_diffraction_1d(diffraction_result, values.deg) if False: # Unwrap the phases. print("\nUnwrapping the phase data...") phase_limits = (values.phase_inf_limit, values.phase_sup_limit) plot_1d[3].smart_unwrap(values.intervals, values.intervals_number, phase_limits, values.deg)
def calculate_simple_diffraction_angular_scan_accelerated(): # Create a diffraction setup. diffraction_setup_dabax = DiffractionSetupDabax( geometry_type=BraggDiffraction(), # GeometryType object crystal_name="YB66", # string thickness=7e-3, # meters miller_h=4, # int miller_k=0, # int miller_l=0, # int asymmetry_angle= 0, #10.0*numpy.pi/180., # radians azimuthal_angle=0.0, dabax=DabaxXraylib()) # radians energy = 8040.0 # eV angle_deviation_min = 20e-6 # radians angle_deviation_max = 80e-6 # radians angle_deviation_points = 200 angle_step = (angle_deviation_max - angle_deviation_min) / angle_deviation_points # # gets Bragg angle needed to create deviation's scan # bragg_angle = diffraction_setup_dabax.angleBragg(energy) print("Bragg angle for E=%f eV is %f deg" % (energy, bragg_angle * 180.0 / numpy.pi)) # Create a Diffraction object (the calculator) diffraction = Diffraction() diffraction_dabax = Diffraction() # initialize arrays for storing outputs deviations = numpy.zeros(angle_deviation_points) intensityS = numpy.zeros(angle_deviation_points) intensityP = numpy.zeros(angle_deviation_points) intensityS_dabax = numpy.zeros(angle_deviation_points) intensityP_dabax = numpy.zeros(angle_deviation_points) for ia in range(angle_deviation_points): deviation = angle_deviation_min + ia * angle_step angle = deviation + bragg_angle # calculate the components of the unitary vector of the incident photon scan # Note that diffraction plane is YZ yy = numpy.cos(angle) zz = -numpy.abs(numpy.sin(angle)) photon = Photon(energy_in_ev=energy, direction_vector=Vector(0.0, yy, zz)) # perform the calculation coeffs = diffraction.calculateDiffractedComplexAmplitudes( diffraction_setup_dabax, photon) # store results deviations[ia] = deviation intensityS[ia] = coeffs['S'].intensity() intensityP[ia] = coeffs['P'].intensity() psi_0, psi_H, psi_H_bar = diffraction_setup_dabax.psiAll(energy) for ia in range(angle_deviation_points): deviation = angle_deviation_min + ia * angle_step angle = deviation + bragg_angle # calculate the components of the unitary vector of the incident photon scan # Note that diffraction plane is YZ yy = numpy.cos(angle) zz = -numpy.abs(numpy.sin(angle)) photon = Photon(energy_in_ev=energy, direction_vector=Vector(0.0, yy, zz)) # perform the calculation # coeffs_dabax = diffraction_dabax.calculateDiffractedComplexAmplitudes(diffraction_setup_dabax, photon) # # # store results # deviations[ia] = deviation # intensityS_dabax[ia] = coeffs_dabax['S'].intensity() # intensityP_dabax[ia] = coeffs_dabax['P'].intensity() # Create PerfectCrystalDiffraction instance. perfect_crystal = PerfectCrystalDiffraction( geometry_type=diffraction_setup_dabax.geometryType(), bragg_normal=diffraction_setup_dabax.normalBragg(), surface_normal=diffraction_setup_dabax.normalSurface(), bragg_angle=diffraction_setup_dabax.angleBragg(energy), psi_0=psi_0, psi_H=psi_H, psi_H_bar=psi_H_bar, thickness=diffraction_setup_dabax.thickness(), d_spacing=diffraction_setup_dabax.dSpacing() * 1e-10) complex_amplitudes = perfect_crystal.calculateDiffraction(photon) deviations[ia] = deviation intensityS_dabax[ia] = complex_amplitudes['S'].intensity( ) # 0.0 # coeffs_dabax['S'].intensity() intensityP_dabax[ia] = complex_amplitudes['P'].intensity( ) # 0.0 # coeffs_dabax['P'].intensity() # plot results import matplotlib.pylab as plt plt.plot(1e6 * deviations, intensityS_dabax) plt.plot(1e6 * deviations, intensityP_dabax) plt.xlabel("deviation angle [urad]") plt.ylabel("Reflectivity") plt.legend(["Sigma-polarization DABAX", "Pi-polarization DABAX"]) plt.show()
def trace_beam(self, beam_in, flag_lost_value=-1): p = self.get_coordinates().p() q = self.get_coordinates().q() theta_grazing1 = numpy.pi / 2 - self.get_coordinates().angle_radial() theta_grazing2 = numpy.pi / 2 - self.get_coordinates( ).angle_radial_out() alpha1 = self.get_coordinates().angle_azimuthal() # beam = beam_in.duplicate() # # put beam in mirror reference system # beam.rotate(alpha1, axis=2) beam.rotate(theta_grazing1, axis=1) beam.translation([ 0.0, -p * numpy.cos(theta_grazing1), p * numpy.sin(theta_grazing1) ]) # # reflect beam in the mirror surface # soe = self.get_optical_element() beam_in_crystal_frame_before_reflection = beam.duplicate() if not isinstance(soe, Crystal): # undefined raise Exception("Undefined Crystal") else: beam_mirr, normal = self.apply_crystal_diffraction( beam) # warning, beam is also changed!! # # apply mirror boundaries # beam_mirr.apply_boundaries_syned(soe.get_boundary_shape(), flag_lost_value=flag_lost_value) ######################################################################################## # # TODO" apply crystal reflectivity # nrays = beam_mirr.get_number_of_rays() # energy = 8000.0 # eV # Create a Diffraction object (the calculator) diffraction = Diffraction() scan_type = 1 # 0=scan, 1=loop on rays, 2=bunch of photons (not functional) # TODO: delete 0,2 if scan_type == 0: # scan energy = 8000.0 # eV # setting_angle = self._crystalpy_diffraction_setup.angleBragg(energy) setting_angle = self._crystalpy_diffraction_setup.angleBraggCorrected( energy) angle_deviation_points = nrays # initialize arrays for storing outputs intensityS = numpy.zeros(nrays) intensityP = numpy.zeros(nrays) angle_deviation_min = -100e-6 # radians angle_deviation_max = 100e-6 # radians angle_step = (angle_deviation_max - angle_deviation_min) / angle_deviation_points deviations = numpy.zeros(angle_deviation_points) for ia in range(angle_deviation_points): deviation = angle_deviation_min + ia * angle_step angle = deviation + setting_angle # calculate the components of the unitary vector of the incident photon scan # Note that diffraction plane is YZ yy = numpy.cos(angle) zz = -numpy.abs(numpy.sin(angle)) photon = Photon(energy_in_ev=energy, direction_vector=Vector(0.0, yy, zz)) # if ia < 10: print(ia, 0.0, yy, zz) # perform the calculation coeffs = diffraction.calculateDiffractedComplexAmplitudes( self._crystalpy_diffraction_setup, photon) # store results deviations[ia] = deviation intensityS[ia] = coeffs['S'].intensity() intensityP[ia] = coeffs['P'].intensity() elif scan_type == 1: # from beam, loop # initialize arrays for storing outputs complex_reflectivity_S = numpy.zeros(nrays, dtype=complex) complex_reflectivity_P = numpy.zeros(nrays, dtype=complex) # we retrieve data from "beam" meaning the beam before reflection, in the crystal frame (incident beam...) xp = beam_in_crystal_frame_before_reflection.get_column(4) yp = beam_in_crystal_frame_before_reflection.get_column(5) zp = beam_in_crystal_frame_before_reflection.get_column(6) energies = beam_in_crystal_frame_before_reflection.get_photon_energy_eV( ) for ia in range(nrays): photon = Photon(energy_in_ev=energies[ia], direction_vector=Vector( xp[ia], yp[ia], zp[ia])) # if ia < 10: print(ia, xp[ia], yp[ia], zp[ia]) # perform the calculation coeffs = diffraction.calculateDiffractedComplexAmplitudes( self._crystalpy_diffraction_setup, photon) # store results complex_reflectivity_S[ia] = coeffs['S'].complexAmplitude() complex_reflectivity_P[ia] = coeffs['P'].complexAmplitude() beam_mirr.apply_complex_reflectivities(complex_reflectivity_S, complex_reflectivity_P) elif scan_type == 2: # from beam, bunch # this is complicated... and not faster... # todo: accelerate crystalpy create calculateDiffractedComplexAmplitudes for a PhotonBunch # we retrieve data from "beam" meaning the beam before reflection, in the crystal frame (incident beam...) xp = beam_in_crystal_frame_before_reflection.get_column(4) yp = beam_in_crystal_frame_before_reflection.get_column(5) zp = beam_in_crystal_frame_before_reflection.get_column(6) energies = beam_in_crystal_frame_before_reflection.get_photon_energy_eV( ) Esigma = numpy.sqrt(beam_in_crystal_frame_before_reflection.get_column(24)) * \ numpy.exp(1j * beam_in_crystal_frame_before_reflection.get_column(14)) Epi = numpy.sqrt(beam_in_crystal_frame_before_reflection.get_column(25)) * \ numpy.exp(1j * beam_in_crystal_frame_before_reflection.get_column(15)) photons = ComplexAmplitudePhotonBunch() for ia in range(nrays): photons.addPhoton( ComplexAmplitidePhoton( energy_in_ev=energies[ia], direction_vector=Vector(xp[ia], yp[ia], zp[ia]), Esigma=1.0, # Esigma[ia], Epi=1.0, # [ia], )) bunch_out = diffraction.calculateDiffractedComplexAmplitudePhotonBunch( self._crystalpy_diffraction_setup, photons) bunch_out_dict = bunch_out.toDictionary() reflectivity_S = numpy.sqrt( numpy.array(bunch_out_dict["intensityS"])) reflectivity_P = numpy.sqrt( numpy.array(bunch_out_dict["intensityP"])) beam_mirr.apply_reflectivities(reflectivity_S, reflectivity_P) beam_mirr.add_phases(numpy.array(bunch_out_dict["intensityS"]), numpy.array(bunch_out_dict["intensityP"])) ######################################################################################## # # from element reference system to image plane # beam_out = beam_mirr.duplicate() beam_out.change_to_image_reference_system(theta_grazing2, q) # plot results if False: if scan_type == 0: pass else: deviations = beam_out.get_column(6) intensityS = beam_out.get_column(24) intensityP = beam_out.get_column(25) from srxraylib.plot.gol import plot plot(1e6 * deviations, intensityS, 1e6 * deviations, intensityP, xtitle="deviation angle [urad]", ytitle="Reflectivity", legend=["Sigma-polarization", "Pi-polarization"], linestyle=['', ''], marker=['+', '.']) return beam_out, beam_mirr
def calculate_simple_diffraction(): # Create a diffraction setup. print("\nCreating a diffraction setup...") diffraction_setup = DiffractionSetup( geometry_type=BraggDiffraction(), # GeometryType object crystal_name="Si", # string thickness=1e-2, # meters miller_h=1, # int miller_k=1, # int miller_l=1, # int asymmetry_angle= 0, #10.0*numpy.pi/180., # radians azimuthal_angle=0.0) # radians # int energy = 8000.0 # eV angle_deviation_min = -100e-6 # radians angle_deviation_max = 100e-6 # radians angle_deviation_points = 500 angle_step = (angle_deviation_max - angle_deviation_min) / angle_deviation_points # # gets Bragg angle needed to create deviation's scan # bragg_angle = diffraction_setup.angleBragg(energy) print("Bragg angle for E=%f eV is %f deg" % (energy, bragg_angle * 180.0 / numpy.pi)) # Create a Diffraction object (the calculator) diffraction = Diffraction() # initialize arrays for storing outputs deviations = numpy.zeros(angle_deviation_points) intensityS = numpy.zeros(angle_deviation_points) intensityP = numpy.zeros(angle_deviation_points) for ia in range(angle_deviation_points): deviation = angle_deviation_min + ia * angle_step angle = deviation + bragg_angle # calculate the components of the unitary vector of the incident photon scan # Note that diffraction plane is YZ yy = numpy.cos(angle) zz = -numpy.abs(numpy.sin(angle)) photon = Photon(energy_in_ev=energy, direction_vector=Vector(0.0, yy, zz)) # perform the calculation coeffs = diffraction.calculateDiffractedComplexAmplitudes( diffraction_setup, photon) # store results deviations[ia] = deviation intensityS[ia] = coeffs['S'].intensity() intensityP[ia] = coeffs['P'].intensity() # plot results import matplotlib.pylab as plt plt.plot(1e6 * deviations, intensityS) plt.plot(1e6 * deviations, intensityP) plt.xlabel("deviation angle [urad]") plt.ylabel("Reflectivity") plt.legend(["Sigma-polarization", "Pi-polarization"]) plt.show()
def calculate_simple_diffraction(): # Create a diffraction setup. thickness = 2e-6 print("\nCreating a diffraction setup...") diffraction_setup_r = DiffractionSetup(geometry_type = BraggDiffraction(), # GeometryType object crystal_name = "Si", # string thickness = thickness, # meters miller_h = 1, # int miller_k = 1, # int miller_l = 1, # int asymmetry_angle = 0,#10.0*numpy.pi/180., # radians azimuthal_angle = 0.0) # radians # int diffraction_setup_t = DiffractionSetup(geometry_type = BraggTransmission(), # GeometryType object crystal_name = "Si", # string thickness = thickness, # meters miller_h = 1, # int miller_k = 1, # int miller_l = 1, # int asymmetry_angle = 0,#10.0*numpy.pi/180., # radians azimuthal_angle = 0.0) # radians diffraction_setup_r_half = DiffractionSetup(geometry_type = BraggDiffraction(), # GeometryType object crystal_name = "Si", # string thickness = thickness/2, # meters miller_h = 1, # int miller_k = 1, # int miller_l = 1, # int asymmetry_angle = 0,#10.0*numpy.pi/180., # radians azimuthal_angle = 0.0) # radians # int diffraction_setup_t_half = DiffractionSetup(geometry_type = BraggTransmission(), # GeometryType object crystal_name = "Si", # string thickness = thickness/2, # meters miller_h = 1, # int miller_k = 1, # int miller_l = 1, # int asymmetry_angle = 0,#10.0*numpy.pi/180., # radians azimuthal_angle = 0.0) # radians energy = 8000.0 # eV angle_deviation_min = -300e-6 # radians angle_deviation_max = 300e-6 # radians angle_deviation_points = 500 wavelength = codata.h * codata.c / codata.e / energy print(">>>>>>>>>>>>", wavelength) angle_step = (angle_deviation_max-angle_deviation_min)/angle_deviation_points # # gets Bragg angle needed to create deviation's scan # bragg_angle = diffraction_setup_r.angleBragg(energy) print("Bragg angle for E=%f eV is %f deg"%(energy,bragg_angle*180.0/numpy.pi)) # Create a Diffraction object (the calculator) diffraction = Diffraction() # initialize arrays for storing outputs deviations = numpy.zeros(angle_deviation_points) intensityS_r = numpy.zeros(angle_deviation_points) intensityS_r_half = numpy.zeros(angle_deviation_points) intensityS_t = numpy.zeros(angle_deviation_points) intensityS_rr = numpy.zeros(angle_deviation_points) intensityS_tt = numpy.zeros(angle_deviation_points) r = numpy.zeros(angle_deviation_points, dtype=complex) r2um = numpy.zeros(angle_deviation_points, dtype=complex) t = numpy.zeros(angle_deviation_points, dtype=complex) for ia in range(angle_deviation_points): deviation = angle_deviation_min + ia * angle_step angle = deviation + bragg_angle # calculate the components of the unitary vector of the incident photon scan # Note that diffraction plane is YZ yy = numpy.cos(angle) zz = - numpy.abs(numpy.sin(angle)) photon = Photon(energy_in_ev=energy,direction_vector=Vector(0.0,yy,zz)) # perform the calculation coeffs_r = diffraction.calculateDiffractedComplexAmplitudes(diffraction_setup_r, photon) coeffs_t = diffraction.calculateDiffractedComplexAmplitudes(diffraction_setup_t, photon) coeffs_r_half = diffraction.calculateDiffractedComplexAmplitudes(diffraction_setup_r_half, photon) coeffs_t_half = diffraction.calculateDiffractedComplexAmplitudes(diffraction_setup_t_half, photon) # coeffs_rr = \ # coeffs_r_half['S'] * \ # (coeffs_t_half['S']**0 + \ # coeffs_t_half['S']**2 * ( \ # coeffs_r_half['S'] ** 0 + \ # coeffs_r_half['S'] ** 2 + \ # coeffs_r_half['S'] ** 4 + \ # coeffs_r_half['S'] ** 6 + \ # coeffs_r_half['S'] ** 8 + \ # coeffs_r_half['S'] ** 10 + \ # coeffs_r_half['S'] ** 12 + \ # coeffs_r_half['S'] ** 14 + \ # coeffs_r_half['S'] ** 16 + \ # coeffs_r_half['S'] ** 18 \ # ) ) # a = coeffs_r_half['S'] # b = coeffs_t_half['S'] r[ia] = coeffs_r_half['S'].complexAmplitude() # t[ia] = coeffs_t_half['S'].complexAmplitude() #* numpy.exp(1j * 2 * numpy.pi / wavelength * (0.5 * thickness / numpy.sin(bragg_angle)) ) t[ia] = coeffs_t_half['S'].complexAmplitude() * numpy.exp(-1j * 2 * numpy.pi / wavelength * numpy.cos(bragg_angle) * deviation * (thickness/2) ) r2um[ia] = coeffs_r['S'].complexAmplitude() # # sum = a**0 # # for i in range(2,400,2): # # sum += a**i # sum = a**0 / (a**0 - a**2) # # coeffs_rr = a * (b**0 + b**2 * sum) # one = a**0 # coeffs_rr = a * ( one + b**2 / (one - a**2)) # coeffs_tt = b**2 * sum # # intensityS_rr[ia] = coeffs_rr.intensity() # intensityS_tt[ia] = coeffs_tt.intensity() # # # print(coeffs_r) # # print(coeffs_r['S'].complexAmplitude()) # # # store results deviations[ia] = deviation # intensityS_r[ia] = coeffs_r['S'].intensity() # intensityS_r_half[ia] = coeffs_r_half['S'].intensity() # intensityS_t[ia] = coeffs_t['S'].intensity() # print(">>>>>>>>>>", coeffs_r['S'].complexAmplitude() , coeffs_rr.complexAmplitude() ) # plot results print(r, r.shape) from srxraylib.plot.gol import plot # plot(1e6 * deviations, numpy.abs(r)**2, # 1e6 * deviations, numpy.abs(t)**2, # ) # plot(1e6 * deviations, numpy.abs(r)**2, 1e6 * deviations, numpy.abs(r+r*t*t/(1-r*r))**2, 1e6 * deviations, numpy.abs(r2um) ** 2, 1e6 * deviations, numpy.abs(r2um) ** 2 - numpy.abs(r+r*t*t/(1-r*r))**2, legend=['r','r2','r 2um','r 2 um - r2'] )