How to generate adsorption complexes¶
In heteregeneous catalysis, locating adsorption sites and placing adsorbates on
those sites can be a tedious task. For this purpose, the ccu.adsorption
defines several utilities for working with adsorption complexes. Namely, the
generate_complexes() function can be
used to generate adsorption complexes from a surface structure.
Preparing the structure¶
generate_complexes() can work with any
Atoms object. However, currently, the function requires
that three atoms are appropriately tagged. In particular, two atoms must
possess tags equal to 1 and one atom must have a tag equal to 2.
generate_complexes() will then generate
adsorption sites centered on each of the tagged atoms as well as the midpoint
between each pair of tagged atom and the centroid of the three tagged atoms.
For example, if you are working with a \(3 \times 3 \times 1\) supercell
of the Cu(100) surface,
from ase.build import fcc100
cu100 = fcc100("Cu", (3 , 3, 1))
you could tag the central atom with the nubmer 2 and two adjacent atoms with the number 1.
tags = [0] * len(cu100)
tags[1] = tags[3] = 1
tags[4] = 2
cu100.set_tags(tags)
Note
If the atoms tagged with 1 have the same chemical symbol (as is the case
here), only one set of adsorbate complexes will be generated by default.
This behaviour can be changed setting the symmetric parameter to False.
Generating complexes¶
Once your structure is correctly prepared, then you can simply call
generate_complexes() with your
structure and the desired adsorbate (CO in this case).
from ccu.adsorption.complexes import generate_complexes
complexes = generate_complexes(adsorbate="CO", structure=cu100)
complexes[0].edit()
The first adsorption complex returned by
generate_complexes()
for a Cu(100) surface.¶
Adsorbate selection¶
ccu recognizes reaction intermediates for the carbon dioxide reduction
reaction (CO2RR_ADSORBATES), oxygen
evolution/reduction reaction
(ORR_ADSORBATES), nitrate reduction
reaction (NRR_ADSORBATES), and hydrogen
evolution reaction
(HER_ADSORBATES). For a complete list of
these intermediates inspect the
ALL_ADSORBATES dictionary.
>>> from ccu.adsorption.adsorbates import ALL_ADSORBATES
>>> list(ALL_ADSORBATES)
['CO2', 'COOH_CIS', 'COOH_TRANS', 'COOH', 'OCHO', ...]
In addition, any Atoms object, string corresponding to a
molecule retrievable by the ASE function ase.build.molecule(),
or path pointing to a file readable by ase.io.read() can be
passed as the adsorbate argument to
generate_complexes().
Modifying which adsorption complexes are returned¶
generate_complexes() can alter the
surface-adsorbate separation, use atomic indices to center adsorbates,
and return fewer/additional complexes depending on the symmetry of the
adsorbate. For example, by modifying the previous example, we can generate
complexes with a minimum surface-adsorbate separation of only 1 Å (the default
is 1.8 Å) centered on the C atom of CO, include vertical orientations, and
ignore orientations in which the C and O atom are exchanged with one another.
from ccu.adsorption.adsorbates import get_adsorbate
co = get_adsorbate("CO")
co.info["special_centers"] = [next(a.index for a in co if a.symbol == "C")]
complexes = generate_complexes(
adsorbate=co,
structure=cu100,
separation=1.0,
special_centers=True,
symmetric=True,
vertical=True,
)
Identifying adsorbate complexes¶
The structures returned by
generate_complexes() will have
additional metadata that can be used to identify the complexes. In particular,
the info dictionary of the Atoms object will contain the
following keys:
"adsorbate"the name of the adsorbate placed on the structure (e.g.,
"CO")"site"the name of the site on which the adsorbate lies in the complex (e.g.,
"on Cu linker")"orientation"the orientation of the adsorbate (e.g.,
"colinear with Cu 1")
This metadata can then be used to identify specific adsorption complexes,
for example, if one wanted to programmatically generate free energy diagrams
without having to manually inspect each Atoms object to determine
which adsorbate is present in the complex.
Tip
In use-cases, where multiple different surfaces are used, it is recommended
to include the surface name as metadata in the Atoms.info dictionary.