Source code for geom.classes.input_class

from geom.classes import parameters
from geom.functions import general, output

[docs] class input_class: """ Manages user-defined parameters for geometric transformations and structure generation. This class stores user inputs related to translation, rotation, structure creation, and other transformations for metal nanoparticles and graphene structures. Attributes: - Transformation Flags: Enable operations such as translation, rotation, mirroring, and structure generation. - Geometry Files: Stores input filenames for molecular structures. - Translation & Rotation: Contains direction, distances, angles, and axis information. - Structure Generation: Flags and parameters for generating different nanostructures. - Miscellaneous: Handles alloy composition, verbosity settings, and file extensions. Notes: - The full list of attributes is initialized in `__init__()`. - Methods validate inputs, read data, and apply transformations. """ def __init__(self): """ Initializes input parameters for geometric transformations and structure generation. Attributes Initialized: - Flags for operations (translation, rotation, mirroring, geometry creation). - File handling (input geometry, output file names, temporary directories). - Geometric parameters (distances, angles, lattice properties). - Structure-specific settings (graphene edge type, core-shell configuration, alloy composition). """ # -- RDKit options
[docs] self.rdkit = False
[docs] self.rdkit_visualize = False
[docs] self.rdkit_visualize_2d = False
[docs] self.rdkit_visualize_3d = False
[docs] self.rdkit_bw = False
[docs] self.rdkit_match = False
[docs] self.rdkit_abbreviations = False
[docs] self.rdkit_file_conversion = False
[docs] self.rdkit_opt = False
[docs] self.rdkit_conformers = False
[docs] self.stereo_annotations = False
[docs] self.atom_index = False
[docs] self.remove_H = False
[docs] self.check_aromaticity = False
[docs] self.match_smiles = ''
[docs] self.rdkit_mol_file = ''
[docs] self.rdkit_mol_file_extension = ''
[docs] self.rdkit_force_field = ''
[docs] self.rdkit_output_file = ''
[docs] self.rdkit_confs_ext = '.pdb'
[docs] self.rdkit_max_iters = 200
[docs] self.rdkit_confs = 50
[docs] self.rdkit_confs_prune_rms = 0.30
# -- Small tasks
[docs] self.small_tasks = False
# -- Translate
[docs] self.translate = False
[docs] self.translate_controlled_distance = False
[docs] self.translate_1 = False
[docs] self.translate_center = False
[docs] self.move_geom_to_000 = False
[docs] self.move_geom_1_to_000 = False
[docs] self.move_geom_2_to_000 = False
[docs] self.distances = []
[docs] self.dir_factor = []
[docs] self.file_geom2_translated = ''
[docs] self.distances_input = ''
[docs] self.geom_file = ''
[docs] self.geom1_file = ''
[docs] self.geom2_file = ''
[docs] self.dir_axis_input = ''
[docs] self.origin_CM = ''
[docs] self.origin_CM_1 = ''
[docs] self.origin_CM_2 = ''
[docs] self.direction = 1.0
[docs] self.dimer_distance = 0.0
# -- Minimum distance
[docs] self.min_dist = False
# -- Rotate
[docs] self.rotate = False
[docs] self.rotate_angles = False
[docs] self.rotate_1 = False
[docs] self.angles = []
[docs] self.angles_input = ''
[docs] self.file_geom_rotated = ''
[docs] self.angle = 0.0
# -- Geometrical center
[docs] self.geom_center = False
# -- Specular geometry
[docs] self.geom_specular = False
# -- Generate structure geometry
[docs] self.create_dimer = False
[docs] self.create_bowtie = False
[docs] self.create_geom = False
[docs] self.create_ase_bulk = False
[docs] self.gen_3d_mesh = False
[docs] self.gen_3d_mesh_sphere = False
[docs] self.gen_3d_mesh_rod = False
[docs] self.gen_graphene = False
[docs] self.gen_core_shell = False
[docs] self.gen_sphere = False
[docs] self.gen_sphere_core_shell = False
[docs] self.gen_rod = False
[docs] self.gen_rod_core_shell = False
[docs] self.gen_tip = False
[docs] self.gen_cone = False
[docs] self.gen_icosahedra = False
[docs] self.gen_cto = False
[docs] self.gen_idh = False
[docs] self.gen_pyramid = False
[docs] self.gen_pentpyramid = False
[docs] self.gen_microscope = False
[docs] self.gen_bipyramid = False
[docs] self.gen_pencil = False
[docs] self.gen_pentbipyramid = False
[docs] self.pentbipyramid_type = ''
[docs] self.alloy = False
[docs] self.mesh_size = 1.0
[docs] self.alloy_perc = 0.0
[docs] self.elliptic_parabola_a = 1.0 # Modifies stepness along x
[docs] self.elliptic_parabola_b = 1.0 # Modifies stepness along y
[docs] self.elliptic_parabola_c = 0.0 # Fixed for xy parabolloid
[docs] self.z_min = 0.0
[docs] self.z_max = 0.0
[docs] self.z_max_paraboloid = 0.0
[docs] self.z_max_pyramid = 0.0
[docs] self.rod_length = 0.0
[docs] self.rod_length_in = 0.0
[docs] self.rod_length_out = 0.0
[docs] self.rod_width = 0.0
[docs] self.rod_width_in = 0.0
[docs] self.rod_width_out = 0.0
[docs] self.bipyramid_width = 0.0
[docs] self.bipyramid_length = 0.0
[docs] self.side_length = 0.0
[docs] self.base_width = 0.0
[docs] self.radius = 0.0
[docs] self.radius_in = 0.0
[docs] self.radius_out = 0.0
[docs] self.X_length = 0.0
[docs] self.Y_length = 0.0
[docs] self.sphere_center = [0.0,0.0,0.0]
[docs] self.xyz_output = ''
[docs] self.mesh_output = ''
[docs] self.tmp_folder = ''
[docs] self.alloy_string = ''
[docs] self.atomtype = ''
[docs] self.atomtype_in = ''
[docs] self.atomtype_out = ''
[docs] self.atomtypes_alloys = ['ag','au']
[docs] self.atomtypes_core_shell = ['ag','au']
[docs] self.axes = ["x","y","z"]
[docs] self.graphene_structures = ["rib","disk","ring","triangle"]
[docs] self.graphene_structure = ""
[docs] self.graphene_edge_types = ["armchair","zigzag"]
[docs] self.graphene_edge_type = ""
# -- Merge geometries
[docs] self.merge = False
[docs] self.merge_cutoff = 0.0
# -- Verbose
[docs] self.verbose = False
[docs] self.verbose_inp = ''
# -------------------------------- # # ------- Check input case ------- #
[docs] def check_input_case(self): """ Validates and checks input requirements for selected operations. Returns: None: Performs necessary checks and raises errors if conditions are not met. Notes: - Ensures input files exist before processing. - Checks file extensions for validity. - Validates direction axis input. - Ensures selected operations are correctly configured. """ if (self.translate_controlled_distance): general.check_file_exists(self.distances_input) self.read_input(what='distances') general.check_file_exists(self.geom1_file) general.check_file_exists(self.geom2_file) general.check_file_extension(self.geom1_file,'.xyz') general.check_file_extension(self.geom2_file,'.xyz') general.check_dir_axis(self) elif (self.translate_1): general.check_file_exists(self.geom_file) general.check_file_extension(self.geom_file,'.xyz') general.check_dir_axis(self) elif (self.rotate_angles): general.check_file_exists(self.angles_input) self.read_input(what='angles') general.check_file_exists(self.geom_file) general.check_file_extension(self.geom_file,'.xyz') general.check_dir_axis(self) elif (self.rotate_1): general.check_file_exists(self.geom_file) general.check_file_extension(self.geom_file,'.xyz') general.check_dir_axis(self) elif (self.min_dist): general.check_file_exists(self.geom1_file) general.check_file_exists(self.geom2_file) general.check_file_extension(self.geom1_file,'.xyz') general.check_file_extension(self.geom2_file,'.xyz') elif (self.merge): general.check_file_exists(self.geom1_file) general.check_file_exists(self.geom2_file) general.check_file_extension(self.geom1_file,'.xyz') general.check_file_extension(self.geom2_file,'.xyz') elif (self.geom_center): general.check_file_exists(self.geom_file) general.check_file_extension(self.geom_file,'.xyz') elif (self.geom_specular): general.check_file_exists(self.geom_file) general.check_file_extension(self.geom_file,'.xyz') elif (self.rdkit): general.check_file_exists(self.rdkit_mol_file) # Extract parameters to check extension param = parameters.parameters() general.check_file_extension_rdkit(self.rdkit_mol_file, param.rdkit_file_extensions) if (self.rdkit_file_conversion): general.check_file_extension_rdkit(self.rdkit_output_file, param.rdkit_file_extensions) general.check_equal_extensions(self.rdkit_mol_file_extension, self.rdkit_output_file) if (self.rdkit_opt): general.check_accepted_parameters(self.rdkit_force_field, param.rdkit_force_fields, label='Force field') general.check_accepted_parameters(self.rdkit_output_file[-4:], param.rdkit_file_extensions_opt, label='Optimization saved to file extension') elif (self.create_geom): if (not self.gen_graphene and not self.gen_sphere and not self.gen_sphere_core_shell and not self.gen_rod and not self.gen_rod_core_shell and not self.gen_tip and not self.gen_pyramid and not self.gen_pentpyramid and not self.gen_cone and not self.gen_microscope and not self.gen_icosahedra and not self.gen_cto and not self.gen_idh and not self.gen_3d_mesh_sphere and not self.gen_3d_mesh_rod and not self.gen_bipyramid and not self.gen_pencil and not self.gen_pentbipyramid): output.error("Create geom option not recognised.") if self.create_ase_bulk: general.check_file_exists(self.geom_file) general.check_file_extension(self.geom_file,'.xyz')
# ------------------------------------------- # # ------- Read distances/angles input ------- #
[docs] def read_input(self,what): """ Reads an input file containing distances or angles. Args: what (str): Specifies whether to read 'distances' or 'angles'. Returns: None: Populates the respective list attribute (`self.distances` or `self.angles`). Raises: RuntimeError: If a blank line or multiple values are found in a single line. Notes: - Reads a file line by line and converts values to floats. - Ensures valid input formatting before processing. """ if (what=='distances'): with open(self.distances_input) as infile: for line in infile: if len(line.split()) == 0: output.error(f'blank line found in distances input file "{self.distances_input}"') if len(line.split()) > 1: output.error(f'more than one distance found in a single line of input file "{self.distances_input}"') self.distances.append(float(line.split()[0])) elif (what=='angles'): with open(self.angles_input) as infile: for line in infile: if len(line.split()) == 0: output.error(f'blank line found in angles input file "{self.angles_input}"') if len(line.split()) > 1: output.error(f'more than one angle found in a single line of input file "{self.angles_input}"') self.angles.append(float(line.split()[0]))
# ---------------------------------------- # # ------- Change translation sense ------- #
[docs] def change_trans_sense(self): """ Reverses the direction factor for translations. Returns: input_class: The modified `input_class` instance with updated `dir_factor`. Notes: - Multiplies all direction factors by -1. - Used to invert translation direction dynamically. """ self.dir_factor = [-x for x in self.dir_factor] return(self)