Coverage for /Users/Newville/Codes/xraylarch/larch/xsw/multilayer_film.py: 0%
73 statements
« prev ^ index » next coverage.py v7.3.2, created at 2023-11-09 10:08 -0600
« prev ^ index » next coverage.py v7.3.2, created at 2023-11-09 10:08 -0600
1"""
2parses multilayer film structure as input, like Si/Cr/Pt for Cr/Pt on Si-substrate
3sends lists for reflectivity calculation
5# 9/24/2010 Yong Choi
7adapted for Larch, M. Newville
8"""
10def letters_between(text, strl, strr):
11 """finds letters in text between strl and strr
12 returns list of tuples (string, pos of strl, and pos of strr)
13 """
14 mid = ''
15 out = []
16 left = None
17 for ii, letter in enumerate(text):
18 if letter == strl:
19 left = ii
20 # second to last letter
21 if (left == len(text)-2) or (left == len(text)-3):
22 mid = text[left+1:]
23 out.append((mid, left, len(text)-1))
24 left = None
25 if left is not None and letter == strr:
26 mid = text[left+1: ii]
27 out.append((mid, left, ii))
28 left = None
29 return out
31class FilmLayer:
32 """single layer -- composition, density, thickness, roughness"""
33 def __init__(self, composition='Si', density=1, thickness=1,
34 roughness=1, tag='film'):
35 self.tag = tag
36 self.composition = composition
37 self.density = density # g/cc
38 self.relden = thickness # relative density
39 self.thickness = thickness # layer thickness
40 self.roughness = roughness # layer roughness
42class Film:
43 """Multilayer Film"""
44 def __init__(self, film_structure='Si/Cr(50)/Pt(200)'):
45 self.film_structure = film_structure
46 self.layer_sequence = film_structure
47 self.layers = []
49 def get_structure(self):
50 # expand layer structure
51 self.layer_sequence = self.expand_sequence(self.film_structure)
52 for layer in self.layer_sequence.split('/'):
53 tag='film'
54 words = layer.split('(')
55 material = words[0]
56 if len(words)==1:
57 tag, thickness = 'substrate', '100000.'
58 else:
59 tag, thickness = 'film', words[1][:-1] # remove ')'
60 self.layers.append(FilmLayer(composition=material,
61 thickness=thickness, tag=tag))
62 # add a vacuum layer on top
63 self.layers.append(FilmLayer(composition='He', density=1e-10,
64 thickness=0, tag='vacuum'))
66 def reverse_structure(self):
67 self.layers.reverse()
69 def expand_sequence(self, sequence):
70 fullname = sequence[:]
71 repeats = letters_between(fullname, '[', ']')
72 factors = letters_between(fullname, 'x', '/')
73 for nn in range(len(repeats)):
74 repeats = letters_between(fullname, '[', ']')
75 factors = letters_between(fullname, 'x', '/')
76 (text1, posL1, posR1) = repeats[0]
77 (num2, posL2, posR2) = factors[0]
78 pre=fullname[:posL1]
79 center=''
80 for ix in range(0, int(num2)):
81 center=center+text1+'/'
82 post = fullname[posR2+1:]
83 if post == '':
84 center = center[:-1]
85 fullname = pre+center+post
86 return fullname
88def test(structure):
89 film=Film(structure)
90 film.get_structure()
91 print( '--> ', film.film_structure)
92 for item in film.layers:
93 print( item.composition, item.thickness, item.density,\
94 item.roughness, item.tag)
96def testall():
97 test('Si/Ta(10)/[Pt(20)/Cr(30)]x3/Au(40)')
98 test('Si/Nd(10)/[Pd(20)/Co(30)]x3/Ag(40)/[Pt(22)/Fe(33)]x2/Al(10)')
99 test('Si/Nd(10)/[Pd(20)/Co(30)]x3/Ag(40)/[Pt(22)/Fe(33)]x10')
100 test('Si/Cr(50)/[Pt(40)/Fe(20)]x10')
102if __name__ == '__main__':
103 testall()