Esempio n. 1
0
    def test_keys(self):
        """
        Test the edge case for tI.
        """
        import seekpath

        cell = [[4., 0., 0.], [0., 4., 0.], [0., 0., 4.]]
        positions = [[0., 0., 0.], [0.5, 0.5, 0.5]]
        atomic_numbers = [6, 6]

        system = (cell, positions, atomic_numbers)

        res = seekpath.get_explicit_k_path(system, recipe='hpkot')

        known_keys = set([
            'augmented_path', 'bravais_lattice', 'bravais_lattice_extended',
            'conv_lattice', 'conv_positions', 'conv_types',
            'explicit_kpoints_abs', 'explicit_kpoints_labels',
            'explicit_kpoints_linearcoord', 'explicit_kpoints_rel',
            'explicit_segments', 'has_inversion_symmetry',
            'inverse_primitive_transformation_matrix', 'path', 'point_coords',
            'primitive_lattice', 'primitive_positions',
            'primitive_transformation_matrix', 'primitive_types',
            'reciprocal_primitive_lattice', 'spacegroup_international',
            'spacegroup_number', 'volume_original_wrt_conv',
            'volume_original_wrt_prim'
        ])

        missing_known_keys = known_keys - set(res.keys())
        if missing_known_keys:
            raise AssertionError("Some keys are not returned from the "
                                 "get_explicit_k_path function: {}".format(
                                     ', '.join(missing_known_keys)))
Esempio n. 2
0
def _bands_from_force_constants(data: ForceConstants,
                                q_distance: Quantity,
                                insert_gamma: bool = True,
                                frequencies_only: bool = False,
                                **calc_modes_kwargs
                                ) -> Tuple[Union[QpointPhononModes,
                                                 QpointFrequencies],
                                           XTickLabels, SplitArgs]:
    structure = data.crystal.to_spglib_cell()
    bandpath = seekpath.get_explicit_k_path(
        structure,
        reference_distance=q_distance.to('1 / angstrom').magnitude)

    if insert_gamma:
        _insert_gamma(bandpath)

    x_tick_labels = _get_tick_labels(bandpath)
    split_args = {'indices': _get_break_points(bandpath)}

    print(
        "Computing phonon modes: {n_modes} modes across {n_qpts} q-points"
        .format(n_modes=(data.crystal.n_atoms * 3),
                n_qpts=len(bandpath["explicit_kpoints_rel"])))
    qpts = bandpath["explicit_kpoints_rel"]

    if frequencies_only:
        modes = data.calculate_qpoint_frequencies(qpts,
                                                  reduce_qpts=False,
                                                  **calc_modes_kwargs)
    else:
        modes = data.calculate_qpoint_phonon_modes(qpts,
                                                   reduce_qpts=False,
                                                   **calc_modes_kwargs)
    return modes, x_tick_labels, split_args
 def find_seekpath_data(self) -> None:
     """Get full information of seekpath band path. """
     self._seekpath_data = \
         seekpath.get_explicit_k_path(structure=self.cell,
                                      symprec=self.symprec,
                                      angle_tolerance=self.angle_tolerance,
                                      with_time_reversal=self.time_reversal,
                                      reference_distance=self.ref_distance)
     lattice = self._seekpath_data["primitive_lattice"]
     element_types = self._seekpath_data["primitive_types"]
     species = [Element.from_Z(i) for i in element_types]
     positions = self._seekpath_data["primitive_positions"]
     self._band_primitive = Structure(lattice, species, positions)
Esempio n. 4
0
 def get_bandstructure(self, reference_distance=0.2):
     import seekpath
     path = seekpath.get_explicit_k_path(
         self.get_cell(), reference_distance=reference_distance)
     kpath = path['explicit_kpoints_rel']
     explicit_labels = path['explicit_kpoints_labels']
     bands = []
     labels = []
     for segment in path['segments']:
         start_k, end_k = segment
         labels.append(explicit_labels[start_k])
         bands.append(kpath[start_k:end_k])
     labels.append(explicit_labels[-1])
     self.bands = bands
     self.labels = labels
Esempio n. 5
0
def structure_to_seekpath(structure: Structure,
                          time_reversal: bool = True,
                          ref_distance: float = BAND_REF_DIST,
                          recipe: str = 'hpkot',
                          threshold: float = 1e-7,
                          symprec: float = SYMMETRY_TOLERANCE,
                          angle_tolerance: float = ANGLE_TOL) -> dict:
    """
    Return the full information for the band path of the given Structure class
    object generated by seekpath.

    Args:
        structure (Structure):
            Pymatgen Structure class object
        time_reversal (bool):
            If the time reversal symmetry exists
        ref_distance (float):
            Distance for the k-point mesh.
        recipe (str):
            See docstrings of seekpath.
        threshold (float):
            To use to verify if we are in edge case (see seekpath).
        symprec (float):
            Distance tolerance in cartesian coordinates Unit is compatible with
            the cell.
        angle_tolerance (float):
            Angle tolerance used for symmetry analyzer.

    Return:
        Dict with some properties. See docstrings of seekpath.
    """
    cell = structure_to_spglib_cell(structure)
    res = seekpath.get_explicit_k_path(cell,
                                       with_time_reversal=time_reversal,
                                       reference_distance=ref_distance,
                                       recipe=recipe,
                                       threshold=threshold,
                                       symprec=symprec,
                                       angle_tolerance=angle_tolerance)

    # If numpy.allclose is too strict in pymatgen.core.lattice __eq__,
    # make almost_equal
    if structure.lattice != seekpath_to_hpkot_structure(res).lattice:
        logger.warning(
            "Given structure is modified to be compatible with HPKOT k-path.")

    return res
Esempio n. 6
0
    def _cell_change(self, change):
        system = (np.array(change['new']), np.array(self.positions),
                  np.array(self.numbers))
        res = seekpath.getpaths.get_path(system, with_time_reversal=False)

        real_lattice = res["primitive_lattice"]
        rec_lattice = np.array(
            seekpath.hpkot.tools.get_reciprocal_cell_rows(real_lattice))
        b1, b2, b3 = rec_lattice

        faces_data = get_BZ(b1=b1, b2=b2, b3=b3)

        response = {}
        response["faces_data"] = faces_data
        response["b1"] = b1.tolist()
        response["b2"] = b2.tolist()
        response["b3"] = b3.tolist()
        ## Convert to absolute
        response["kpoints"] = {
            k: (v[0] * b1 + v[1] * b2 + v[2] * b3).tolist()
            for k, v in res["point_coords"].items()
        }
        response["kpoints_rel"] = {
            k: [v[0], v[1], v[2]]
            for k, v in res["point_coords"].items()
        }
        response["path"] = res["path"]

        # It should use the same logic, so give the same cell as above
        res_explicit = seekpath.get_explicit_k_path(system,
                                                    with_time_reversal=False)
        for k in res_explicit:
            if k == "segments" or k.startswith("explicit_"):
                if isinstance(res_explicit[k], np.ndarray):
                    response[k] = res_explicit[k].tolist()
                else:
                    response[k] = res_explicit[k]

        if (np.sum(
                np.abs(
                    np.array(res_explicit["reciprocal_primitive_lattice"]) -
                    np.array(res["reciprocal_primitive_lattice"]))) > 1.0e-7):
            raise AssertionError("Got different reciprocal cells...")

        self.jsondata = response
        self.update_structure += 1
Esempio n. 7
0
    def test_keys(self):  # pylint: disable=no-self-use
        """
        Test the edge case for tI.
        """
        import seekpath

        cell = [[4.0, 0.0, 0.0], [0.0, 4.0, 0.0], [0.0, 0.0, 4.0]]
        positions = [[0.0, 0.0, 0.0], [0.5, 0.5, 0.5]]
        atomic_numbers = [6, 6]

        system = (cell, positions, atomic_numbers)

        res = seekpath.get_explicit_k_path(system, recipe="hpkot")

        known_keys = set([
            "augmented_path",
            "bravais_lattice",
            "bravais_lattice_extended",
            "conv_lattice",
            "conv_positions",
            "conv_types",
            "explicit_kpoints_abs",
            "explicit_kpoints_labels",
            "explicit_kpoints_linearcoord",
            "explicit_kpoints_rel",
            "explicit_segments",
            "has_inversion_symmetry",
            "inverse_primitive_transformation_matrix",
            "path",
            "point_coords",
            "primitive_lattice",
            "primitive_positions",
            "primitive_transformation_matrix",
            "primitive_types",
            "reciprocal_primitive_lattice",
            "spacegroup_international",
            "spacegroup_number",
            "volume_original_wrt_conv",
            "volume_original_wrt_prim",
        ])

        missing_known_keys = known_keys - set(res.keys())
        if missing_known_keys:
            raise AssertionError("Some keys are not returned from the "
                                 "get_explicit_k_path function: {}".format(
                                     ", ".join(missing_known_keys)))
Esempio n. 8
0
    def automatic_linemode(self, structure,num_kpts=16):
        all_kpath = seekpath.get_explicit_k_path((structure.lattice,
        structure.positions,structure.atoms))
        points = all_kpath['point_coords']
        path = all_kpath['path']
        kpoints,labels = [],[]
        for p in path:
            kpoints.append(points[p[0]])
            kpoints.append(points[p[1]])
            labels.append(p[0])
            labels.append(p[1])

        comment = 'Line_mode KPOINTS file, '+'num_kpts: '+str(num_kpts)
        self.comment = comment
        self._style = Kpoints.supported_modes.Line_mode
        self.coord_type = 'Reciprocal'
        self.kpts = kpoints
        self.labels = labels
        self.num_kpts = num_kpts
Esempio n. 9
0
def get_json_for_visualizer(cell, relcoords, atomic_numbers):
    system = (np.array(cell), np.array(relcoords), np.array(atomic_numbers))
    res = seekpath.hpkot.get_path(system, with_time_reversal=False)

    real_lattice = res['primitive_lattice']
    #rec_lattice = np.linalg.inv(real_lattice).T # Missing 2pi!
    rec_lattice = np.array(
        seekpath.hpkot.tools.get_reciprocal_cell_rows(real_lattice))
    b1, b2, b3 = rec_lattice

    faces_data = brillouinzone.get_BZ(b1=b1, b2=b2, b3=b3)

    response = {}
    response['faces_data'] = faces_data
    response['b1'] = b1.tolist()
    response['b2'] = b2.tolist()
    response['b3'] = b3.tolist()
    ## Convert to absolute
    response['kpoints'] = {
        k: (v[0] * b1 + v[1] * b2 + v[2] * b3).tolist()
        for k, v in res['point_coords'].items()
    }
    response['path'] = res['path']

    # It should use the same logic, so give the same cell as above
    res_explicit = seekpath.get_explicit_k_path(system,
                                                with_time_reversal=False)
    for k in res_explicit:
        if k == 'segments' or k.startswith('explicit_'):
            if isinstance(res_explicit[k], np.ndarray):
                response[k] = res_explicit[k].tolist()
            else:
                response[k] = res_explicit[k]

    if np.sum(
            np.abs(
                np.array(res_explicit['reciprocal_primitive_lattice']) -
                np.array(res['reciprocal_primitive_lattice']))) > 1.e-7:
        raise AssertionError("Got different reciprocal cells...")

    # Response for JS, and path_results
    return response, res
Esempio n. 10
0
def find_hpkot_primitive(structure: Structure,
                         symprec: float = SYMMETRY_TOLERANCE,
                         angle_tolerance: float = ANGLE_TOL
                         ) -> Structure:
    """
    Return a hpkot primitive unit cell.
    Args:
        structure (Structure):
            Pymatgen Structure class object
        symprec (float):
            Distance tolerance in cartesian coordinates Unit is compatible with
            the cell.
        angle_tolerance (float):
            Angle tolerance used for symmetry analyzer.
    """
    cell = structure_to_spglib_cell(structure)
    res = seekpath.get_explicit_k_path(structure=cell,
                                       symprec=symprec,
                                       angle_tolerance=angle_tolerance)

    return seekpath_to_hpkot_structure(res)
Esempio n. 11
0
def get_explicit_kpoints_path(structure, parameters):
    """
    Return the kpoint path for band structure (in scaled and absolute
    coordinates), given a crystal structure,
    using the paths proposed in the various publications (see description
    of the 'recipe' input parameter). The parameters are the same
    as get get_explicit_k_path in __init__, but here all structures are
    input and returned as AiiDA structures rather than tuples, and similarly
    k-points-related information as a AiiDA KpointsData class.

    :param structure: The AiiDA StructureData for which we want to obtain
        the suggested path.

    :param parameters: A dictionary whose key-value pairs are passed as
        additional kwargs to the ``seekpath.get_explicit_k_path`` function.

    :return: A dictionary with four nodes:

        - ``explicit_kpoints``: a KpointsData with the (explicit) kpoints
          (with labels set).

        - ``parameters``: a Dict, whose content is
          the same dictionary as returned by the ``seekpath.get_explicit_k_path`` function
          (see `seekpath documentation <https://seekpath.readthedocs.io/>`_),
          except that:

          - ``conv_lattice``, ``conv_positions``, ``conv_types``
            are removed and replaced by the ``conv_structure`` output node

          - ``primitive_lattice``, ``primitive_positions``, ``primitive_types``
            are removed and replaced by the `primitive_structure` output node

          - ``reciprocal_primitive_lattice``, ``explicit_kpoints_abs``,
            ``explicit_kpoints_rel`` and ``explicit_kpoints_labels`` are removed
            and replaced by the ``explicit_kpoints`` output node

        - ``primitive_structure``: A StructureData with the primitive structure

        - ``conv_structure``: A StructureData with the primitive structure
    """
    # pylint: disable=too-many-locals
    from aiida.tools.data.structure import spglib_tuple_to_structure, structure_to_spglib_tuple

    structure_tuple, kind_info, kinds = structure_to_spglib_tuple(structure)

    result = {}
    rawdict = seekpath.get_explicit_k_path(structure=structure_tuple,
                                           **parameters)

    # Replace primitive structure with AiiDA StructureData
    primitive_lattice = rawdict.pop('primitive_lattice')
    primitive_positions = rawdict.pop('primitive_positions')
    primitive_types = rawdict.pop('primitive_types')
    primitive_tuple = (primitive_lattice, primitive_positions, primitive_types)
    primitive_structure = spglib_tuple_to_structure(primitive_tuple, kind_info,
                                                    kinds)

    # Replace conv structure with AiiDA StructureData
    conv_lattice = rawdict.pop('conv_lattice')
    conv_positions = rawdict.pop('conv_positions')
    conv_types = rawdict.pop('conv_types')
    conv_tuple = (conv_lattice, conv_positions, conv_types)
    conv_structure = spglib_tuple_to_structure(conv_tuple, kind_info, kinds)

    # Remove reciprocal_primitive_lattice, recalculated by kpoints class
    rawdict.pop('reciprocal_primitive_lattice')
    kpoints_abs = rawdict.pop('explicit_kpoints_abs')
    kpoints_labels = rawdict.pop('explicit_kpoints_labels')

    # set_kpoints expects labels like [[0,'X'],[34,'L'],...], so generate it here skipping empty labels
    labels = [[idx, label] for idx, label in enumerate(kpoints_labels)
              if label]
    kpoints = KpointsData()
    kpoints.set_cell_from_structure(primitive_structure)
    kpoints.set_kpoints(kpoints_abs, cartesian=True, labels=labels)

    result['parameters'] = Dict(dict=rawdict)
    result['explicit_kpoints'] = kpoints
    result['primitive_structure'] = primitive_structure
    result['conv_structure'] = conv_structure

    return result
Esempio n. 12
0
def structure2input(structure, prefix, dk_path, dq_grid, pseudo_kind,
                    pseudo_dir, queue, rel):

    if pseudo_kind == "sg15":
        if rel:
            from sg15_rel import pseudo_dict, ecutwfc_dict, ecutrho_dict, valence_dict, atomwfc_dict
        else:
            from sg15 import pseudo_dict, ecutwfc_dict, ecutrho_dict, valence_dict, atomwfc_dict
    elif pseudo_kind == "pslibrary":
        if rel:
            from pslibrary_rel import pseudo_dict, ecutwfc_dict, ecutrho_dict, valence_dict, atomwfc_dict
        else:
            from pslibrary import pseudo_dict, ecutwfc_dict, ecutrho_dict, valence_dict, atomwfc_dict
    else:
        from sssp import pseudo_dict, ecutwfc_dict, ecutrho_dict, valence_dict, atomwfc_dict
    #
    # Band path and primitive lattice
    #
    frac_coord2 = numpy.array(structure.frac_coords)
    for ipos in range(len(frac_coord2)):
        for iaxis in range(3):
            coord3 = frac_coord2[ipos, iaxis] * 6.0
            if abs(round(coord3) - coord3) < 0.001:
                frac_coord2[ipos, iaxis] = float(round(coord3)) / 6.0
    #
    skp = seekpath.get_explicit_k_path(
        (structure.lattice.matrix, frac_coord2,
         [pymatgen.Element(str(spc)).number for spc in structure.species]),
        reference_distance=dk_path)
    #
    # Lattice information
    #
    bvec = skp["reciprocal_primitive_lattice"]
    atom = [str(get_el_sp(iat)) for iat in skp["primitive_types"]]
    typ = set(atom)
    #
    # WFC and Rho cutoff
    #
    ecutwfc = 0.0
    ecutrho = 0.0
    for ityp in typ:
        if ecutwfc < ecutwfc_dict[str(ityp)]:
            ecutwfc = ecutwfc_dict[str(ityp)]
        if ecutrho < ecutrho_dict[str(ityp)]:
            ecutrho = ecutrho_dict[str(ityp)]
    #
    # k and q grid
    #
    nq = numpy.zeros(3, numpy.int_)
    for ii in range(3):
        norm = numpy.sqrt(numpy.dot(bvec[ii][:], bvec[ii][:]))
        nq[ii] = round(norm / dq_grid)
        print(norm)
    print("Coarse grid : ", nq[0], nq[1], nq[2])
    #
    # Band path
    #
    print("Band path")
    for ipath in range(len(skp["path"])):
        start = skp["explicit_segments"][ipath][0]
        final = skp["explicit_segments"][ipath][1] - 1
        print("%5d %8s %10.5f %10.5f %10.5f %8s %10.5f %10.5f %10.5f" %
              (final - start + 1, skp["explicit_kpoints_labels"][start],
               skp["explicit_kpoints_rel"][start][0],
               skp["explicit_kpoints_rel"][start][1],
               skp["explicit_kpoints_rel"][start][2],
               skp["explicit_kpoints_labels"][final],
               skp["explicit_kpoints_rel"][final][0],
               skp["explicit_kpoints_rel"][final][1],
               skp["explicit_kpoints_rel"][final][2]))
    #
    # Number of electrons
    #
    nbnd = 0
    for iat in atom:
        nbnd += valence_dict[iat]
    if rel:
        nbnd *= 2
    #
    # Shell scripts
    #
    structure2 = pymatgen.Structure(skp["primitive_lattice"],
                                    skp["primitive_types"],
                                    skp["primitive_positions"])
    spg_analysis = SpacegroupAnalyzer(structure2)
    middle = spg_analysis.get_ir_reciprocal_mesh(mesh=(nq[0] * 2, nq[1] * 2,
                                                       nq[2] * 2),
                                                 is_shift=(0, 0, 0))
    dense = spg_analysis.get_ir_reciprocal_mesh(mesh=(nq[0] * 4, nq[1] * 4,
                                                      nq[2] * 4),
                                                is_shift=(0, 0, 0))
    print("Number of irreducible k : ", len(middle), len(dense))
    write_sh(len(middle), len(dense), len(skp["explicit_kpoints_rel"]), atom,
             prefix, atomwfc_dict, queue)
    #
    # rx.in, scf.in, nscf.in, band.in , nscf_w.in, nscf_r.in
    #
    write_pwx(prefix, skp, pseudo_dir, ecutwfc, ecutrho, pseudo_dict, nq, nbnd,
              rel)
    #
    # ph.in, elph.in, epmat.in, phdos.in, rpa.in, scdft.in
    #
    write_ph(prefix, nq, ecutwfc, nbnd)
    #
    # bands.in, pp.in, proj.in, pw2wan.in, q2r.in
    #
    write_pp(prefix)
    #
    # band.gp, {prefix}.win, respack.in, disp.in
    #
    write_wannier(prefix, skp, nbnd, nq)
    #
    # openmx.in : Input file for openmx
    #
    if not os.path.isfile("openmx.in"):
        write_openmx(prefix, skp, nq, rel)
Esempio n. 13
0
        # PyMatGen structure from CIF file
        #
        structure = pymatgen.Structure.from_file(cif_file)
        structure.remove_oxidation_states()
        #
        # Refine 3-folded Wyckoff position
        #
        frac_coord2 = numpy.array(structure.frac_coords)
        for ipos in range(len(frac_coord2)):
            for iaxis in range(3):
                coord3 = frac_coord2[ipos, iaxis] * 6.0
                if abs(round(coord3) - coord3) < 0.001:
                    frac_coord2[ipos, iaxis] = float(round(coord3)) / 6.0
        #
        # Disordered structure raises AttributeError. So it is skipped.
        #
        try:
            skp = seekpath.get_explicit_k_path(
                (structure.lattice.matrix, frac_coord2, [
                    pymatgen.Element(str(spc)).number
                    for spc in structure.species
                ]))
            structure2 = pymatgen.Structure(skp["primitive_lattice"],
                                            skp["primitive_types"],
                                            skp["primitive_positions"])
        except AttributeError:
            print("Fractional occupancy, may be disordered.")
            continue
        #
        print(cif_file[0:len(cif_file) - 4], structure2.volume)
Esempio n. 14
0
Colours = [(0, 0, 255), (128, 0, 255), (255, 0, 255), (255, 0, 128), (255, 0, 0), (255, 128, 0)];

#EndRegion


#Region:BandPathGeneration

structure = io.read(StructureFile)
numbers = structure.get_atomic_numbers()
inp = (structure.cell,structure.get_scaled_positions(),numbers)

BandPaths = None # Set up k-path explicitly here if not using SeeKpath

if UseSeeKpath:
	explicit_data = seekpath.get_explicit_k_path(inp,reference_distance=0.1)
	k_labels = (explicit_data['explicit_kpoints_labels'])
	kpoint_labels = []
	for label in k_labels:
		label = r"$\Gamma$" if label == 'GAMMA' else label
		kpoint_labels.append(label)
	kpoint_positions = (explicit_data['explicit_kpoints_rel'])
	BandPath = [(tuple(pos), lab) for lab,pos in zip(kpoint_labels,kpoint_positions) if lab != '']
	BandPaths = [BandPath[i:j] for i, j in zip([0]+BandPathBreaks, BandPathBreaks+[None])]

if BandPaths == None:
	sys.exit('You need to set up the BandPath explicitly or use seeKpath to do it for you!')


new_data = seekpath.get_path(inp)
ReciprocalLatticeVectors = new_data['reciprocal_primitive_lattice']
Esempio n. 15
0
import seekpath
from pymatgen import Structure
import os

os.chdir('/home/ksrc5/FTJ/bfo/sto-bfo')
s = Structure.from_file('POSCAR')
skp = seekpath.get_explicit_k_path(s)
print(skp)
Esempio n. 16
0
    help=
    "Turns off time reversal symmetry, if it is off and there is no centrosymmetry, additional lines are needed."
)
(options, args) = parser.parse_args()

structure = io.read(options.input_file)
numbers = structure.get_atomic_numbers()
inp = (structure.cell, structure.get_scaled_positions(), numbers)

# Turn off time reversal symmetry if necessary
if not options.time_reversal:
    tr = True
else:
    tr = False

explicit_data = seekpath.get_explicit_k_path(
    inp, with_time_reversal=tr, reference_distance=options.resolution)

kpath = explicit_data['explicit_kpoints_rel']

weight = 0.
with open(options.output_file, 'a') as outfile:
    for point in kpath:
        outfile.write("%8.6f %8.6f %8.6f %5.3f\n" %
                      (point[0], point[1], point[2], weight))

print('Output written to {}'.format(options.output_file))

# Write new conventions cell, to ensure compliance with the kpoints
new_data = seekpath.get_path(inp)

new_cell = ase.Atoms(positions=new_data['conv_positions'],
Esempio n. 17
0
def get_seekpath_kpoint_path(doc,
                             standardize=True,
                             explicit=True,
                             spacing=0.01,
                             threshold=1e-7,
                             debug=False,
                             symmetry_tol=None):
    """ Return the conventional kpoint path of the relevant crystal system
    according to the definitions by "HKPOT" in
    Comp. Mat. Sci. 128, 2017:

    http://dx.doi.org/10.1016/j.commatsci.2016.10.015

    Parameters:
        doc (dict/tuple): matador doc or spglib tuple to find kpoint path for.

    Keyword arguments:
        spacing (float): desired kpoint spacing
        threshold (float): internal seekpath threshold
        symmetry_tol (float): spglib symmetry tolerance

    Returns:
        dict: standardized version of input doc
        list: list of kpoint positions
        dict: full dictionary of all seekpath results

    """
    try:
        from seekpath import get_explicit_k_path, get_path
    except ImportError:
        raise ImportError(
            "SeeK-Path dependency missing, please install it with `pip install seekpath`."
        )

    if symmetry_tol is None:
        symmetry_tol = 1e-5

    if isinstance(doc, tuple):
        spg_structure = doc
    else:
        if standardize:
            spg_structure = doc2spg(
                standardize_doc_cell(doc, symprec=symmetry_tol))
        else:
            spg_structure = doc2spg(doc)

    if explicit:
        seekpath_results = get_explicit_k_path(spg_structure,
                                               reference_distance=spacing,
                                               with_time_reversal=True,
                                               symprec=symmetry_tol,
                                               threshold=threshold)

        kpt_path = seekpath_results['explicit_kpoints_rel']
    else:
        seekpath_results = get_path(spg_structure)
        kpt_path = []

    primitive_doc = dict()
    primitive_doc['lattice_cart'] = seekpath_results['primitive_lattice']
    primitive_doc['positions_frac'] = seekpath_results['primitive_positions']
    primitive_doc['atom_types'] = [
        str(elements[i]) for i in seekpath_results['primitive_types']
    ]
    primitive_doc['num_atoms'] = len(primitive_doc['atom_types'])
    primitive_doc['lattice_abc'] = cart2abc(primitive_doc['lattice_cart'])
    primitive_doc['cell_volume'] = cart2volume(primitive_doc['lattice_cart'])
    if debug:
        print('Found lattice type {}'.format(
            seekpath_results['bravais_lattice_extended']))
        print('Old lattice:\n', np.asarray(doc['lattice_cart']))
        print('Contained {} atoms'.format(doc['num_atoms']))
        print('New lattice:\n', np.asarray(primitive_doc['lattice_cart']))
        print('Contains {} atoms'.format(primitive_doc['num_atoms']))
        print('k-point path contains {} points.'.format(len(kpt_path)))

    if 'site_occupancy' in doc:
        if min(doc['site_occupancy']) < 1 - EPS:
            print('Ignoring any site occupancy found in this cell.')
        primitive_doc['site_occupancy'] = [
            1 for atom in primitive_doc['atom_types']
        ]

    return primitive_doc, kpt_path, seekpath_results
Esempio n. 18
0
    def __init__(self, cell, positions, numbers, face_color=True):
        if type(cell) == np.ndarray:
            cell = cell.tolist()

        if type(positions) == np.ndarray:
            positions = positions.tolist()

        if type(numbers) == np.ndarray:
            numbers = numbers.tolist()

        super().__init__(cell=cell,
                         positions=positions,
                         numbers=numbers,
                         face_color=face_color)

        system = (np.array(cell), np.array(positions), np.array(numbers))
        res = seekpath.getpaths.get_path(system, with_time_reversal=False)

        real_lattice = res["primitive_lattice"]
        rec_lattice = np.array(
            seekpath.hpkot.tools.get_reciprocal_cell_rows(real_lattice))
        b1, b2, b3 = rec_lattice

        faces_data = get_BZ(b1=b1, b2=b2, b3=b3)

        response = {}
        response["faces_data"] = faces_data
        response["b1"] = b1.tolist()
        response["b2"] = b2.tolist()
        response["b3"] = b3.tolist()
        ## Convert to absolute
        response["kpoints"] = {
            k: (v[0] * b1 + v[1] * b2 + v[2] * b3).tolist()
            for k, v in res["point_coords"].items()
        }
        response["kpoints_rel"] = {
            k: [v[0], v[1], v[2]]
            for k, v in res["point_coords"].items()
        }
        response["path"] = res["path"]

        # It should use the same logic, so give the same cell as above
        res_explicit = seekpath.get_explicit_k_path(system,
                                                    with_time_reversal=False)
        for k in res_explicit:
            if k == "segments" or k.startswith("explicit_"):
                if isinstance(res_explicit[k], np.ndarray):
                    response[k] = res_explicit[k].tolist()
                else:
                    response[k] = res_explicit[k]

        if (np.sum(
                np.abs(
                    np.array(res_explicit["reciprocal_primitive_lattice"]) -
                    np.array(res["reciprocal_primitive_lattice"]))) > 1.0e-7):
            raise AssertionError("Got different reciprocal cells...")

        self.jsondata = response
        self.kpts = self.jsondata['explicit_kpoints_abs']
        self.path_vectors = self.jsondata['path']
        self.update_structure = 0
Esempio n. 19
0
    "-r",
    "--resolution",
    action="store",
    type="float",
    dest="resolution",
    default=0.1,
    help=
    "a reference target distance between neighboring k-points in the path, in units of 1/ang."
)
(options, args) = parser.parse_args()

structure = io.read(options.input_file)
numbers = structure.get_atomic_numbers()
inp = (structure.cell, structure.get_scaled_positions(), numbers)

explicit_data = seekpath.get_explicit_k_path(
    inp, reference_distance=options.resolution)

kpath = explicit_data['explicit_kpoints_rel']

weight = 0.
with open(options.output_file, 'a') as outfile:
    for point in kpath:
        outfile.write("%8.6f %8.6f %8.6f %5.3f\n" %
                      (point[0], point[1], point[2], weight))

print('Output written to {}'.format(options.output_file))

# Write new conventions cell, to ensure compliance with the kpoints
new_data = seekpath.get_path(inp)

new_cell = ase.Atoms(positions=new_data['conv_positions'],
Esempio n. 20
0
# #----------------------------
# print("Structure information [spglib]:")
# spacegroup = spglib.get_spacegroup(inp, symprec=float(options.symprec))
# print("\tSpace group number: %s" % spacegroup.split()[1])
# print("\tSpace international symbol: %s" % spacegroup.split()[0])

# Turn off time reversal symmetry if necessary
if not options.time_reversal:
    tr = True
else:
    tr = False

# get K-points
explicit_data = seekpath.get_explicit_k_path(inp,
                                             with_time_reversal=tr,
                                             reference_distance=float(
                                                 options.resolution),
                                             symprec=float(options.symprec))
kpath = explicit_data['explicit_kpoints_rel']
seg = np.array(explicit_data['explicit_segments'])
labels = np.array(explicit_data['explicit_kpoints_labels'])

# return symmetry
if options.verbose == True:
    print("Structure information:")
    print("\tPrecision for finding symmetry: %8.6f \AA" % options.symprec)
    print("\tSpace group number: %s" % explicit_data['spacegroup_number'])
    print("\tSpace international symbol: %s" %
          explicit_data['spacegroup_international'])
    print("\nTime reversal symmtery: %s" % tr)