예제 #1
0
def load(fullfilename):
    #TODO move this splitting to within Material so the extension can
    #automatically be the default prefix...then move it into structure
    filedir, fileprefix, fileext = path_split(fullfilename)
    from vimm.Material import Material
    from vimm.Atom import Atom
    from vimm.Cell import Cell
    material = Material(fileprefix)
    material.format = fileext

    pkl_file = open(fullfilename, 'rb')
    structure = pickle.load(pkl_file)

    first_run = 1

    if first_run:
        first_run = 0
    else:
        material.new_geo()

    for structureAtom in structure:
        material.add_atom(Atom(structureAtom.Z, structureAtom.xyz_cartn))
    aVec, bVec, cVec = structure.lattice.base
    cell = Cell(aVec, bVec, cVec)
    material.set_cell(cell)
    material.bonds_from_distance()
    return material
예제 #2
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material = Material(fileprefix)
    file = open(fullfilename, 'r')

    line = file.readline()
    title = line.strip()
    line = file.readline()
    title2 = line.strip()
    line = file.readline()
    title3 = line.strip()

    line = file.readline()
    natoms = int(line[:3])
    nbonds = int(line[3:6])

    # Note: I'm skipping the H information here, which is
    #  typically given in fields 5-
    for i in range(natoms):
        line = file.readline()
        words = line.split()
        xyz = array(map(float, words[:3]))
        sym = cleansym(words[3])
        atno = sym2no[sym]
        material.add_atom(Atom(atno, xyz, sym, sym + str(i)))
    atoms = material.get_atoms()
    for i in range(nbonds):
        line = file.readline()
        words = line.split()
        # bond order is the third field, which I'm ignoring
        iat, jat, iorder = map(int, words[:3])
        material.add_bond(Bond(atoms[iat - 1], atoms[jat - 1], iorder))
    return material
예제 #3
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material=Material(fileprefix)
    file=open(fullfilename, 'r')


    first_run = 1

    while 1:
        line = file.readline()
        if not line: break
        words = line.split()
        nat = int(words[0])

        comment = file.readline()

        if first_run:
            first_run = 0
        else:
            material.new_geo()

        for i in range(nat):
            line = file.readline()
            words=line.split()
            sym=cleansym(words[0])
            atno = sym2no[sym]
            xyz = array(map(float,words[1:4]))
            material.add_atom(Atom(atno, xyz, sym, sym+str(i)))
    material.bonds_from_distance()
    return material
예제 #4
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material = Material(fileprefix)
    file = open(fullfilename, 'r')

    atoms = []
    bfs = []
    orbs = []

    mode = None

    for line in file.readlines():
        if atpat.search(line): mode = 'atoms'
        elif bfpat.search(line): mode = 'bfs'
        elif orbpat.search(line): mode = 'orbs'
        elif mode == 'atoms': atoms.append(line)
        elif mode == 'bfs': bfs.append(line)
        elif mode == 'orbs': orbs.append(line)
        else: print '? ', line,

    for line in atoms:
        words = line.split()
        if len(words) < 6: continue

        atno = int(words[2])
        xyz = map(float, words[3:6])
        material.add_atom(Atom(atno, array(xyz)))
    material.bonds_from_distance()
    material.geo.basis = parse_basis(bfs)
    material.geo.orbs = parse_orbs(orbs)
    return material
예제 #5
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material = Material(fileprefix)
    file = open(fullfilename, 'r')
    nwchem_options = {}

    geo_pat = re.compile("\s*No\.\s*Tag\s*Charge")
    molchg_pat = re.compile("\s*Charge\s*:\s*")
    multip_pat = re.compile("\s*Spin multiplicity:\s*")

    geos = []
    while 1:
        line = file.readline()
        if not line: break
        if geo_pat.search(line):
            geo = get_geo(file)
            geos.append(geo)
        elif molchg_pat.search(line):
            words = string.split(line)
            nwchem_options['molchg'] = int(words[2])
        elif multip_pat.search(line):
            words = string.split(line)
            nwchem_options['multip'] = int(words[2])
    # end of main infinite loop
    file.close()

    print "Loading %d geometries" % len(geos)
    for igeo in range(len(geos)):
        if igeo: material.new_geo()
        for (atno, xyz) in geos[igeo]:
            material.add_atom(Atom(atno, xyz))
    if len(material.geo.atoms) < 200: material.bonds_from_distance()
    material.nwchem_options = nwchem_options
    return material
예제 #6
0
def add_the_unit_cell(material, buffer):
    name = material.get_name()
    cell = material.get_cell()
    atoms = material.get_atom_list()

    if cell: return material  # Don't do anything for now

    newname = "%s_cell" % name
    newmaterial = Material(newname)

    if not buffer: buffer = 2.  # Can still set to a small value like 0.01
    xmin, xmax, ymin, ymax, zmin, zmax = bbox_atoms(atoms, buffer)

    for atom in atoms:
        atno = atom.get_atno()
        xyz = atom.get_position()
        xyznew = array((xyz[0] - xmin, xyz[1] - ymin, xyz[2] - zmin))
        newmaterial.add_atom(Atom(atno, xyznew))

    newmaterial.set_cell(
        Cell((xmax - xmin, 0, 0), (0, ymax - ymin, 0), (0, 0, zmax - zmin)))

    opts = getattr(material, "seqquest_options", {})
    if opts: newmaterial.seqquest_options = opts.copy()

    opts = getattr(material, "socorro_options", {})
    if opts: newmaterial.socorro_options = opts.copy()

    newmaterial.bonds_from_distance()
    return newmaterial
예제 #7
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material=Material(fileprefix)
    file=open(fullfilename, 'r')

    first_run = 1

    while 1:
        line = file.readline()
        if not line: break
        if not geostart.search(line): continue
        if first_run:
            first_run = 0
        else:
            material.new_geo()
        i = 1
        while 1:
            line = file.readline()
            if geoend.search(line): break
            match = atpat.match(line)
            sym = match.group(1)
            x = float(match.group(2))
            y = float(match.group(3))
            z = float(match.group(4))
            sym=cleansym(sym)
            atno = sym2no[sym]
            xyz = array((x,y,z))
            material.add_atom(Atom(atno, xyz, sym, sym+str(i)))
            i += 1
    material.bonds_from_distance()
    return material
예제 #8
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material = Material(fileprefix)
    file = open(fullfilename, 'r')

    line = file.readline()
    title = line.strip()

    line = file.readline()
    natoms, nbonds = map(int, line.split())
    for i in range(natoms):
        line = file.readline()
        words = line.split()
        xyz = array(map(float, words[:3]))
        sym = cleansym(words[3])
        atno = sym2no[sym]
        material.add_atom(Atom(atno, xyz, sym, sym + str(i)))
    atoms = material.get_atoms()
    for i in range(nbonds):
        line = file.readline()
        words = line.split()
        # I think order is the third one, but I'm not sure
        iat, jat, iorder = map(int, words[:3])
        material.add_bond(Bond(atoms[iat - 1], atoms[jat - 1], iorder))
    return material
예제 #9
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material = Material(fileprefix)
    file = open(fullfilename, 'r')

    first_run = True

    while 1:
        line = file.readline()
        if not line: break
        words = line.split()
        nat = int(words[0])

        comment = file.readline()
        ax, ay, az, bx, by, bz, cx, cy, cz = [
            float(i) for i in comment.split()
        ]
        cell = Cell((ax, ay, az), (bx, by, bz), (cx, cy, cz))

        if first_run:
            first_run = False
        else:
            material.new_geo()

        material.set_cell(cell)

        for i in range(nat):
            line = file.readline()
            words = line.split()
            sym = cleansym(words[0])
            atno = sym2no[sym]
            xyz = array(map(float, words[1:4]))
            material.add_atom(Atom(atno, xyz, sym, sym + str(i)))
    material.bonds_from_distance()
    return material
예제 #10
0
def build_the_alkane(n):
    atoms = alkanebuilder(n)
    if not n: n = 1
    nc = 2 * n + 2
    nh = 2 * nc + 2
    material = Material("C%dH%d" % (nc, nh))
    for atno, xyz in atoms:
        material.add_atom(Atom(atno, xyz))
    material.bonds_from_distance()
    return material
예제 #11
0
def build_the_crystal(crystal_type, sym1, sym2, a, c_a):
    uc, atoms = builders[crystal_type](a, c_a, sym1, sym2)
    material = Material(crystal_type.replace(' ', '_'))
    for sym, (x, y, z) in atoms:
        atno = sym2no[sym]
        material.add_atom(Atom(atno, array((x, y, z))))
    cell = Cell(uc[0], uc[1], uc[2])
    material.set_cell(cell)
    material.bonds_from_distance()
    return material
예제 #12
0
def build_the_crystal_from_db(crystal_type):
    uc, atoms = crystal_type_dict[crystal_type]
    material = Material(crystal_type.replace(' ', '_'))
    for sym, (x, y, z) in atoms:
        atno = sym2no[sym]
        material.add_atom(Atom(atno, array((x, y, z)), sym))
    cell = Cell(uc[0], uc[1], uc[2])
    material.set_cell(cell)
    material.bonds_from_distance()
    return material
예제 #13
0
def parse_cart(lines):
    material = Material("vimm")
    for line in lines:
        words = line.split()
        if not words: continue
        sym = str(words[0])
        atno = sym2no[sym]
        xyz = array(map(float, words[1:4]))
        material.add_atom(Atom(atno, xyz, sym, sym))
    material.bonds_from_distance()
    return material
예제 #14
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material=Material(fileprefix)
    file=open(fullfilename, 'r')

    hatpat = re.compile('HETATM')
    atpat = re.compile('^ATOM')
    conpat = re.compile('^CONECT')
    ordpat = re.compile('^ORDER')
    endpat = re.compile('^END')
    ucpat = re.compile('^CRYSTX')

    bonds = {}
    orders = {}
    iat = 0
    for line in open(fullfilename):
        if hatpat.search(line) or atpat.search(line):
            d1,i,d2,d3,d4,d5,x,y,z,attype,d6,d7,q = read(line,atom_format)
            xyz = array([x,y,z])
            sym = cleansym(attype)
            atno = sym2no[sym]
            atom = Atom(atno,xyz,sym,sym+str(iat))
            atom.fftype = attype # save just in case
            material.add_atom(atom)
            iat += 1
        elif conpat.search(line):
            ats = map(int,line[6:].split())
            index = ats[0]-1
            bonds[index] = [atj-1 for atj in ats[1:]]
            orders[index] = [1]*(len(ats)-1)
        elif ordpat.search(line):
            ords = map(int,line[6:].split())
            index = ords[0]-1
            orders[index] = ords[1:]
        elif ucpat.search(line):
            words = line.split()
            a,b,c,alpha,beta,gamma = map(float,words[1:7])
            axyz,bxyz,cxyz = abcabg2abc(a,b,c,alpha,beta,gamma)
            cell = Cell(axyz,bxyz,cxyz)
            material.set_cell(cell)
    atoms = material.get_atoms()
    #print len(atoms)," atoms loaded"
    for iat in bonds.keys():
        bond_partners = bonds[iat]
        bond_orders = orders[iat]
        for jat,ij_order in zip(bond_partners,bond_orders):
            if jat > iat: material.add_bond(Bond(atoms[iat],atoms[jat],
                                                 ij_order))
    return material
예제 #15
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material=Material(fileprefix)
    
    try:
        from matter.Structure import Structure
        st = Structure()
        st.read(fullfilename)
        for i,atom in enumerate(st):
            Z = atom.Z
            xyz_cartn = atom.xyz_cartn
            sym = atom.symbol
            material.add_atom(Atom(Z, xyz_cartn, sym, sym+str(i)))
        material.bonds_from_distance()
        lvs = st.lattice.base
        cell = Cell(lvs[0],lvs[1],lvs[2])
        material.set_cell(cell)
        return material
    except:
        print 'Vimm needs matter package from pypi to open cif files'
        return
예제 #16
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material = Material(fileprefix)

    parser = CMLParser()
    geos = parser.process(fullfilename)

    molecule = geos[0]
    atoms = molecule.atoms
    cell = molecule.cell
    nat = len(atoms)

    for i in range(nat):
        sym, pos = atoms[i]
        pos = array(pos)
        atno = sym2no[sym]
        material.add_atom(Atom(atno, pos, sym, sym + str(i)))
    if cell:
        the_cell = Cell(cell[0], cell[1], cell[2])
        material.set_cell(the_cell)
    material.bonds_from_distance()
    return material
예제 #17
0
def build_the_supercell(material, ass, bss, css):
    if ass == 1 and bss == 1 and css == 1:
        return material

    name = material.get_name()
    cell = material.get_cell()
    atomlist = material.get_atom_list()

    axyz = cell.axyz
    bxyz = cell.bxyz
    cxyz = cell.cxyz

    newname = "%s%d%d%d" % (name, ass, bss, css)
    newmaterial = Material(newname)
    naxyz = ass * axyz
    nbxyz = bss * bxyz
    ncxyz = css * cxyz

    for atom in atomlist:
        atno = atom.get_atno()
        sym = atom.get_symbol()
        xyz = atom.get_position()
        for i in range(ass):
            for j in range(bss):
                for k in range(css):
                    xyznew = xyz + i * axyz + j * bxyz + k * cxyz
                    newmaterial.add_atom(Atom(atno, xyznew, sym))

    newmaterial.set_cell(Cell(naxyz, nbxyz, ncxyz))

    opts = getattr(material, "seqquest_options", {})
    if opts: newmaterial.seqquest_options = opts.copy()

    opts = getattr(material, "socorro_options", {})
    if opts: newmaterial.socorro_options = opts.copy()

    newmaterial.bonds_from_distance()
    return newmaterial
예제 #18
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    material=Material(fileprefix)

    curresnum = None
    curres = None
    locator = None
    residues = []
    for line in open(fullfilename):
        tag = line[:6].strip()
        if tag == 'ATOM' or tag == 'HETATM':
            loctag = line[16:17].strip()
            resnum = int(line[22:26])
            modifyer = line[26].strip()
            restag = line[18:21].strip()
            x = float(line[30:38])
            y = float(line[38:46])
            z = float(line[46:54])
            xyz = array([x,y,z])
            try:
                sym = line[13:15].strip()
                sym = symconv[sym]
                atno = sym2no[sym]
            except:
                sym = line[12:15].strip()
                atno = sym2no[sym]
            if loctag:
                if not locator: locator = loctag
            if loctag and loctag != locator: continue
            if modifyer: continue  # skip residue #25B if we already have #25
            material.add_atom(Atom(atno,xyz))
        elif tag == 'CRYST1':
            words = line.split()
            a,b,c,alpha,beta,gamma = map(float,words[1:7])
            #finish
    material.bonds_from_distance()
    return material
예제 #19
0
def load(fullfilename,**kwargs):
    # Keyword args
    VERBOSE = kwargs.get('VERBOSE',False)
    
    filedir, fileprefix, fileext = path_split(fullfilename)
    material=Material(fileprefix)

    # Pass 1: check ndtset
    ndtset = 0
    natom = 0
    ntypat = 0
    dt = 1
    iter = abinit_tokenizer(open(fullfilename),**kwargs)
    while 1:
        try:
            word = iter.next()
        except:
            break
        if word == 'ndtset':
            ndtset = int(iter.next())
            if ndtset > 1:
                print "Multiple data sets found. Reading only the first"
                # If you want to select a particular data set, pop
                #  up a dialog box here and ask which one you
                #  want to load.
                # Also need to put code in here so that you don't
                #  get the dialog box twice, such as dt_selected
                #  boolean
        elif word == 'natom':
            natom = int(iter.next())
        elif word == 'ntypat':
            ntypat = int(iter.next())
            
    # Pass 2: get remaining info
    xangst = None
    xred = None
    xcart = None
    znucl = None
    typat = None
    rprim = None
    acell = None
    angdeg = None
    iter = abinit_tokenizer(open(fullfilename),**kwargs)
    while 1:
        try:
            word = iter.next()
        except:
            break
        if word == 'xangst' or word == 'xangst%d' % dt:
            xangst = get_natom3(iter,natom)
        elif word == 'xred' or word == 'xred%d' % dt:
            xred = get_natom3(iter,natom)
        elif word == 'xcart' or word == 'xcart%d' % dt:
            xcart = get_natom3(iter,natom)
        elif word == 'znucl':
            znucl = [int(float(i)) for i in nextn(iter,ntypat)]
        elif word == 'typat':
            typat = [int(i) for i in nextn(iter,natom)]
        elif word == 'acell' or word == 'acell%d' % dt:
            acell = [float(i) for i in nextn(iter,3)]
        elif word == 'rprim' or word == 'rprim%d' % dt:
            rprim = [float(i) for i in nextn(iter,9)]
        elif word == 'angdeg' or word == 'angdeg%d' % dt:
            angdeg = [float(i) for i in nextn(iter,3)]

    # Done parsing
    if VERBOSE:
        print "natom = ",natom
        print "ntypat = ",ntypat
        print "znucl = ",znucl
        print "typat = ",typat
        print "xcart = ",xcart
        print "xred = ",xred
        print "xangst = ",xangst
        print "acel = ",acell
        print "rprim = ",rprim
        print "angdeg = ",angdeg

    # Build the unit cell. Precedence is rprim > angdeg
    if not acell: acell = [1,1,1]
    acell = [bohr2ang*i for i in acell] # Convert acell to Angstrom
    
    if rprim:
        ax,ay,az,bx,by,bz,cx,cy,cz = rprim
        cell = Cell( (acell[0]*ax,acell[0]*ay,acell[0]*az),
                     (acell[1]*bx,acell[1]*by,acell[1]*bz),
                     (acell[2]*cx,acell[2]*cy,acell[2]*cz))
    else:
        if not angdeg:
            angdeg = [90.,90.,90.]
        axyz,bxyz,cxyz = abcabg2abc(acell[0],acell[1],acell[2],
                                    angdeg[0],angdeg[1],angdeg[2])
        cell = Cell(axyz,bxyz,cxyz)
    material.set_cell(cell)
    
    # Build the atom list. Precedence is xred > xangst > xcart
    if xred:
        A,B,C = cell.abc()
        for i in range(natom):
            atno = znucl[typat[i-1]-1]
            xr,yr,zr = xred[i]
            xyz = xr*A + yr*B + zr*C
            material.add_atom(Atom(atno,xyz))
    elif xangst:
        for i in range(natom):
            atno = znucl[typat[i-1]-1]
            material.add_atom(Atom(atno,xangst[i]))
    elif xcart:
        for i in range(natom):
            atno = znucl[typat[i-1]-1]
            xyz = [bohr2ang*a for a in xcart[i]]
            material.add_atom(Atom(atno,xyz))
    else:
        raise "Abinit Input: must specify xred, xangst, or xcart"
    material.bonds_from_distance()
    return material
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    file = open(fullfilename, 'r')

    # Initialize atom data
    material = Material(fileprefix)
    element = []  # Initialize element variable to be appended
    timestamp = 1
    nat = None
    cell = None
    lattice_coords = False
    scale = 1.
    scalez = 1.
    conv_to_ang = True

    while 1:
        line = file.readline()
        if not line: break

        if p_atomtype.search(line):
            # From the headerfile get the number of atom types
            line = file.readline()
            numberoftypes = int(line)

        elif p_coord_type.search(line):
            line = file.readline()
            line = line.strip().lower()
            if line == 'lattice':
                lattice_coords = True
        elif p_to_lattice.search(line):
            raise "Quest to_lattice flags not currently supported"

        elif p_scale.search(line):
            line = file.readline()
            scale = float(line.strip())

        elif p_scalez.search(line):
            line = file.readline()
            scalez = float(line.strip())

        # Using the atom type number, set the atom names
        elif p_atomfile.search(line):
            line = file.readline()
            words = string.split(line)
            atomname = cleansym(words[0]).capitalize()
            #atomname,atomext = path.splitext(words[0])
            #atomname = string.capitalize(atomname) # Captitalize the
            element.append(atomname)  # first letter

        elif p_nat.search(line):
            line = file.readline()
            words = string.split(line)
            nat = int(words[0])

        # Read in the initial geometry data
        elif p_geometry.search(line):
            for i in range(nat):
                line = file.readline()
                words = string.split(line)
                num = int(words[0])
                try:
                    type = element[int(words[1]) - 1]  #Set the type
                    atno = sym2no[type]
                except:
                    # Fallback for when atoms are specified with symbols
                    atno = sym2no[words[1]]
                x, y, z = [float(i) for i in words[2:5]]
                #print x,y,z
                if lattice_coords:
                    converter = cell.lat2cart_factory()
                    x, y, z = converter(x, y, z)
                    #print x,y,z
                elif conv_to_ang:
                    x, y, z = [bohr2ang * i for i in [x, y, z]]
                    #print x,y,z
                xyz = array((x, y, z))
                material.add_atom(Atom(atno, xyz))
            if cell: material.set_cell(cell)

        elif p_newgeo.search(line):
            comment = file.readline()
            material.new_geo()
            for i in range(nat):
                line = file.readline()
                words = string.split(line)
                num = int(words[0])
                try:
                    type = element[int(words[1]) - 1]  #Set the type
                    atno = sym2no[type]
                except:
                    # Fallback for when atoms are specified with symbols
                    atno = sym2no[words[1]]
                x, y, z = [float(i) for i in words[2:5]]
                #print x,y,z
                if lattice_coords:
                    converter = cell.lat2cart_factory()
                    x, y, z = converter(x, y, z)
                    #print x,y,z
                elif conv_to_ang:
                    x, y, z = [bohr2ang * i for i in [x, y, z]]
                    #print x,y,z
                xyz = array((x, y, z))
                material.add_atom(Atom(atno, xyz))
            if cell: material.set_cell(cell)
        elif p_cell.search(line):
            line = file.readline()
            words = string.split(line)
            ax, ay, az = [float(i) for i in words[:3]]
            if conv_to_ang:
                ax, ay, az = [bohr2ang * i for i in [ax, ay, az]]
            line = file.readline()
            words = string.split(line)
            bx, by, bz = [float(i) for i in words[:3]]
            if conv_to_ang:
                bx, by, bz = [bohr2ang * i for i in [bx, by, bz]]
            line = file.readline()
            words = string.split(line)
            cx, cy, cz = [float(i) for i in words[:3]]
            if conv_to_ang:
                cx, cy, cz = [bohr2ang * i for i in [cx, cy, cz]]
            cell = Cell((ax, ay, az), (bx, by, bz), (cx, cy, cz),
                        scale=scale,
                        scalez=scalez)
    file.close()
    material.bonds_from_distance()
    return material
예제 #21
0
def parse_zmat(lines):
    material = Material("vimm")
    for line in lines:
        words = line.split()
        if len(words) == 0:
            continue
        sym = words[0]
        if len(words) == 1:
            # Atom at origin
            x = y = z = 0
        elif len(words) == 3:
            # Atom along z-axis
            x = y = 0
            iat = int(words[1]) - 1
            assert iat == 0
            r = float(words[2])
            z = r
        elif len(words) == 4:
            # This line contains a simple list of cartesian coordinates
            x, y, z = map(float, words[1:])
        elif len(words) == 5:
            # Atom in xy-plane
            y = 0
            iat = int(words[1]) - 1
            r = float(words[2])
            jat = int(words[3]) - 1
            theta = float(words[4]) * deg2rad
            # Change this to simply use the numpy object:
            x0, y0, z0 = material.get_atom(iat).get_xyz()
            x = x0 + r * sin(theta)
            if iat == 0:
                z = z0 + r * cos(theta)
            else:
                z = z0 - r * cos(theta)
        else:
            # General case
            iat = int(words[1]) - 1
            r = float(words[2])
            jat = int(words[3]) - 1
            theta = float(words[4]) * deg2rad
            kat = int(words[5]) - 1
            phi = float(words[6]) * deg2rad
            # Change these to simply use the numpy object:
            xi, yi, zi = material.get_atom(iat).get_xyz()
            xj, yj, zj = material.get_atom(jat).get_xyz()
            xk, yk, zk = material.get_atom(kat).get_xyz()

            # Change these to use numpy math:
            # Vector from iat -> jat
            xx = xj - xi
            yy = yj - yi
            zz = zj - zi
            rinv = 1 / sqrt(xx * xx + yy * yy + zz * zz)
            xa = xx * rinv
            ya = yy * rinv
            za = zz * rinv

            # Vector from iat -> kat
            xb = xk - xi
            yb = yk - yi
            zb = zk - zi

            # Unit vector from iat -> kat
            xc = ya * zb - za * yb
            yc = za * xb - xa * zb
            zc = xa * yb - ya * xb
            rinv = 1 / sqrt(xc * xc + yc * yc + zc * zc)
            xc *= rinv
            yc *= rinv
            zc *= rinv

            xb = yc * za - zc * ya
            yb = zc * xa - xc * za
            zb = xc * ya - yc * xa

            zz = r * cos(theta)
            xx = r * sin(theta) * cos(phi)
            yy = r * sin(theta) * sin(phi)

            x = xi + xa * zz + xb * xx + xc * yy
            y = yi + ya * zz + yb * xx + yc * yy
            z = zi + za * zz + zb * xx + zc * yy
        atno = sym2no[sym]
        xyz = array([x, y, z])
        material.add_atom(Atom(atno, xyz, sym, sym))
    material.bonds_from_distance()
    return material
예제 #22
0
def load(fullfilename):
    filedir, fileprefix, fileext = path_split(fullfilename)
    file = open(fullfilename, 'r')

    # Initialize atom data
    material = Material(fileprefix)
    opts = {}
    material.seqquest_options = opts

    line = file.readline()  # start reading

    # Read in the run options
    while 1:
        if line[:8] == 'output l':
            line = file.readline()
            opts['lvlout'] = int(line.strip())
            line = file.readline()
        elif line[:8] == 'do setup':
            opts['dosetup'] = True
            line = file.readline()
        elif line[:8] == 'no setup':
            opts['dosetup'] = False
            line = file.readline()
        elif line[:8] == 'do iters':
            opts['doiters'] = True
            line = file.readline()
        elif line[:8] == 'no iters':
            opts['doiters'] = False
            line = file.readline()
        elif line[:8] == 'do force':
            opts['doforce'] = True
            line = file.readline()
        elif line[:8] == 'no force':
            opts['doforce'] = False
            line = file.readline()
        elif line[:8] == 'do relax':
            opts['dorelax'] = True
            line = file.readline()
        elif line[:8] == 'no relax':
            opts['dorelax'] = False
            line = file.readline()
        elif line[:7] == 'do cell':
            opts['docell'] = True
            line = file.readline()
        elif line[:7] == 'no cell':
            opts['docell'] = False
            line = file.readline()
        elif line[:6] == 'do neb':
            opts['doneb'] = True
            line = file.readline()
        elif line[:6] == 'no neb':
            opts['doneb'] = False
            line = file.readline()
        elif line[:5] == 'do md':
            opts['domd'] = True
            line = file.readline()
        elif line[:5] == 'no md':
            opts['domd'] = False
            line = file.readline()
        elif line[:7] == 'do post':
            opts['dopost'] = True
            line = file.readline()
        elif line[:7] == 'no post':
            opts['dopost'] = False
            line = file.readline()

        elif line[:7] == 'do blas':
            opts['doblas3'] = True
            line = file.readline()
        elif line[:7] == 'no blas':
            opts['doblas3'] = False
            line = file.readline()
        else:
            # Comment this out when debugged:
            print "Unknown line from command section"
            print line,
            print "Assuming end of Input Options Section"
            break
    # end of run options

    # Beginning of setup info
    if line[:6] == 'input ':
        line = file.readline()  # skip line
    # Title
    if line[:5] == 'title':
        opts['title'] = []
        try:
            ntitl = int(line[5])
        except:
            ntitl = 1
        for i in range(ntitl):
            line = file.readline()
            opts['title'].append(line.strip())
        line = file.readline()

    if line[:5] == 'scale':
        line = file.readline()
        opts['scalep'] = float(line.strip())
        line = file.readline()

    # DFT fcnal
    if line[:6] == 'functi':
        line = file.readline()
        opts['dft_func'] = line.strip()
        line = file.readline()

    # Spin polarization
    if line[:6] == 'spin p':
        line = file.readline()
        opts['spinpol'] = int(line.strip())
        #should put an error condition here if dft requires
        # spin and no spinpol input
        line = file.readline()

    # External electric field
    if line[:6] == 'efield':
        line = file.readline()
        ex, ey, ez = map(float, line.split())
        opts['efield'] = (ex, ey, ez)  # in Ry/au
        line = file.readline()

    # External dielectric constant
    if line[:6] == 'dielec':
        line = file.readline()
        opts['dielec'] = float(line.split())
        line = file.readline()

    # Problem dimension
    if line[:6] == 'dimens' or line[:6] == 'lattic':
        line = file.readline()
        opts['ndim'] = int(line.strip())
        line = file.readline()
    else:
        print line
        raise "Dimension must be specified in Quest input"

    # Coordinates (lattice or cartesian)
    if line[:6] == 'coordi':
        line = file.readline()
        opts['coordi'] = line.strip()
        line = file.readline()

    # Problem scaling
    # RPM: Need to do a better job of this:
    #if line[:6] == 'scalep' or (line[:5] == 'scale' and len(line) == 5):
    if line[:6] == 'scalep' or line[:6] == 'scale\n':
        line = file.readline()
        opts['scalep'] = float(line.strip())
        line = file.readline()

    if line[:6] == 'scaleu':
        line = file.readline()
        opts['scaleu'] = float(line.strip())
        line = file.readline()

    if line[:6] == 'scalex':
        line = file.readline()
        opts['scalex'] = float(line.strip())
        line = file.readline()

    if line[:6] == 'scaley':
        line = file.readline()
        opts['scaley'] = float(line.strip())
        line = file.readline()

    if line[:6] == 'scalez':
        line = file.readline()
        opts['scalez'] = float(line.strip())
        line = file.readline()

    # Strain
    if line[:6] == 'strain':
        line = file.readline()
        xx, xy, xz = map(float, line.split())
        line = file.readline()
        yx, yy, yz = map(float, line.split())
        line = file.readline()
        zx, zy, zz = map(float, line.split())
        opts['strain'] = (xx, xy, xz, yx, yy, yz, zx, zy, zz)
        line = file.readline()
    if line[:6] == 'strfac':
        line = file.readline()
        opts['strfac'] = float(line.strip())
        line = file.readline()

    # Lattice vectors:
    if line[:6] == 'primit':
        line = file.readline()
        ax, ay, az = map(float, line.split())
        axyz = ax * bohr2ang, ay * bohr2ang, az * bohr2ang
        line = file.readline()
        bx, by, bz = map(float, line.split())
        bxyz = bx * bohr2ang, by * bohr2ang, bz * bohr2ang
        line = file.readline()
        cx, cy, cz = map(float, line.split())
        cxyz = cx * bohr2ang, cy * bohr2ang, cz * bohr2ang
        cell = Cell(axyz, bxyz, cxyz)
        line = file.readline()

    # grid dimensions
    if line[:6] == 'grid d' or line[:6] == 'points':
        line = file.readline()
        opts['griddim'] = map(int, line.split())
        line = file.readline()

    # nearby function
    if line[:6] == 'nearby':
        line = file.readline()
        opts['nearby'] = int(line.strip())
        line = file.readline()

    # number of atom types
    if line[:6] == 'atom t':
        line = file.readline()
        opts['ntyp'] = int(line.strip())
        opts['types'] = []
        line = file.readline()
    else:
        print line, len(line)
        raise "Number of atom types must be specified"

    # atom types:
    for i in range(opts['ntyp']):
        if line[:6] == 'atom f':
            line = file.readline()
            opts['types'].append(line.strip())
            line = file.readline()
        else:
            raise "Error: expecting another atom file"

    # number of atoms
    if line[:6] == 'number':
        line = file.readline()
        opts['nat'] = int(line.strip())
        line = file.readline()

    if line[:6] == 'atom, ':
        for i in range(opts['nat']):
            line = file.readline()
            words = line.split()
            inum = int(words[0])
            ityp = int(words[1])
            x, y, z = map(float, words[2:5])
            xyz = x * bohr2ang, y * bohr2ang, z * bohr2ang
            xyz = array(xyz)
            sym = cleansym(opts['types'][ityp - 1])
            atno = sym2no[sym]
            material.add_atom(Atom(atno, xyz))
        line = file.readline()
        material.set_cell(cell)
        material.bonds_from_distance()
    else:
        raise "Error: expected atom listing here"

    # to lattice/to cartesian
    if line[:6] == 'to_lat':
        opts['to_lat'] = True
        line = file.readline()
    elif line[:6] == 'to_car':
        opts['to_car'] = True
        line = file.readline()

    # origin offset
    if line[:6] == 'origin':
        line = file.readline()
        opts['dorig'] = map(float, line.split())
        line = file.readline()

    # wigner-seitz origin
    if line[:6] == 'wigner':
        line = file.readline()
        opts['rchrg'] = map(float, line.split())
        line = file.readline()

    # center of symmetry
    if line[:6] == 'symmet':
        line = file.readline()
        opts['rsym'] = map(float, line.split())
        line = file.readline()

    # bloch info
    if line[:5] == 'kgrid':
        line = file.readline()
        opts['kgrid'] = map(int, line.split())
        line = file.readline()
    elif line[:4] == 'khex':
        line = file.readline()
        opts['khex'] = map(int, line.split())
        line = file.readline()

    # skipping more detailed bloch info for now
    if line[:6] == 'n bloc':
        line = file.readline()
        opts['nk'] = int(line.strip())
        line = file.readline()

    if line[:6] == 'scalin':
        line = file.readline()
        opts['scalin'] = map(float, line.split())
        line = file.readline()

    if line[:6] == 'lattic':
        line = file.readline()
        opts['bloch_lattic'] = map(float, line.split())
        line = file.readline()
    elif line[:6] == 'cartes':
        line = file.readline()
        opts['bloch_cartes'] = map(float, line.split())
        line = file.readline()

    if line[:6] == 'bloch ':
        opts['bloch_vecs'] = []
        for i in range(opts['nk']):
            line = file.readline()
            opts['bloch_vecs'].append(map(float, line.split()))
        line = file.readline()

    # symmetry info
    if line[:6] == 'symops':
        line = file.readline()
        opts['nsymi'] = int(line.strip())
        line = file.readline()

    if line[:6] == 'defini':
        opts['symvecs'] = []
        for i in range(opts['nsymi']):
            line = file.readline()
            words = line.split()
            type = int(words[0])
            s1, s2, s3, s4, s5, s6 = map(float, words[1:])
            opts['symvecs'].append((type, s1, s2, s3, s4, s5, s6))
        line = file.readline()

    if line[:6] == 'end se':
        line = file.readline()
    else:
        raise "Expected end setup phase tag"
    # End of setup info

    # Beginning of Run Data
    if line[:6] == 'run ph':
        while 1:
            line = file.readline()
            if not line: break
            if line[:6] == 'end ru' or line[:6] == 'end of':
                break
            elif line[:6] == 'do fla':
                opts['doflag'] = True
            elif line[:6] == 'no fla':
                opts['doflag'] = False
            elif line[:6] == 'first ':
                line = file.readline()
                opts['itstart'] = int(line.strip())
            elif line[:6] == 'last i':
                line = file.readline()
                opts['itstop'] = int(line.strip())
            elif line[:6] == 'histor':
                line = file.readline()
                opts['nhiste'] = int(line.strip())
            elif line[:6] == 'restar':
                line = file.readline()
                opts['itrst'] = int(line.strip())
            elif line[:6] == 'states':
                line = file.readline()
                opts['nstate'] = int(line.strip())
            elif line[:6] == 'temper':
                line = file.readline()
                opts['etemp'] = float(line.strip())
            elif line[:6] == 'blend ' or line[:6] == 'percen':
                line = file.readline()
                opts['scfblnd'] = float(line.strip())
            elif line[:6] == 'scfbl2':
                line = file.readline()
                opts['scfbl2'] = float(line.strip())
            elif line[:6] == 'conver':
                line = file.readline()
                opts['scfconv'] = float(line.strip())
            elif line[:6] == 'alfast':
                line = file.readline()
                opts['alfast'] = float(line.strip())
            elif line[:6] == 'cutii ':
                line = file.readline()
                opts['convii'] = float(line.strip())
            elif line[:6] == 'cutslo':
                line = file.readline()
                opts['convsl'] = float(line.strip())
            elif line[:6] == 'cut2s ':
                line = file.readline()
                opts['conv2s'] = float(line.strip())
            elif line[:6] == 'cutset':
                line = file.readline()
                opts['cutset'] = float(line.strip())
            elif line[:6] == 'cutfrc':
                line = file.readline()
                opts['cutfrc'] = float(line.strip())
            elif line[:6] == 'cutgrd':
                line = file.readline()
                opts['convgr'] = float(line.strip())
            elif line[:6] == 'cut1c ':
                line = file.readline()
                opts['conv1c'] = float(line.strip())
            elif line[:6] == 'geomet':
                # Jump into Geometry Data
                opts['write_geo_sect'] = True
                while 1:
                    line = file.readline()
                    if line[:4] == 'stop' or line[:3] == 'end':
                        break
                    elif line[:6] == 'relax ':
                        opts['dorelax'] = True
                        opts['geo_dorelax'] = True
                    elif line[:6] == 'grelax':
                        line = file.readline()
                        opts['relax_range'] = map(int, line.split())
                    elif line[:6] == 'gfixed':
                        line = file.readline()
                        opts['fixed_range'] = map(int, line.split())
                    elif line[:6] == 'only r':
                        line = file.readline()
                        opts['only_relax'] = int(line.strip())
                    elif line[:6] == 'frame ':
                        line = file.readline()
                        opts['relax_frame'] = map(int, line.split())
                    elif line[:6] == 'defect':
                        line = file.readline()
                        opts['defect'] = int(line.strip())
                    elif line[:6] == 'gblend':
                        line = file.readline()
                        opts['gblend'] = float(line.strip())
                    elif line[:5] == 'gconv':
                        line = file.readline()
                        opts['gconv'] = float(line.strip())
                    elif line[:6] == 'gstart':
                        line = file.readline()
                        opts['gstart'] = int(line.strip())
                    elif line[:6] == 'gsteps':
                        line = file.readline()
                        opts['gsteps'] = int(line.strip())
                    elif line[:6] == 'ghisto':
                        line = file.readline()
                        opts['nhistg'] = int(line.strip())
                    elif line[:6] == 'no ges':
                        opts['igges'] = 0
                    elif line[:6] == 'guess ':
                        line = file.readline()
                        opts['igges'] = int(line.strip())
                    elif line[:6] == 'gmetho':
                        line = file.readline()
                        opts['gmethod'] = line.strip()
                    elif line[:6] == 'timest':
                        line = file.readline()
                        opts['gtstep'] = float(line.strip())
                    else:
                        print "Unknown geomdata line:"
                        print line
                # End of Geometry Data
            elif line[:5] == 'cell ':
                # Jump into Cell Data
                opts['write_cell_sect'] = True
                while 1:
                    line = file.readline()
                    if line[:6] == 'end ce':
                        break
                    elif line[:6] == 'ucstep':
                        line = file.readline()
                        opts['maxucsteps'] = int(line.strip())
                    elif line[:6] == 'ucconv':
                        line = file.readline()
                        opts['ucconv'] = float(line.strip())
                    elif line[:6] == 'pressu':
                        line = file.readline()
                        opts['pressure'] = float(line.strip())
                    elif line[:6] == 'uniaxi':
                        line = file.readline()
                        opts['uniaxial'] = map(float, line.split())
                    elif line[:6] == 'stress':
                        opts['stress'] = []
                        for i in range(opts['ndim']):
                            line = file.readline()
                            opts['stress'].append(map(float, line.split()))
                    elif line[:6] == 'uchist':
                        line = file.readline()
                        opts['nhistuc'] = int(line.strip())
                    elif line[:6] == 'ucmeth':
                        line = file.readline()
                        opts['ucmeth'] = line.strip()
                    elif line[:6] == 'str_br':
                        line = file.readline()
                        opts['strsbroy'] = float(line.strip())
                    elif line[:6] == 'max_st':
                        line = file.readline()
                        opts['strnmax'] = float(line.strip())
                    elif line[:6] == 'cell_f':
                        line = file.readline()
                        opts['cell_f'] = float(line.strip())
                    elif line[:6] == 'bulk_m':
                        line = file.readline()
                        opts['bmod'] = float(line.strip())
                    elif line[:6] == 'uc_ble':
                        line = file.readline()
                        opts['ucblend'] = float(line.strip())
                    else:
                        print "Unknown celldata line:"
                        print line
                # End of Cell Data
            else:
                print "Unknown rundata line:"
                print line
    # End of Run Data

    # Start of MD Data
    line = file.readline()
    if line[:6] == 'md dat':
        while 1:
            line = file.readline()
            if line[:3] == 'end':
                break
            elif line[:6] == 'temper':
                line = file.readline()
                opts['mdtemp'] = float(line.strip())
            elif line[:6] == 'time s':
                line = file.readline()
                opts['ntstep'] = int(line.strip())
            elif line[:6] == 'equil ':
                line = file.readline()
                opts['neqsteps'] = int(line.strip())
            elif line[:6] == 'step s':
                line = file.readline()
                opts['md_dt'] = float(line.strip())
            elif line[:6] == 'md typ':
                line = file.readline()
                opts['mdtype'] = line.strip()
            else:
                print "Unknown md flag"
                print line
    return material
예제 #23
0
def build_the_slab(material, cleave_dir, depth, vacuum):
    name = material.get_name()
    cell = material.get_cell()
    atomlist = material.get_atom_list()
    if not cleave_dir: cleave_dir = 'C'

    axyz = cell.axyz
    bxyz = cell.bxyz
    cxyz = cell.cxyz

    if depth == 1 and vacuum == 0:
        return material  # do nothing

    newname = "%s_slab" % name
    newmaterial = Material(newname)
    #
    # Replace abc -> uvw (w is the cleave direction) so we can
    # cleave in more general ways:
    #
    if cleave_dir == "C":
        uxyz = axyz
        vxyz = bxyz
        wxyz = cxyz
        idir = 2
    elif cleave_dir == "B":
        uxyz = cxyz
        vxyz = axyz
        wxyz = bxyz
        idir = 1
    elif cleave_dir == "A":
        uxyz = bxyz
        vxyz = cxyz
        wxyz = axyz
        idir = 0

    wlength = sqrt(dot(wxyz, wxyz))
    wscale = (wlength * depth + vacuum) / wlength
    nwxyz = wxyz * wscale

    for atom in atomlist:
        atno = atom.get_atno()
        xyz = atom.get_position()
        for k in range(depth):
            xyznew = xyz + k * wxyz
            xyznew[idir] += vacuum / 2.
            newmaterial.add_atom(Atom(atno, xyznew))
        if abs(xyz[idir]) < 1e-2:  # Periodic image of bottom:
            xyznew = xyz + depth * wxyz
            xyznew[idir] += vacuum / 2.
            newmaterial.add_atom(Atom(atno, xyznew))

    # I can't tell whether I have to do the cyclic permutations here
    #  i.e. output w,u,v in some cases.
    newmaterial.set_cell(Cell(uxyz, vxyz, nwxyz))

    opts = getattr(material, "seqquest_options", {})
    if opts: newmaterial.seqquest_options = opts.copy()

    opts = getattr(material, "socorro_options", {})
    if opts: newmaterial.socorro_options = opts.copy()

    newmaterial.center()
    newmaterial.bonds_from_distance()
    return newmaterial
예제 #24
0
def create_nanotube_material(n, m, ncells):
    bondlength = 1.35  # Angstroms
    buffer = 2  # Angstroms to pack around nt in uc

    np, nq, ndr = gen11(n, m)

    rt3 = sqrt(3)

    a = rt3 * bondlength
    r = a * sqrt(np * np + nq * nq + np * nq)
    c = a * sqrt(n * n + m * m + n * m)
    t = rt3 * c / ndr
    rs = c / 2 / pi
    nn = 2 * (n * n + m * m + n * m) / ndr  # hexagons in unit cell N

    #print 'Nanotube unit cell length ',t
    #print 'Nanotube radius ',rs
    #print 'Nanotube unit cell atoms ',nn*2

    q1 = atan((rt3 * m) / (2 * n + m))  # Chiral angle for C_h
    q2 = atan((rt3 * nq) / (2 * np + nq))  # Chiral angle for R
    q3 = q1 - q2  # Angle btw C_h and R
    q4 = 2 * pi / nn  # Period of angle for A atom
    q5 = bondlength * cos(pi / 6 - q1) / c * 2 * pi
    #   diff of the angle btw A and B atoms
    h1 = abs(t) / abs(sin(q3))
    h2 = bondlength * sin(pi / 6 - q1)  # dz btw A and B atoms

    xyz = []
    for i in range(nn):
        # A atom
        k = int(i * abs(r) / h1)
        x1 = rs * cos(i * q4)
        y1 = rs * sin(i * q4)
        z1 = (i * abs(r) - k * h1) * sin(q3)
        kk2 = abs(int(z1 / t)) + 1

        # Insure A in unit cell
        if z1 > t - 0.02: z1 -= t * kk2
        if z1 < -0.02: z1 += t * kk2

        xyz.append((x1, y1, z1))

        # B atom
        # Insure B in unit cell
        z3 = (i * abs(r) - k * h1) * sin(q3) - h2
        if z3 > -0.02 and z3 < t - 0.02:
            x2 = rs * cos(i * q4 + q5)
            y2 = rs * sin(i * q4 + q5)
            z2 = (i * abs(r) - k * h1) * sin(q3) - h2
            xyz.append((x2, y2, z2))
        else:
            x2 = rs * cos(i * q4 + q5)
            y2 = rs * sin(i * q4 + q5)
            z2 = (i * abs(r) - (k + 1) * h1) * sin(q3) - h2
            kk = abs(int(z2 / t)) + 1
            if z2 > t - 0.01: z2 -= t * kk
            if z2 < -0.01: z2 += t * kk
            xyz.append((x2, y2, z2))

    xyznew = []
    ii = 0
    dxy = rs + buffer
    for j in range(ncells):
        dz = j * t
        for i in range(2 * nn):
            x, y, z = xyz[i]
            xyznew.append((x + dxy, y + dxy, z + dz))

    #for x,y,z in xyznew: print " C %10.4f %10.4f %10.4f" % (x,y,z)

    material = Material('nanotube%d%d%d' % (ncells, n, m))
    for xyz in xyznew:
        material.add_atom(Atom(6, array(xyz)))

    material.bonds_from_distance()
    material.set_cell(
        Cell((2 * dxy, 0, 0), (0, 2 * dxy, 0), (0, 0, ncells * t)))
    return material
예제 #25
0
def load(fullfilename):
    gstep = 0
    filedir, fileprefix, fileext = path_split(fullfilename)
    file=open(fullfilename, 'r')
    
    # Initialize atom data
    material = Material(fileprefix)
    opts = {}
    material.seqquest_options = opts

    dconv = 1. # default to Angstroms, which don't need conversion
    cell = None

    while 1:
        line = file.readline()
        if not line: break
        line = line.strip()
        if line == '@=KEYCHAR':
            continue # ignore other keychars for now
        elif line == '@DISTANCE UNIT':
            line = file.readline().strip()
            if line == 'ANGSTROM':
                continue
            elif line == 'BOHR':
                dconv = bohr2ang
            else:
                print "Warning: unknown distance unit ",line
        elif line == '@DIMENSION':
            line = file.readline().strip()
            opts['ndim'] = int(line)
        elif line == '@NUMBER OF ATOMS':
            line = file.readline().strip()
            opts['nat'] = int(line)
            opts['attypes'] = []
            nread = int(ceil(opts['nat']/20.))
            for i in range(nread):
                line = file.readline().strip()
                opts['attypes'].extend(map(int,line.split()))
            assert len(opts['attypes']) == opts['nat']
        elif line == '@TYPES':
            line = file.readline().strip()
            opts['ntyp'] = int(line)
            opts['types'] = []
            for i in range(opts['ntyp']):
                line = file.readline().strip()
                opts['types'].append(cleansym(line))
        elif line == '@CELL VECTORS':
            line = file.readline()
            axyz = map(float,line.split())
            line = file.readline()
            bxyz = map(float,line.split())
            line = file.readline()
            cxyz = map(float,line.split())
            if abs(dconv-1) > 1e-4: # careful when comparing floats
                axyz = axyz[0]*dconv,axyz[1]*dconv,axyz[2]*dconv
                bxyz = bxyz[0]*dconv,bxyz[1]*dconv,bxyz[2]*dconv
                cxyz = cxyz[0]*dconv,cxyz[1]*dconv,cxyz[2]*dconv
            cell = Cell(axyz,bxyz,cxyz)
        elif line == '@GSTEP':
            line = file.readline().strip()
            gstep = int(line)
        elif line == '@COORDINATES':
            atoms = []
            for i in range(opts['nat']):
                line = file.readline()
                xyz = map(float,line.split())
                if abs(dconv-1) > 1e-4: # careful when comparing floats
                    xyz = xyz[0]*dconv,xyz[1]*dconv,xyz[2]*dconv
                isym = opts['attypes'][i]
                sym = opts['types'][isym-1]
                atoms.append((sym,xyz))
            if gstep > 1: material.new_geo()
            for i in range(opts['nat']):
                sym,xyz = atoms[i]
                atno = sym2no[sym]
                xyz = array(xyz)
                material.add_atom(Atom(atno,xyz))
            if cell: material.set_cell(cell)
        elif line == '@ESCF':
            line = file.readline().strip()
            escf = float(line)
            # Consider saving these for plotting
        elif line == '@FORCES':
            forces = []
            for i in range(opts['nat']):
                line = file.readline()
                forces.append(map(float,line.split()))
        elif line == '@FMAX':
            line = file.readline().strip()
            fmax = float(line)
        elif line == '@FRMS':
            line = file.readline().strip()
            frms = float(line)
        else:
            print "Unknown line ",line
    material.bonds_from_distance()
    return material