Open gihanpanapitiya opened 10 months ago
Do you know why we get different slabs for the same miller index?
There could be multiple slabs for a miller index because of different shifts and if the top and bottom aren't symmetric.
No. of layers should be the same though; let us know if you find otherwise.
I obtain slabs as below.
bulk = Bulk(bulk_atoms=slab_ats)
slabs = Slab.from_bulk_get_specific_millers(bulk = bulk, specific_millers=(0,0,1))
slab_ats is an ase.atoms.Atoms
object,
Atoms(symbols='Cu64', pbc=True, cell=[[10.21062183380127, 0.0, 0.0], [5.105310916900635, 8.842658042907715, 0.0], [0.0, 0.0, 32.25270462036133]], tags=..., constraint=FixAtoms(indices=[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47]), calculator=SinglePointCalculator(...))
which looks as below.
slabs
contain 4 slabs. They visualize as below.
So, only slab[2]
has 4 layers as that of the slab_ats
.
That definitely looks buggy, especially the gap between some of the layers.. Could you share the atoms object for slab_ats
so we can try debugging at our end?
@mshuaibii any thoughts?
@gihanpanapitiya Where did you create slab_ats
from? The Bulk
class expects a conventional unit cell to be supplied for slabs to be properly created. I suspect something weird is going on either here or here because of the slab being fed in as a bulk structure. If you can share the atoms object for slab_ats
directly or describe how to recreate it, I can look closer on my end.
Thanks! The issue can be reproduced using the following code.
from ocdata.core import Bulk, Slab
from ase.build import fcc111
slab_ats = fcc111('Cu', size=(4, 4, 4), vacuum=10.0)
bulk = Bulk(bulk_atoms=slab_ats)
slabs = Slab.from_bulk_get_specific_millers(bulk = bulk, specific_millers=(0,0,1))
I see. Yeah, it looks like you've created a 111 surface, and then are feeding that into the Slab creator, which is not the correct use case. You should feed in a bulk structure, as follows:
from ocdata.core import Bulk, Slab
bulk = Bulk(
bulk_id_from_db=12, # this corresponds to the Cu bulk structure.
bulk_db_path="/path/to/ocdata/databases/pkls/bulks.pkl"
)
slabs = Slab.from_bulk_get_specific_millers(bulk = bulk, specific_millers=(0,0,1))
If you are interested in other bulk structures, you can look for them in the following database - https://github.com/Open-Catalyst-Project/Open-Catalyst-Dataset/blob/main/ocdata/databases/pkls/bulks.pkl.
If we want to use a bulk not in /path/to/ocdata/databases/pkls/bulks.pkl
is there a particular way we should prepare our own bulk object so that it's compatible with Slab.from_bulk_get_specific_millers()
?
We would like to use our own slabs to find the heuristic placements. Is the method below a valid way to use AdsorbateSlabConfig
?
I am not very sure about step 2
and step 3
. Particularly about what values should be used for specific_millers
. Even though my Cu
slab has a 111
surface using (0,0,1)
for specific_millers
seems to produce structures that look correct.
from ocdata.core import Adsorbate, AdsorbateSlabConfig, Bulk, Slab
import ase.build as build
# step 1 - create the slab
ats = build.fcc111('Cu', (4, 4, 4))
ats.center(vacuum=13.0, axis=2)
# step 2 - create the bulk
bulk = Bulk(bulk_atoms=ats)
# step 3 - create the Slab object
slabs = Slab.from_bulk_get_specific_millers(bulk=bulk, specific_millers=(0,0,1))
# step 4 - find the heuristic placements
adsorbate_smiles = "*CO"
adsorbate = Adsorbate(adsorbate_smiles_from_db=adsorbate_smiles,
adsorbate_db_path = "../Open-Catalyst-Dataset/ocdata/databases/pkls/adsorbates.pkl")
heuristic_adslabs = AdsorbateSlabConfig(slabs[0], adsorbate, mode="heuristic")
I am following the example at adsorbml_walkthrough.ipynb. Do you know why we get different slabs for the same miller index? I want to select the slab that has the same number of layers as that of the bulk. Is there a way to do this?