# Crystal module¶

The aim of the crystal module is to be able to easily manipulate all lattice parameters of a crystal and do some basic operation on atomic coordinate such as :

• Compute lattice vectors, volume
• Coordinates transformation
• input or output in VASP or CRYSTAL format

Today, symmetry is not considered. See python ASE for symetry support.

Requirements :
numpy module is used internally in several functions or methods.
WARNING :
please, paid attention to angle unit. All angles are in degrees, they are internally converted to radian when needed.

In the following we use a Cu2O crystal as an example.

>>> import crystal
>>> Cu2O = crystal.fromPOSCAR("POSCAR")
--------------------------------------------------
lattice parameters : Cu2O Bulk
--------------------------------------------------
a     =    4.26000
b     =    4.28000
c     =    4.27000
alpha =     90.000
beta  =     90.000
gamma =     90.000
--------------------------------------------------


## class crystal¶

class crystal.Crystal(*largs, **args)[source]

class Crystal allows to describe and do operations on a crystal lattice

Parameters: a (float) – lattice parameter a. b (float) – lattice parameter b. c (float) – lattice parameter c. alpha (float) – lattice parameter alpha. beta (float) – lattice parameter beta. gamma (float) – lattice parameter gamma. name (string) – crystal name. lattice (string) – bravais lattice name. veca (list) – lattice vector a (length = 3). vecb (list) – lattice vector b (length = 3). vecc (list) – lattice vector c (length = 3). Z (integer) – number of unti formula

If you give the bravais lattice name you may not set all lattice parameters :

>>> cry = crystal.Crystal(a = 3., lattice = "cubic")
>>> print(cry)
--------------------------------------------------
lattice parameters :
--------------------------------------------------
a     =    3.00000
b     =    3.00000
c     =    3.00000
alpha =     90.000
beta  =     90.000
gamma =     90.000
--------------------------------------------------


If you give only the bravais lattice, the prompt will ask you parameters needed according to the bravais lattice.

>>> cry = crystal.Crystal(lattice = "hexagonal")
a = 3.
c = 7.
>>> print(cry)
--------------------------------------------------
lattice parameters :
--------------------------------------------------
a     =    3.00000
b     =    3.00000
c     =    7.00000
alpha =     90.000
beta  =     90.000
gamma =    120.000
--------------------------------------------------


You can give directly lattice vectors.

>>> cry = crystal.Crystal(veca = [2., 0., 0.], vecb = [-1., sqrt(3), 0.], vecc = [0., 0., 4.])
>>> cry.lattice
'hexagonal'
>>> print(cry)
--------------------------------------------------
lattice parameters :
--------------------------------------------------
a     =    2.00000
b     =    2.00000
c     =    4.00000
alpha =     90.000
beta  =     90.000
gamma =    120.000
--------------------------------------------------


You cannot set lattice parameters and lattice vectors at the same time. Only one of them can be set when you create a crystal object in order to ensure consistency between lattice vectors, lattice parameters and bravais lattice name. A method is available in order to print lattice vectors in a cartesian frame.

>>> cry = crystal.Crystal(lattice = "hexagonal")
a = 3.
c = 7.
>>> cry.printLatticeVectors()
--------------------------------------------------
Lattice vectors in cartesian frame : lattice is hexagonal
--------------------------------------------------
a =    3.0000000000    0.0000000000    0.0000000000
b =   -1.5000000000    2.5980762114    0.0000000000
c =    0.0000000000    0.0000000000    7.0000000000
--------------------------------------------------


### attribute concerning the lattice¶

Crystal.a

Lattice parameter a, lengths of the vectors :math: ec{a}

Crystal.b

Lattice parameter b, lengths of the vectors :math: ec{b}

Crystal.c

Lattice parameter c, lengths of the vectors :math: ec{c}

Crystal.alpha

Lattice angle $$lpha$$ . All angles must be given in degrees and are return in degrees. They are internally convert in radian when needed.

Crystal.beta

Lattice angle $$eta$$ . All angles must be given in degrees and are return in degrees. They are internally convert in radian when needed.

Crystal.gamma

Lattice angle $$\gamma$$ . All angles must be given in degrees and are return in degrees. They are internally convert in radian when needed.

Crystal.veca

Lattice vector :math: ec{a} in a cartesian frame where :math: ec{a} is along x axes and :math: ec{b} is in the (x,y) plane.

Crystal.vecb

Lattice vector :math: ec{b} in a cartesian frame where :math: ec{a} is along x axes and :math: ec{b} is in the (x,y) plane.

Crystal.vecc

Lattice vector :math: ec{c} in a cartesian frame where :math: ec{a} is along x axes and :math: ec{b} is in the (x,y) plane.

Crystal.volume

volume of the unit cell.

Crystal.lattice

Name of the lattice according to the 7 Bravais lattices. Remind that symmetry is not considered for the moment.

See bravaisLattice()

### attribute concerning the structure¶

Crystal.name = None

Name of the crystal object

Crystal.Z = None

number of unit formula

Crystal.Natoms = None

number of atoms in the unit cell

Crystal.atomNames = None

List of atom names of all atoms in the unit cell.

Crystal.group = None

Symmetry group. Nevertheless, remind that symmetry is not considered.

Crystal.XYZCoord = None

List of cartesian coordinates of the atoms in the unit cell. This is a list object.

Crystal.redCoord = None

List of reduce coordinates of the atoms in the unit cell. This is a list object.

### Create a crystal object¶

classmethod Crystal.fromPOSCAR(poscar='POSCAR', verbose=True)[source]

Create a crystal object from a POSCAR/CONTCAR VASP structure file. The POSCAR file can be given as a list of string (lines of the POSCAR file) or you can give a file object, or a file name.

Parameters: poscar (list, string, or file object) – POSCAR file verbose (bool) – verbosity
classmethod Crystal.fromCRYSTAL09(outputfile, verbose=True)[source]

Create a crystal object from an output of CRYSTAL09 program. The function read the last crystallographic cell. Outputfile can be a file or a file name.

Parameters: outputfile (string or file object) – CRYSTAL09 output file (.out) verbose (bool) – verbosity
classmethod Crystal.fromCONFIG(config='CONFIG', verbose=True)[source]

Create a crystal object from a CONFIG/REVCON file of DLPOLY classic.

Parameters: config (string) – name of the CONFIG/REVCON file verbose (bool) – verbosity

### Coordinates manipulations¶

Crystal.red2cart(x)[source]

Convert reduce coordinate into cartesian coordinate.

Parameters: x (list or array or ndarray, len(x) = 3) – cartesian coordinate vector list of lenght 3
Crystal.cart2red(x)[source]

Convert cartesian coordinate into reduce coordinate.

Parameters: x (list or array or ndarray, len(x) = 3) – reduce coordinate vector list of lenght 3
Crystal.computeRedCoord()[source]

Compute cartesian coordinates for all coordinates stored in self.redCoord.

Crystal.computeXYZCoord()[source]

Compute reduce coordinates for all coordinates stored in self.XYZCoord.

Crystal.img(r1, r2)[source]

Return the shortest vector in reduce coordinates considering the periodic conditions.

Parameters: r1 (list or array or ndarray, len(A1) = 3) – reduce coordinate of atom r1 r2 (list or array or ndarray, len(A2) = 3) – reduce coordinate of atom r2 list

r1 and r2 must be reduce coordinate and an object of length 3 ! In order to improve efficiency no check are done.

Crystal.dist_r(r1, r2)[source]

Compute the minimum distance between reduce coordinates r1 and r2 considering the periodic conditions.

Parameters: r1 (list or array or ndarray, len(A1) = 3) – reduce coordinate of atom 1 r2 (list or array or ndarray, len(A2) = 3) – reduce coordinate of atom 2 float
Crystal.dist_x(x1, x2)[source]

Compute the minimum distance between cartesian coordinates x1 and x2 considering the periodic conditions.

Parameters: x1 (list or array or ndarray, len(A1) = 3) – cartesian coordinates of atom 1 x2 (list or array or ndarray, len(A2) = 3) – cartesian coordinates of atom 2 float
Crystal.dist_i(iat, jat)[source]

Compute the minimum distance between atom with index iat and jat considering the periodic conditions.

Parameters: iat – atom index of atom i A2 (atom index) – atom index of atom j float
Crystal.calcDeplacementAtomes(other)[source]

Compute the distance between the cartesian postion fo the same atom in self and other structures.

Parameters: other – crystal object list of distance
Crystal.wrapAtoms()[source]

Replace all atoms into the unit cell using reduce coordinate

Crystal.alignCrystal(other)[source]

For each atom of the crystal, if an image of the atom belonging to other is closer to the same atom belonging to self, the other’s atom is translated to that position.

This method could be usefull if one wants to compute displacements of atoms after a relaxation of the structre.

param other: crystal object list of distance

Warning :if lattices of self and other are not the same, this have not any sense.

Crystal.makeSupercell(nx, ny, nz, sort=True)[source]

Build a supercell from the cell defined by the object. Return a new Crystal object as output.

Parameters: nx (int) – number of cell in x direction ny (int) – number of cell in y direction nz (int) – number of cell in z direction sort (bool) – if True atoms are sorted by name and by z (needed for POSCAR output !). Crystal

### Output method¶

Crystal.toXYZ(filename)[source]

(Under development) Write cartesian coordinate in a XYZ format

Parameters: filename (string) – name of the output file.
Crystal.toPOSCAR(filename='POSCAR', sort=True)[source]

Write crystal object in a vasp POSCAR file

Parameters: filename (string) – name of the output file.
Crystal.toCONFIG(filename='CONFIG')[source]

Write crystal object in a CONFIG DLPOLY file

Parameters: filename (string) – name of the output file.
Crystal.printLatticeVectors()[source]

Print the lattice vectors in a cartesian frame.

Crystal.printLatticeParameters()[source]

Print lattice paramters.