diff --git a/src/py/mat3ra/made/tools/build/defect/builders.py b/src/py/mat3ra/made/tools/build/defect/builders.py index 95f7f9a5..8da09313 100644 --- a/src/py/mat3ra/made/tools/build/defect/builders.py +++ b/src/py/mat3ra/made/tools/build/defect/builders.py @@ -44,6 +44,7 @@ PointDefectPairConfiguration, ) from .factories import DefectBuilderFactory +from pymatgen.analysis.adsorption import AdsorbateSiteFinder class PointDefectBuilderParameters(BaseModel): @@ -434,6 +435,36 @@ def create_adatom( return self.merge_slab_and_defect(new_material, only_adatom_material) +class HollowSiteAdatomSlabDefectBuilder(AdatomSlabDefectBuilder): + """ + Builder class for generating adatoms at hollow sites. + + The adatom is placed at the hollow site closest to the specified position on the surface of the material. + + """ + + def _calculate_coordinate_from_position_and_distance( + self, material: Material, position_on_surface: List[float], distance_z: float + ) -> List[float]: + coordinate = super()._calculate_coordinate_from_position_and_distance(material, position_on_surface, distance_z) + pymatgen_structure = to_pymatgen(material) + asf = AdsorbateSiteFinder(pymatgen_structure) + + sites = asf.find_adsorption_sites( + positions=[ + "hollow", + ], + no_obtuse_hollow=False, + ) + hollow_coordinates = [array.tolist() for array in sites["hollow"]] + print(hollow_coordinates) + closest_hollow_site_coordinate = min( + hollow_coordinates, key=lambda x: np.linalg.norm(np.array(x) - np.array(coordinate)) + ) + print(closest_hollow_site_coordinate[0:2] + [coordinate[2]]) + return closest_hollow_site_coordinate[0:2] + [coordinate[2]] + + class DefectPairBuilder(DefectBuilder): def create_defect_pair( self, diff --git a/src/py/mat3ra/made/tools/build/defect/enums.py b/src/py/mat3ra/made/tools/build/defect/enums.py index bdc22279..014e6f58 100644 --- a/src/py/mat3ra/made/tools/build/defect/enums.py +++ b/src/py/mat3ra/made/tools/build/defect/enums.py @@ -26,6 +26,12 @@ class AtomPlacementMethodEnum(str, Enum): EQUIDISTANT = "equidistant" # Places the atom at the existing or extrapolated crystal site closest to the given coordinate. CRYSTAL_SITE = "crystal_site" + # Places the atom at the hollow site of the surface (for HEX) + HOLLOW_SITE = "hollow" + # Places the atom at the bridge site of the surface (for HEX) + BRIDGE_SITE = "bridge" + # Places the atom at the on-top site of the surface (for HEX) + ON_TOP_SITE = "on_top" class CoordinatesShapeEnum(str, Enum):