def getLa(self, energy, NumLayer=1.0): # emitted fluorescence trasmission attenuation up to top surface transmitted=1.0 temp=f1f2.get_delta(self.composition1, self.density1, energy) # energy is for fluorescence self.delta1 = temp[0] self.beta1 = temp[1] self.la1 = temp[4] # in cm, temp[4] instead of temp[2], using total instead of photoelectric # absorption length in cm at emitted fluorescence energy # temp[3]: atomic number density of the first element in atoms/cc temp=f1f2.get_delta(self.composition2, self.density2, energy) # energy is for fluorescence self.delta2 = temp[0] self.beta2 = temp[1] self.la2 = temp[4] # absorption length in cm at emitted fluorescence energy # in cm, temp[4] instead of temp[2], using total instead of photoelectric angle_exit = (math.pi/2.0 - self.angle) # becomes 90 at a small incident angle for (ii, depth) in enumerate(self.depths): if self.depths[ii]<self.thickness1: # top layer transmitted=math.exp(-depth/math.sin(angle_exit)*NumLayer/self.la1) else: # bottom layer transmitted2 = math.exp(-(depth-self.thickness1)/math.sin(angle_exit)*NumLayer/self.la2) transmitted1 = math.exp(-self.thickness1/math.sin(angle_exit)*NumLayer/self.la1) transmitted = transmitted2*transmitted1 self.trans[ii] = transmitted self.absrp[ii] = 1.0 - transmitted scale = 0.0; scale1=0.0; scale2=0.0 for (ii,trans) in enumerate(self.trans): scale = scale + trans*self.inten0[ii]*self.factors[ii] if self.depths[ii]<self.thickness1: scale1 = scale1 + trans*self.inten0[ii]*1.0 else: # if thickness2 is different from thickness1, weight differently scale2 = scale2 + trans*self.inten0[ii]*(self.thickness2/self.thickness1) # scale, scale1, scale2: emitted fluorescence transmission and depth profile self.scale = scale # sum of (trans*factors) for nonsubstrate FY self.scale1 = scale1 # sum of (trans*factors) for substrate FY. factors=1, top layer self.scale2 = scale2 # sum of (trans*factors) for substrate FY. factors=pre, bttom layer
def getPenetration(self, energy0): # incident x-ray penetration(attenuation) # refraction at air/top layer interface temp=f1f2.get_delta(self.composition1, self.density1, energy0) # energy0: incident x-ray energy delta1=temp[0]; beta1=temp[1] la1=temp[4] # in cm, temp[4] instead of temp[2], using total instead of photoelectric self.la1=la1 # absorption length in microns at incident x-ray energy angle_critical1 = (2.0*delta1)**(0.5) # in radian, critical angle for total external reflection if angle_critical1>=self.angle: # below critical angle, the corrected should be zero. angle_corrected1=1.0e-15 # a smaller number instead of zero else: # above critical angle angle_corrected1 = (self.angle**2.0 - angle_critical1**2.0)**(0.5) # in radian # refraction at top/bottom layers interface temp=f1f2.get_delta(self.composition2, self.density2, energy0) # energy0: incident x-ray energy delta2=temp[0]; beta2=temp[1]; la2=temp[4] # in cm, temp[4] instead of temp[2], using total instead of photoelectric self.la2=la2 # absorption length in cm at incident x-ray energy angle_corrected2 = ( 2.0-(1.0-delta1)/(1.0-delta2)*(2.0-angle_corrected1**2) )**0.5 # using Snell's law, assume beta effect not ignificant, in radian for (ii, depth) in enumerate(self.depths): if self.depths[ii]<self.thickness1: # top layer beampath = depth/math.sin(angle_corrected1) # in cm inten0 = math.exp(-beampath/la1) # attenuated incident beam intensity at depths else: # bottom layer beampath1 = self.thickness1/math.sin(angle_corrected1) beampath2 = (depth-self.thickness1)/math.sin(angle_corrected2) inten0 = math.exp(-beampath1/la1)*math.exp(-beampath2/la2) self.inten0[ii] = inten0 # incident x-ray attenuation
def getLa(self, energy, NumLayer=1.0): # get absorption legnth for incident x-ray, NumLayer for multiple layers temp=f1f2.get_delta(self.composition, self.density, energy) # returns delta, beta, la_photoE, Nat, la_total self.delta=temp[0]; self.beta=temp[1] self.la=temp[4] # temp[4] (total) instead of temp[2] (photoelectric) if NumLayer<0: NumLayer=0 # Number of layers cannot be less than zero self.trans=math.exp(-self.thickness*NumLayer/self.la) #la attenuation length cm, NumLayer for multiple layers self.absrp=1-self.trans
def get_index(self, energy=8370.0, indexNat=0): # x-ray energy in eV, relative density temp=readf1f2a.get_delta(self.composition, self.density*self.relden, energy, indexNat) # used to be fluo self.delta=temp[0] self.beta=temp[1] self.la=temp[2] # in cm, self.Nat=temp[3] self.trans=math.exp(-self.thickness*1e8/self.la) #la attenuation length cm, NumLayer for multiple layers self.absrp=1.0-self.trans
def OnSimulate(self, event): reload(SimpleParratt) # --- Retrive values from panel -------------- # self.Text1 text=self.Text1.GetValue() eV0=float(text) eV0_min=500 if eV0<=eV0_min: eV0=eV0_min+10. # self.Text2 film_mat=self.Text2.GetValue() # self.Text3 text=self.Text3.GetValue() film_thick=float(text) # self.Text4 text=self.Text4.GetValue() film_den=float(text) # self.Text5 text=self.Text5.GetValue() film_roughness=float(text) # self.Text6 subs_mat=self.Text6.GetValue() # self.Text7 text=self.Text7.GetValue() subs_den=float(text) # self.cb2 text=self.cb2.GetValue() use_Cr=0 if text=='Yes': use_Cr=1 # self.cb1 text=self.cb1.GetValue() xUnit='m rad' xUnit=text # self.cb0 text=self.cb0.GetValue() use_Log=False if text=='Yes': use_Log=True if use_Cr==1: NumLayers=2 else: NumLayers=1 # --- make lists as reflectivity calculation input ---------- out=readf1f2a.get_delta(film_mat, film_den, eV0) # used to be fluo. delta_film=out[0] la_film=out[2]*10000. # absorption length in cm, convert to microns thc_film=(2.*delta_film)**(0.5)*180./math.pi print '%s %3.4f Degrees (%3.4f m radians)' % ('critical angle for film:', thc_film, thc_film*math.pi/180.*1000.) th_step=0.001 th_range=numpy.arange(0.000, thc_film*3.0, th_step) # angular range depths=[0.0] # calculate efield intensity at air/film interface layer_mat=[]; layer_thick=[]; layer_den=[]; layer_rough=[]; layer_tag=[] # air layer_mat.append('He') layer_thick.append(0.0) # in Angstroms #layer_den.append(0.0013) # in g/cm^2, this will make layer_den.append(1e-10) # force this to be zero for vacuum layer_rough.append(film_roughness) # in Angstroms layer_tag.append('air') # layer name # film layer_mat.append(film_mat) layer_thick.append(film_thick) # in Angstroms layer_den.append(film_den) # in g/cm^2 layer_rough.append(film_roughness) # in Angstroms layer_tag.append(film_mat+'_layer') # Cr underlayer if use_Cr=1 if (NumLayers==2): layer_mat.append('Cr') layer_thick.append(50.0) layer_den.append(7.19) layer_rough.append(film_roughness) layer_tag.append('Cr_layer') # Substrate layer_mat.append(subs_mat) layer_thick.append(100000.) # not necessary layer_den.append(subs_den) layer_rough.append(film_roughness) # not necessary layer_tag.append(subs_mat+'_substrate') # print critical angle and absorption length for film and substrate print 'energy(eV) \t layer \t critical_angle(Deg.) \t absorption_length(micron) \n' print '%4.1f \t %s \t %4.4f \t %4.4f\n' % (eV0, film_mat, thc_film, la_film) out=readf1f2a.get_delta(subs_mat, subs_den, eV0) delta_subs=out[0] la_subs=out[2]*10000. # absorption length in cm, convert it to microns thc_subs=(2.*delta_subs)**(0.5)*180./math.pi print '%4.1f \t %s \t %4.4f \t %4.4f\n' % (eV0, subs_mat, thc_subs, la_subs) # --- call reflectivity in SimpleParratt.py ------------------ SimpleParratt.reflectivity(eV0, th_range, layer_mat, layer_thick, layer_den,\ layer_rough, layer_tag, depths) # --- Plot ---------------------------------------------------- if self.plot_on==1: print self.plot_on self.plot.Destroy() #self.frm.Destroy() frm = wx.Frame(self, 1, 'SimpleParratt.txt', size=(600,450)) self.data=[]; self.data0=[] th0=0; refl_half=1e6 inputfile='SimpleParratt.txt' f=open(inputfile) lines=f.readlines() self.xMin=1e6; self.xMax=-1e6; self.yMin=1e6; self.yMax=-1e6 for line in lines: if line.startswith('#'): continue words=line.split() if xUnit=='m rad': xx=float(words[0])*math.pi/180.0*1000. # convert deg to m rad if xUnit=='Deg': xx=float(words[0]) if xUnit=='qz': ang=float(words[0]) qz=4*math.pi*(eV0/1000.0/12.39842)*math.sin(ang*math.pi/180.0) xx=qz if self.xMin>xx: self.xMin=xx if self.xMax<=xx: self.xMax=xx yy=float(words[1]) if self.yMin>yy: self.yMin=yy if self.yMax<=yy: self.yMax=yy self.data.append((xx, yy)) self.data0.append((xx, 0.5)) temp=abs(yy-0.5) if temp<=refl_half: refl_half=temp th0=xx self.yMax=1.0 f.close() sample='' for (ii,item) in enumerate(layer_mat): if ii==0: sample='vacuum' else: sample=sample+'/'+item #title=str(eV0)+'eV, '+sample+', Refl.=0.5 at '+str(th0)+' m rad.' text0=' m rad.' text1='Incident angle (m rad)' if xUnit=='Deg': text0=' Deg' text1='Incident angle (Deg)' if xUnit=='qz': text0=' qz (1/Angstrom)' text1='qz (1/Agnstrom)' title='%4.1f, %s, %s %s %3.3f %s' % (eV0, 'eV', sample, 'Refl.=0.5 at', th0, text0) #------------------------------------------------ client = plot.PlotCanvas(frm) # 9/1/2010: enable zooming function, double click for default size client.SetEnableZoom(True) line = plot.PolyLine(self.data, legend='', colour='red', width=1) line0 = plot.PolyLine(self.data0, legend='', colour='black', width=0.5) gc = plot.PlotGraphics([line, line0], title, text1, 'Reflectivity') client.setLogScale((False,False)) if use_Log==True: client.setLogScale((False,True)) client.Draw(gc, xAxis= (self.xMin,self.xMax), yAxis= (self.yMin,self.yMax)) frm.Show(True) self.plot_on = 1 self.plot=frm
def OnSimulate1(self, event): # for arbitrary structure reload(SimpleParratt) # --- Retrive values from panel -------------- # self.Text1 text=self.Text1.GetValue() eV0=float(text) eV0_min=500 if eV0<=eV0_min: eV0=eV0_min+10. # self.Text2 film_mat=self.Text2.GetValue() # self.Text3 text=self.Text3.GetValue() film_thick=float(text) # self.Text4 text=self.Text4.GetValue() film_den=float(text) # self.Text5 text=self.Text5.GetValue() film_roughness=float(text) # self.Text6 subs_mat=self.Text6.GetValue() # self.Text7 text=self.Text7.GetValue() subs_den=float(text) # self.cb2 text=self.cb2.GetValue() use_Cr=0 if text=='Yes': use_Cr=1 # self.cb1 text=self.cb1.GetValue() xUnit='m rad' xUnit=text # self.cb0 text=self.cb0.GetValue() use_Log=False if text=='Yes': use_Log=True if use_Cr==1: NumLayers=2 else: NumLayers=1 LayerStructure0=self.Text8.GetValue() import read_FilmName film1=read_FilmName.Film(LayerStructure0) film1.get_structure() film1.reverse_structure() # reverse the layer order so that the top is vaccum layer_mat=[]; layer_thick=[]; layer_den=[]; layer_rough=[]; layer_tag=[] layer_thc=[]; layer_la=[] print 'energy(eV) \t layer \t th_c(Deg.) \t th_c(m rad) \t absorption_length(micron) \t density (g/cc)\n' for (ii, layer1) in enumerate(film1.LayerList): layer_mat.append(str(layer1.composition)) inputfile='NominalDensity.txt' f=open(inputfile) lines=f.readlines() out=1.0 for line in lines: if not line.startswith('#'): words=line.split(',') if layer1.composition==words[0]: temp=words[1].split() out=temp[0] layer1.density=float(out) f.close() layer_den.append(float(layer1.density)) layer_thick.append(float(layer1.thickness)) layer_rough.append(float(layer1.rms)) layer_tag.append(str(layer1.tag)) out=readf1f2a.get_delta(layer1.composition, layer1.density, eV0) la_layer=out[2]*10000.0 # absorption length in cm, convert to microns delta_layer=out[0] thc_layer=(2.*delta_layer)**(0.5)*180./math.pi # critical angle in deg if ii==1: thc_toplayer=thc_layer print '%4.1f \t %s \t %4.4f \t %4.4f \t %4.1f \t %s\n' % \ (eV0, layer1.composition+'-'+layer1.tag, thc_layer, thc_layer*math.pi/180.*1000., la_layer, layer1.density) th_step=0.001 th_range=numpy.arange(0.000, thc_toplayer*12.0, th_step) # angular range depths=[0.0] # calculate efield intensity at air/film interface #print layer_mat #print layer_thick #print layer_den #print layer_rough #layer_mat=['He', 'Cr', 'Si']; layer_thick=[0, 10., 10000]; layer_den=[1,1,1]; layer_rough=[1,1,1] # --- call reflectivity in SimpleParratt.py ------------------ SimpleParratt.reflectivity(eV0, th_range, layer_mat, layer_thick, layer_den,\ layer_rough, layer_tag, depths) # --- Plot ---------------------------------------------------- if self.plot_on==1: print self.plot_on self.plot.Destroy() #self.frm.Destroy() frm = wx.Frame(self, 1, 'SimpleParratt.txt', size=(600,450)) self.data=[]; self.data0=[] th0=0; refl_half=1e6 inputfile='SimpleParratt.txt' f=open(inputfile) lines=f.readlines() self.xMin=1e6; self.xMax=-1e6; self.yMin=1e6; self.yMax=-1e6 for line in lines: if line.startswith('#'): continue words=line.split() if xUnit=='m rad': xx=float(words[0])*math.pi/180.0*1000. # convert deg to m rad if xUnit=='Deg': xx=float(words[0]) if xUnit=='qz': ang=float(words[0]) qz=4*math.pi*(eV0/1000.0/12.39842)*math.sin(ang*math.pi/180.0) xx=qz if self.xMin>xx: self.xMin=xx if self.xMax<=xx: self.xMax=xx yy=float(words[1]) if self.yMin>yy: self.yMin=yy if self.yMax<=yy: self.yMax=yy self.data.append((xx, yy)) self.data0.append((xx, 0.5)) temp=abs(yy-0.5) if temp<=refl_half: refl_half=temp th0=xx self.yMax=1.0 f.close() sample='' for (ii,item) in enumerate(layer_mat): if ii==0: sample='vacuum' else: sample=sample+'/'+item #title=str(eV0)+'eV, '+sample+', Refl.=0.5 at '+str(th0)+' m rad.' text0=' m rad.' text1='Incident angle (m rad)' if xUnit=='Deg': text0=' Deg' text1='Incident angle (Deg)' if xUnit=='qz': text0=' qz (1/Angstrom)' text1='qz (1/Agnstrom)' title='%4.1f, %s, %s %s %3.3f %s' % (eV0, 'eV', sample, 'Refl.=0.5 at', th0, text0) #------------------------------------------------ client = plot.PlotCanvas(frm) # 9/1/2010: enable zooming function, double click for default size client.SetEnableZoom(True) line = plot.PolyLine(self.data, legend='', colour='red', width=1) line0 = plot.PolyLine(self.data0, legend='', colour='black', width=0.5) gc = plot.PlotGraphics([line, line0], title, text1, 'Reflectivity') client.setLogScale((False,False)) if use_Log==True: client.setLogScale((False,True)) client.Draw(gc, xAxis= (self.xMin,self.xMax), yAxis= (self.yMin,self.yMax)) frm.Show(True) self.plot_on = 1 self.plot=frm
def OnSimulate1(self, event): # for arbitrary structure reload(SimpleParratt) # --- Retrive values from panel -------------- # self.Text1 text=self.Text1.GetValue() eV0=float(text) eV0_min=500 if eV0<=eV0_min: eV0=eV0_min+10. # self.Text2 film_mat=self.Text2.GetValue() # self.Text3 text=self.Text3.GetValue() film_thick=float(text) # self.Text4 text=self.Text4.GetValue() film_den=float(text) # self.Text5 text=self.Text5.GetValue() film_roughness=float(text) # self.Text6 subs_mat=self.Text6.GetValue() # self.Text7 text=self.Text7.GetValue() subs_den=float(text) # self.cb2 text=self.cb2.GetValue() use_Cr=0 if text=='Yes': use_Cr=1 # self.cb1 text=self.cb1.GetValue() xUnit='m rad' xUnit=text # self.cb0 text=self.cb0.GetValue() use_Log=False if text=='Yes': use_Log=True if use_Cr==1: NumLayers=2 else: NumLayers=1 LayerStructure0=self.Text8.GetValue() import read_FilmName film1=read_FilmName.Film(LayerStructure0) film1.get_structure() film1.reverse_structure() # reverse the layer order so that the top is vaccum layer_mat=[]; layer_thick=[]; layer_den=[]; layer_rough=[]; layer_tag=[] layer_thc=[]; layer_la=[] print('energy(eV) \t layer \t th_c(Deg.) \t th_c(m rad) \t absorption_length(micron) \t density (g/cc)\n') for (ii, layer1) in enumerate(film1.LayerList): layer_mat.append(str(layer1.composition)) inputfile='NominalDensity.txt' f=open(inputfile) lines=f.readlines() out=1.0 for line in lines: if not line.startswith('#'): words=line.split(',') if layer1.composition==words[0]: temp=words[1].split() out=temp[0] layer1.density=float(out) f.close() layer_den.append(float(layer1.density)) layer_thick.append(float(layer1.thickness)) layer_rough.append(float(layer1.rms)) layer_tag.append(str(layer1.tag)) out=readf1f2a.get_delta(layer1.composition, layer1.density, eV0) la_layer=out[2]*10000.0 # absorption length in cm, convert to microns delta_layer=out[0] thc_layer=(2.*delta_layer)**(0.5)*180./math.pi # critical angle in deg if ii==1: thc_toplayer=thc_layer print('%4.1f \t %s \t %4.4f \t %4.4f \t %4.1f \t %s\n' % \) (eV0, layer1.composition+'-'+layer1.tag, thc_layer, thc_layer*math.pi/180.*1000., la_layer, layer1.density)