131 lines
4.7 KiB
Python
131 lines
4.7 KiB
Python
# coding: utf8
|
|
|
|
from ase.build import bulk
|
|
import numpy as np
|
|
from msspec.calculator import MSSPEC, XRaySource
|
|
from msspec.utils import hemispherical_cluster, get_atom_index
|
|
|
|
def create_clusters(nplanes=6):
|
|
def get_AlN_tags_planes(side, emitter):
|
|
AlN = bulk('AlN', crystalstructure='wurtzite', a=3.11, c=4.975)
|
|
[atom.set('tag', i) for i, atom in enumerate(AlN)]
|
|
if side == 'Al':
|
|
AlN.rotate([0,0,1],[0,0,-1])
|
|
Al_planes = range(0, nplanes, 2)
|
|
N_planes = range(1, nplanes, 2)
|
|
else:
|
|
N_planes = range(0, nplanes, 2)
|
|
Al_planes = range(1, nplanes, 2)
|
|
if emitter == 'Al':
|
|
tags = [0, 2]
|
|
planes = Al_planes
|
|
else:
|
|
tags = [1, 3]
|
|
planes = N_planes
|
|
return AlN, tags, planes
|
|
|
|
clusters = []
|
|
for side in ('Al', 'N'):
|
|
for emitter in ('Al', 'N'):
|
|
AlN, tags, planes = get_AlN_tags_planes(side, emitter)
|
|
for emitter_tag in tags:
|
|
for emitter_plane in planes:
|
|
cluster = hemispherical_cluster(AlN,
|
|
emitter_tag=emitter_tag,
|
|
emitter_plane=emitter_plane,
|
|
planes=emitter_plane+2)
|
|
cluster.absorber = get_atom_index(cluster, 0, 0, 0)
|
|
cluster.info.update({
|
|
'emitter_plane': emitter_plane,
|
|
'emitter_tag' : emitter_tag,
|
|
'emitter' : emitter,
|
|
'side' : side,
|
|
})
|
|
clusters.append(cluster)
|
|
print("Added cluster {}-side, emitter {}(tag {:d}) in "
|
|
"plane #{:d}".format(side, emitter, emitter_tag,
|
|
emitter_plane))
|
|
return clusters
|
|
|
|
|
|
def compute(clusters, theta=np.arange(-20., 80., 1.), phi=0.):
|
|
data = None
|
|
for ic, cluster in enumerate(clusters):
|
|
# Retrieve info from cluster object
|
|
side = cluster.info['side']
|
|
emitter = cluster.info['emitter']
|
|
plane = cluster.info['emitter_plane']
|
|
tag = cluster.info['emitter_tag']
|
|
|
|
# Set the level and the kinetic energy
|
|
if emitter == 'Al':
|
|
level = '2p'
|
|
ke = 1407.
|
|
elif emitter == 'N':
|
|
level = '1s'
|
|
ke = 1083.
|
|
|
|
calc = MSSPEC(spectroscopy='PED', algorithm='expansion')
|
|
|
|
calc.source_parameters.energy = XRaySource.AL_KALPHA
|
|
calc.source_parameters.theta = -35
|
|
|
|
calc.detector_parameters.angular_acceptance = 4.
|
|
calc.detector_parameters.average_sampling = 'medium'
|
|
|
|
calc.calculation_parameters.scattering_order = max(1, min(4, plane))
|
|
calc.calculation_parameters.path_filtering = 'forward_scattering'
|
|
calc.calculation_parameters.off_cone_events = 1
|
|
[a.set('forward_angle', 30.) for a in cluster]
|
|
|
|
calc.set_atoms(cluster)
|
|
|
|
data = calc.get_theta_scan(level=level, theta=theta, phi=phi,
|
|
kinetic_energy=ke, data=data)
|
|
dset = data[-1]
|
|
dset.title = "\'{}\' side - {}({}) tag #{:d}, plane #{:d}".format(
|
|
side, emitter, level, tag, plane)
|
|
|
|
return data
|
|
|
|
|
|
def analysis(data):
|
|
tmp_data = {}
|
|
for dset in data:
|
|
info = dset.get_cluster().info
|
|
side = info['side']
|
|
emitter = info['emitter']
|
|
try:
|
|
key = '{}_{}'.format(side, emitter)
|
|
tmp_data[key] += dset.cross_section
|
|
except KeyError:
|
|
tmp_data[key] = dset.cross_section.copy()
|
|
|
|
tmp_data['theta'] = dset.theta.copy()
|
|
tmp_data['Al_side'] = tmp_data['Al_Al'] / tmp_data['Al_N']
|
|
tmp_data['N_side'] = tmp_data['N_Al'] / tmp_data['N_N']
|
|
|
|
# now add all columns
|
|
substrate_dset = data.add_dset('Total substrate signal')
|
|
substrate_dset.add_columns(**tmp_data)
|
|
|
|
view = substrate_dset.add_view('Ratios',
|
|
title=r'Al(2p)/N(1s) ratios on both polar '
|
|
r'sides of AlN in the (10$\bar{1}$0) '
|
|
r'azimuthal plane',
|
|
xlabel=r'$\Theta (\degree$)',
|
|
ylabel='Intenisty ratio')
|
|
view.select('theta', 'Al_side', legend='Al side',
|
|
where="theta >= 0 and theta <=70")
|
|
view.select('theta', 'N_side', legend='N side',
|
|
where="theta >= 0 and theta <=70")
|
|
view.set_plot_options(autoscale=True)
|
|
|
|
return data
|
|
|
|
|
|
clusters = create_clusters()
|
|
data = compute(clusters)
|
|
data = analysis(data)
|
|
data.view()
|