TABLE OF CONTENTS
::pwtk::pwi::abc2celldm
SYNOPSIS
proc ::pwtk::pwi::abc2celldm {} {
PURPOSE
Transform the A,B,C,cosAB,cosAC,cosBC cell specification in the SYSTEM namelist into the celldm(1)--celldm(6) specification based on ibrav.
BEWARE
If ibrav==0 & CELL_PARAMETERS are specified in angstrom or bohr units, then celldm(1) is set and CELL_PARAMETERS are transformed to alat units.
If cell is already specified with celldm(i) nothing is done, otherwise A,B,C,cosAB,cosAC,cosBC are unset and celldm(i) are set.
REMARK
This routine is based on the abc2celldm subroutine in QE's Modules/latgen.f90 (if new lattices are introduced to QE, this cmd must be updated).
SOURCE
set ibrav [ibrav] if { $ibrav == "" } { ::pwtk::error "ibrav is not defined" 1 } if { $ibrav == 0 } { # # free lattice: transform CELL_PARAMETERS to alat & set celldm(1) # set unit [::pwtk::input::cardGetFlags CELL_PARAMETERS trim] set cell [::pwtk::input::cardGetContent CELL_PARAMETERS] if { $cell == {} } { ::pwtk::error "CELL_PARAMETERS must be specified for ibrav == 0" 1 } if { [llength $cell] != 9 } { ::pwtk::error "expected a 3x3 matrix for CELL_PARAMETERS, but got\n$cell" 1 } if { ! [string match *alat* $unit] } { # angstrom || bohr set a [::pwtk::norm3 [lrange $cell 0 2]] set scale [expr {1.0/$a}] if { $unit eq {} } { if { [::pwtk::input::namelistGetVarValue SYSTEM celldm(1)] eq {} \ && [::pwtk::pwi::aA] } { # from input_pw.html: # if neither unit nor lattice parameter are specified, 'bohr' # is assumed - DEPRECATED, will no longer be allowed set unit bohr } else { # plain "CELL_PARAMETERS" implies alat units set alat [alat] } } if { [string match *angstrom* $unit] } { set alat [expr {$::pwtk::angs2bohr*$a}] } elseif { [string match *bohr* $unit] } { set alat $a } SYSTEM " celldm(1) = $alat, A = , a = " CELL_PARAMETERS (alat) [::pwtk::scaleVec $scale $cell] return } } # store A, B, C... & unset them in the SYSTEM namelist foreach var {A B C cosAB cosAC cosBC} { set varName [::pwtk::input::namelistGetVarNoCase SYSTEM $var] set value [::pwtk::input::namelistGetVarValue SYSTEM $varName] SYSTEM " $varName = " if { $var == "A" && $value == {} } { # not using A, B, C... return } ::pwtk::ifset value 0.0 set $var $value # $value must be a number (or expression) if { ! [::pwtk::is_expr $value] } { ::pwtk::error "expected a number for lattice parameter $var, but got \"$value\"" 1 } } # check lattice-parameters values if { $A <= 0.0 } { ::pwtk::error "lattice parameter A must be >= 0.0, but got $A" 1 } if { $B < 0.0 } { ::pwtk::error "lattice parameter B must be > 0.0, but got $B" 1 } if { $C < 0.0 } { ::pwtk::error "lattice parameter C must be > 0.0, but got $C" 1 } if { abs($cosAB) > 1.0 } { ::pwtk::error "lattice parameter cosAB must be in \[-1,1\], but got $cosAB" 1 } if { abs($cosAC) > 1.0 } { ::pwtk::error "lattice parameter cosAC must be in \[-1,1\], but got $cosAC" 1 } if { abs($cosBC) > 1.0 } { ::pwtk::error "lattice parameter cosBC must be in \[-1,1\], but got $cosBC" 1 } # load celldm() ... set celldm(1) [expr $A * $::pwtk::angs2bohr] set celldm(2) [expr $B / $A] set celldm(3) [expr $C / $A] set celldm(4) 0.0 set celldm(5) 0.0 set celldm(6) 0.0 if { $ibrav == 14 } { # ... triclinic lattice set celldm(4) $cosBC set celldm(5) $cosAC set celldm(6) $cosAB } elseif { $ibrav == -12 || $ibrav == -13 } { # ... monoclinic P or base centered lattice, unique axis b set celldm(5) $cosAC } elseif { abs($ibrav) == 5 || $ibrav == 12 || $ibrav == 13 } { # ... trigonal and monoclinic lattices, unique axis c set celldm(4) $cosAB } foreach i [seq 1 6] { if { $celldm($i) != 0.0 } { SYSTEM " celldm($i) = $celldm($i) " } } }