예제 #1
0
파일: protein.py 프로젝트: bwbai/bpforms
    def is_n_terminus(self, mol, atom):
        """ Determine if an atom is an N-terminus

        Args:
            mol (:obj:`openbabel.OBMol`): molecule
            atom (:obj:`openbabel.OBAtom`): atom

        Returns:
            :obj:`bool`: :obj:`True` if the atom is an N-terminus
        """
        if atom is None:
            return False

        # check atom is nitrogen
        if atom.GetAtomicNum() != 7:
            return False

        # check atom has charge 0 or +1
        if atom.GetFormalCharge() < 0:
            return False

        # check atom is single-bonded to at least 1 carbon
        has_single_c = False
        for bond in openbabel.OBAtomBondIter(atom):
            other_atom = bond.GetBeginAtom()
            if other_atom == atom:
                other_atom = bond.GetEndAtom()
            if bond.GetBondOrder() == 1 and other_atom.GetAtomicNum() == 6:
                has_single_c = True
        if not has_single_c:
            return False

        # check atom can form another bond
        other_atoms = [
            other_atom.GetAtomicNum()
            for other_atom in openbabel.OBAtomAtomIter(atom)
        ]
        tot_bond_order = sum(
            [bond.GetBondOrder() for bond in openbabel.OBAtomBondIter(atom)])
        other_atoms += [1] * (3 + atom.GetFormalCharge() - tot_bond_order)
        n_charge = atom.GetFormalCharge()
        n_h = other_atoms.count(1)
        if not ((n_charge == 1 and n_h >= 2) or
                (n_charge == 0 and (n_h >= 1 or len(other_atoms) <= 2))):
            return False

        # return True
        return True
예제 #2
0
    def adjust_info(self, obatom):
        '''
        If a atom is bonded to polarhydrogen or heteroatom
        :param obatom: openbabel OBAtom istance
        :return: bond_2_hd, bond_2_hetero : boolean
        '''
        bonds = list(openbabel.OBAtomBondIter(obatom))
        atom_id = obatom.GetId()

        bond_2_hd = False
        bond_2_hetero = False
        for bond in bonds:
            begin = bond.GetBeginAtom().GetId()
            end = bond.GetEndAtom().GetId()
            if atom_id == begin:
                link_atom = bond.GetEndAtom()
            elif atom_id == end:
                link_atom = bond.GetBeginAtom()
            else:
                raise Exception("Wrong bond")

            if link_atom.IsHydrogen():
                # all the remained hydrogen is polarhydrogen
                bond_2_hd = True
            if link_atom.IsHeteroatom():
                bond_2_hetero = True

        return bond_2_hd, bond_2_hetero
예제 #3
0
def get_torsion(mol, ob_atom_idx_0, ob_atom_idx_1):
    """Get torsion between the two coupled atoms. The function is relevant for
    atoms in a 3J coupling

    Arguments:
        mol {OBMol} -- OpenBabel molecule object
        ob_atom_idx_0 {int} -- index of atom 0 in OpenBabel
        ob_atom_idx_1 {int} -- index of atom 1 in OpenBabel

    Returns:
        float -- torsion value for the coupled pair
    """

    atom_0 = mol.GetAtom(ob_atom_idx_0)
    atom_1 = mol.GetAtom(ob_atom_idx_1)

    for bond in ob.OBAtomBondIter(atom_0):

        end_atom_idx = bond.GetEndAtomIdx()

        if end_atom_idx == atom_0.GetIdx():
            pivot_1 = bond.GetBeginAtom()
        else:
            pivot_1 = bond.GetEndAtom()

        pivot_2 = get_torsion_pivot(mol, atom_1.GetIdx(), pivot_1.GetIdx())

        if pivot_2:
            return mol.GetTorsion(atom_0, pivot_1, pivot_2, atom_1)

    return 0
예제 #4
0
def get_angle(mol, ob_atom_idx_0, ob_atom_idx_1):
    """Get the angle between two atoms. The function is relevant for atoms in
    a 2J coupling

    Arguments:
        mol {OBMol} -- OpenBabel molecule object
        ob_atom_idx_0 {int} -- index of atom 0 in OpenBabel
        ob_atom_idx_1 {int} -- index of atom 1 in OpenBabel

    Returns:
        float -- value of angle between coupled atoms
    """

    atom_0 = mol.GetAtom(ob_atom_idx_0)
    atom_1 = mol.GetAtom(ob_atom_idx_1)

    for bond in ob.OBAtomBondIter(atom_0):

        end_atom_idx = bond.GetEndAtomIdx()

        if end_atom_idx == atom_0.GetIdx():
            pivot_atom = bond.GetBeginAtom()
        else:
            pivot_atom = bond.GetEndAtom()

        missing_bond = atom_1.GetBond(pivot_atom)

        if missing_bond:
            return mol.GetAngle(atom_0, pivot_atom, atom_1)

    return 0
예제 #5
0
def get_torsion_pivot(mol, ob_atom_idx_0, ob_atom_idx_1):
    """Find pivot atom of a torsion

    Arguments:
        mol {OBMol} -- OpenBabel molecule object
        ob_atom_idx_0 {int} -- index of atom 0 in OpenBabel
        ob_atom_idx_1 {int} -- index of atom 1 in OpenBabel

    Returns:
        OBAtom -- torsion pivot atom
    """

    atom_0 = mol.GetAtom(ob_atom_idx_0)
    atom_1 = mol.GetAtom(ob_atom_idx_1)

    for bond in ob.OBAtomBondIter(atom_0):

        end_atom_idx = bond.GetEndAtomIdx()

        if end_atom_idx == atom_0.GetIdx():
            pivot_atom = bond.GetBeginAtom()
        else:
            pivot_atom = bond.GetEndAtom()

        missing_bond = atom_1.GetBond(pivot_atom)

        if missing_bond:
            return pivot_atom

    return None
예제 #6
0
def Torsion3J(molname, AtomId1, AtomId2, mol, debug=False):
    mol, firstAtom, lastAtom = Atoms(molname, AtomId1, AtomId2, mol)
    if debug: print(molname, mol.GetFormula())
    if debug:
        print(firstAtom.GetType(), firstAtom.GetId(), ':', lastAtom.GetType(),
              lastAtom.GetId())
    for b in openbabel.OBAtomBondIter(firstAtom):  # all bonds for first atom
        secondAtom = SecondAtom(b, firstAtom)
        for b2 in openbabel.OBAtomBondIter(
                secondAtom):  # all bonds for second atom
            thirdAtom = SecondAtom(b2, secondAtom)
            lastBond = thirdAtom.GetBond(lastAtom)
            if lastBond:  # found!
                if debug:
                    print(secondAtom.GetType(), secondAtom.GetId(), '<->',
                          thirdAtom.GetType(), thirdAtom.GetId())
                return mol.GetTorsion(firstAtom, secondAtom, thirdAtom,
                                      lastAtom)
예제 #7
0
	def findInternalRotors(self, Mol):
		rotor = []
		for atom in openbabel.OBMolAtomIter(Mol):
			if not atom.IsHydrogen() and not atom.IsInRing():
				for bond in openbabel.OBAtomBondIter(atom):
					ptr = bond.GetNbrAtom(atom)
					if ptr.GetId() < atom.GetId(): continue
					elif bond.GetBO() == 1 and atom.BOSum() > 1 and ptr.BOSum() > 1 and not ptr.IsHydrogen():
						idx = [int(atom.GetId())+1, int(ptr.GetId())+1]
						rotor.append(idx)
		return rotor
예제 #8
0
def getatom_b(obatom, marker):
    b = str(0)
    if (marker == "0"):
        return '*'
    if (obatom.HasSingleBond()):
        b = 's'
    if (obatom.HasDoubleBond()):
        b = 'd'
    for obbond in ob.OBAtomBondIter(obatom):
        if (obbond.IsTriple()):
            b = 't'
            break
    i = 0
    for obbond in ob.OBAtomBondIter(obatom):
        if (obbond.IsDouble()):
            i += 1
    if (i > 1):
        b = 'w'
    if (obatom.HasAromaticBond()):
        b = 'd'
    return b
예제 #9
0
def Angle2J(molname, AtomId1, AtomId2, mol, debug=False):
    mol, firstAtom, lastAtom = Atoms(molname, AtomId1, AtomId2, mol)
    if debug: print(mol.GetFormula())
    if debug:
        print(firstAtom.GetType(), firstAtom.GetId(), ':', lastAtom.GetType(),
              lastAtom.GetId())
    for b in openbabel.OBAtomBondIter(firstAtom):  # all bonds for first atom
        secondAtom = SecondAtom(b, firstAtom)
        lastBond = secondAtom.GetBond(lastAtom)
        if lastBond:  # found!
            if debug: print('middle', secondAtom.GetId(), secondAtom.GetType())
            return firstAtom.GetAngle(secondAtom, lastAtom)
예제 #10
0
    def _get_neighbors(self, obatom):
        """ trick or treat? """

        neighbors = []
        for bond in ob.OBAtomBondIter(obatom):
            end = bond.GetEndAtom()
            bgn = bond.GetBeginAtom()
            if bgn == obatom:
                neighbors.append(end.GetIndex())  # Index is 0-indexed
            elif end == obatom:
                neighbors.append(bgn.GetIndex())
            else:
                raise RuntimeError
        return neighbors
예제 #11
0
 def get_bom(self):
     """
     get connectivity table
     """
     bom = np.zeros((self.na, self.na), np.int)
     for i in range(1, self.na + 1):
         ai = self.m.GetAtom(i)
         for bond in ob.OBAtomBondIter(ai):
             ia1 = bond.GetBeginAtomIdx() - 1
             ia2 = bond.GetEndAtomIdx() - 1
             bo = bond.GetBO()
             bom[ia1, ia2] = bo
             bom[ia2, ia1] = bo
     return bom
예제 #12
0
def get_bom(m):
    na = m.NumAtoms()
    bom = np.zeros((na, na), dtype=int)
    for i in range(na):
        ai = m.GetAtomById(i)
        for bond in ob.OBAtomBondIter(ai):
            ab, ae = bond.GetBeginAtom(), bond.GetEndAtom()
            ib1 = ab.GetIdx() - 1
            ie1 = ae.GetIdx() - 1
            #ib2 = ab.GetId(); ie2 = ae.GetId()
            #print i, ' -- ', ib1,ie1, ib2,ie2
            bo = bond.GetBO()
            bom[ib1, ie1] = bo
            bom[ie1, ib1] = bo
    return bom
예제 #13
0
    def test_atom_iteration(self):
        mol = parse_smiles("[U](F)(F)(F)[Cl]")
        atom = mol.GetAtom(1)

        counts = {9: 0, 17: 0}
        for bond in ob.OBAtomBondIter(atom):
            xatom = bond.GetNbrAtom(atom)
            n = xatom.GetAtomicNum()
            counts[n] += 1
        self.assertEqual(counts, {9: 3, 17: 1})

        counts = {9: 0, 17: 0}
        for atom in ob.OBAtomAtomIter(atom):
            n = atom.GetAtomicNum()
            counts[n] += 1
        self.assertEqual(counts, {9: 3, 17: 1})
예제 #14
0
	def perceiveBondOrders(self, Molecule, Atom):
		# . generate OBMol
		frag = openbabel.OBMol()
		atoms = [None] + Molecule
		for i in Molecule:
			frag.AddAtom(Atom[i].atom)
			[frag.AddBond(atoms.index(Atom[i].id), atoms.index(bond), 1) for bond in Atom[i].bonds if Atom[i].id in atoms and bond in atoms]
		frag.AssignSpinMultiplicity(True)
		# . find potential multi-bonds
		multi = [[], []]
		for atom in openbabel.OBMolAtomIter(frag):
			if atom.GetSpinMultiplicity() > 0:
				for bond in openbabel.OBAtomBondIter(atom):
					ptr = bond.GetNbrAtom(atom)
					if ptr.GetSpinMultiplicity() > 0:
						aidx = atom.GetIdx();pidx = ptr.GetIdx()
						bo= Atom[atoms[aidx]].bonds[atoms[pidx]]
						if (pidx, aidx) in multi[1]: continue
						multi[0].append(bo-1.0)
						multi[1].append((aidx, pidx))
		# . sort in order of decreasing bond orders
		multi = sorted(zip(multi[0], multi[1]), reverse=True)
		# . loop over bonds in <multi> and set multi-bonds
		while multi:
			bond = list(multi[0]); del multi[0]
			atom = frag.GetAtom(bond[1][0])
			btom = frag.GetAtom(bond[1][1])
			if atom.GetSpinMultiplicity() > 0 and btom.GetSpinMultiplicity() > 0:
				tmp = frag.GetBond(atom, btom)
				tmp.SetBO(tmp.GetBO() +1)
				atom = self.decreaseMultiplicity(Atom=atom)
				atom.DecrementImplicitValence()
				btom = self.decreaseMultiplicity(Atom=btom)
				btom.DecrementImplicitValence()
				bond[0] -= 1.0
				if bond[0] > 0: multi.append(tuple(bond))
			multi = sorted(multi, reverse=True)
		# . return SMILES
		self.conv.SetInAndOutFormats('mdl', 'can')
		return self.conv.WriteString(frag).strip().replace('@@','@')
예제 #15
0
    def test_rings(self):
        mol = parse_smiles("C12CNCC3C1.C2CCC3")
        atom = mol.GetAtom(1)
        self.assertTrue(atom.IsInRing())
        self.assertTrue(atom.IsInRingSize(6))
        self.assertTrue(atom.IsInRingSize(7))
        self.assertFalse(atom.IsInRingSize(10))
        self.assertEqual(atom.MemberOfRingCount(), 2)
        self.assertEqual(atom.MemberOfRingSize(), 6)
        self.assertEqual(atom.CountRingBonds(), 3)

        sssr = mol.GetSSSR()
        self.assertEqual(len(sssr), 2)
        ring_info = [(ring.Size(), ring) for ring in sssr]
        ring_info.sort()

        sizes = [x[0] for x in ring_info]
        self.assertEqual(sizes, [6, 7])

        ring = ring_info[0][1]
        self.assertFalse(ring.IsAromatic())
        self.assertEqual(ring.GetType(), "")
        # XXX *which* of the non-carbons is the root? That isn't documented
        idx = ring.GetRootAtom() # Shouldn't that be "Idx"?
        # Since there's only one non-C, it must be the N
        atom = mol.GetAtom(idx)
        self.assertEqual(atom.GetAtomicNum(), 7)
        self.assertTrue(ring.IsMember(atom))
        for bond in ob.OBAtomBondIter(atom):
            self.assertTrue(ring.IsMember(bond))
        self.assertTrue(ring.IsInRing(idx))


        lssr = mol.GetLSSR()
        self.assertEqual(len(lssr), 2)
        sizes = [ring.Size() for ring in lssr]
        sizes.sort()
        self.assertEqual(sizes, [6, 7])
예제 #16
0
def molToMat(mol):
    n = mol.NumAtoms()
    # mat = np.zeros((n+3, n+1), dtype=int)
    mat = [[0 for _i in range(n + 1)] for _j in range(n + 3)]
    for i in range(1, n + 1):
        mat[i][0] = mol.GetAtom(i).GetAtomicNum()
        mat[0][i] = mat[i][0]
    for atom in ob.OBMolAtomIter(mol):
        i = atom.GetIdx()
        nBonds = 0
        for bond in ob.OBAtomBondIter(atom):
            nBonds += bond.GetBondOrder()
        nonBondingElecs = numValenceElectron(
            atom.GetAtomicNum()) - nBonds - atom.GetFormalCharge()
        mat[i][i] = nonBondingElecs
        mat[n + 1][i] = nBonds
        mat[n + 2][i] = atom.GetFormalCharge()
    for bond in ob.OBMolBondIter(mol):
        i = bond.GetBeginAtomIdx()
        j = bond.GetEndAtomIdx()
        mat[i][j] = bond.GetBondOrder()
        mat[j][i] = mat[i][j]
    return mat
예제 #17
0
파일: utils.py 프로젝트: PDBeurope/arpeggio
def get_single_bond_neighbour(ob_atom):
    """[summary]

    Args:
        ob_atom ([type]): [description]

    Returns:
        [type]: [description]
    """ '''
    '''

    for bond in ob.OBAtomBondIter(ob_atom):

        if not bond.IsSingle():
            continue

        current_neighbour = bond.GetNbrAtom(ob_atom)

        if current_neighbour.IsHydrogen():
            continue

        return current_neighbour

    return None
예제 #18
0
def extract_ligand(obmol, res_name='INH'):
    """
    This function is used to extract the ligands which are always named 'INH'
    from CSAR structures.
    """
    ligand = ob.OBMol()

    for residue in ob.OBResidueIter(obmol):
        if residue.GetName() == res_name:

            mapping = {}

            # insert the ligand atoms into the new molecule
            for i, atom in enumerate(ob.OBResidueAtomIter(residue), 1):
                ligand.InsertAtom(atom)
                mapping[atom.GetIdx()] = i

            # re-create the bonds
            for atom in ob.OBResidueAtomIter(residue):
                for bond in ob.OBAtomBondIter(atom):
                    bgn_idx = mapping[bond.GetBeginAtomIdx()]
                    end_idx = mapping[bond.GetEndAtomIdx()]

                    ligand.AddBond(bgn_idx, end_idx, bond.GetBondOrder(),
                                   bond.GetFlags())

            # remove the ligand from the original structure
            for atom_idx in sorted(mapping.keys(), reverse=True):
                atom = obmol.GetAtom(atom_idx)
                obmol.DeleteAtom(atom)

            obmol.DeleteResidue(residue)

            break

    return pybel.Molecule(ligand)
예제 #19
0
def _bfs(mol, startatom, D):
    '''
  given openbabel molecule and a starting atom of type OBAtom,
  finds all bonds out to degree D via a breath-first search
  '''

    visited_atoms = set()
    atoms_to_add = []
    bonds_to_add = []
    queue = deque([(startatom, 0)])
    while queue:
        atom, depth = queue.popleft()
        index = atom.GetIndex()
        visited_atoms.add(index)
        atomtype = atom.GetType()
        if depth < D:
            for bond in ob.OBAtomBondIter(atom):
                if bond not in bonds_to_add:
                    bonds_to_add.append(bond)
        if depth < D:
            for atom in ob.OBAtomAtomIter(atom):
                if atom.GetIndex() not in visited_atoms:
                    queue.append((atom, depth + 1))
    return (bonds_to_add)
예제 #20
0
def make_structure(request):
    def makeResidue(mol, idx, aaatoms):
        res = mol.NewResidue()
        res.SetNum(idx)
        for atom in ob.OBMolAtomIter(mol):
            if atom.GetIdx() not in aaatoms:
                res.AddAtom(atom)

    aminoacids = request.GET.getlist("as")
    color = request.GET.get("rescol", "#3EC1CD")

    mol = ob.OBMol()
    conv = ob.OBConversion()
    pattern = ob.OBSmartsPattern()
    pattern.Init("[NX3][$([CX4H1]([*])),$([CX4H2])][CX3](=[OX1])[OX2]")
    builder = ob.OBBuilder()
    conv.SetInAndOutFormats("sdf", "svg")
    conv.AddOption("d", ob.OBConversion.OUTOPTIONS)
    conv.AddOption("b", ob.OBConversion.OUTOPTIONS, "none")
    conv.ReadString(mol, str(Substrate.objects.get(pk=int(aminoacids[0])).structure))
    pattern.Match(mol)
    mollist = pattern.GetUMapList()[0]
    oatom = mol.GetAtom(mollist[4])
    catom = mol.GetAtom(mollist[2])
    firstnatom = mol.GetAtom(mollist[0])
    makeResidue(mol, 0, mollist)

    i = 1
    for aa in aminoacids[1:]:
        mol2 = ob.OBMol()
        conv.ReadString(mol2, str(Substrate.objects.get(pk=int(aa)).structure))
        pattern.Match(mol2)
        mollist = pattern.GetUMapList()[0]
        makeResidue(mol2, i, mollist)

        molnatoms = mol.NumAtoms()
        mol += mol2

        natom = mol.GetAtom(molnatoms + mol2.GetAtom(mollist[0]).GetIdx())

        builder.Connect(mol, catom.GetIdx(), natom.GetIdx())

        foatom = mol.GetAtom(molnatoms + mol2.GetAtom(mollist[4]).GetIdx())
        catom = mol.GetAtom(molnatoms + mol2.GetAtom(mollist[2]).GetIdx())
        mol.DeleteHydrogens(oatom)
        mol.DeleteAtom(oatom)

        natom.SetImplicitValence(3)
        mol.DeleteHydrogens(natom)
        mol.AddHydrogens(natom)
        oatom = foatom

        i += 1

    nidx = firstnatom.GetIdx()
    oidx =  oatom.GetIdx()
    builder.Build(mol)
    natom = mol.GetAtom(nidx)
    oatom = mol.GetAtom(oidx)
    for res in ob.OBResidueIter(mol):
        for atom in ob.OBResidueAtomIter(res):
            for bond in ob.OBAtomBondIter(atom):
                data = ob.OBPairData()
                data.SetAttribute("color")
                data.SetValue(color)
                bond.CloneData(data)
    mol.DeleteHydrogens()
    gen2d = ob.OBOp.FindType("gen2d")
    gen2d.Do(mol)

    opp = oatom.GetY() - natom.GetY()
    adj = oatom.GetX() - natom.GetX()
    angle = abs(math.atan(opp / adj))
    if opp > 0 and adj > 0:
        pass
    elif opp > 0 and adj < 0:
        angle = math.pi - angle
    elif opp < 0 and adj < 0:
        angle = math.pi + angle
    elif opp < 0 and adj > 0:
        angle = 2 * math.pi - angle
    angle = -angle
    mol.Rotate(ob.double_array([math.cos(angle), -math.sin(angle), 0,
                                math.sin(angle), math.cos(angle),  0,
                                0,               0,                1]))
    svg = conv.WriteString(mol)
    # need to get rid of square aspect ratio
    delstart = svg.find("width")
    delend = svg.find("svg", delstart)
    delend = svg.find("viewBox", delend)
    svgend = svg.rfind("</g>")
    svg = svg[0:delstart] + svg[delend:svgend]
    return HttpResponse(svg, mimetype="image/svg+xml")
예제 #21
0
    def draw(self, show=True, filename=None, update=False, usecoords=False,
                   method="mcdl"):
        """Create a 2D depiction of the molecule.

        Optional parameters:
          show -- display on screen (default is True)
          filename -- write to file (default is None)
          update -- update the coordinates of the atoms to those
                    determined by the structure diagram generator
                    (default is False)
          usecoords -- don't calculate 2D coordinates, just use
                       the current coordinates (default is False)
          method -- two methods are available for calculating the
                    2D coordinates: OpenBabel's "mcdl" (the default), or
                    "oasa" (from the OASA toolkit)

        OASA is used for depiction. Tkinter and Python
        Imaging Library are required for image display.
        """
        etab = ob.OBElementTable()

        if not oasa:
            errormessage = ("OASA not found, but is required for depiction. "
                            "OASA is part of BKChem. "
                            "See installation instructions for more "
                            "information.")
            raise ImportError(errormessage)
        if method not in ["mcdl", "oasa"]:
            raise ValueError("Method '%s' not recognised. Should be either"
                               " 'mcdl' or 'oasa'.")

        workingmol = self
        if method == "mcdl":
            if not update: # Call gen2D on a clone
                workingmol = Molecule(self)
            if not usecoords:
                _operations['gen2D'].Do(workingmol.OBMol)
            usecoords = True # Use the workingmol's coordinates
                   
        mol = oasa.molecule()
        for atom in workingmol.atoms:
            v = mol.create_vertex()
            v.symbol = etab.GetSymbol(atom.atomicnum)
            v.charge = atom.formalcharge
            if usecoords:
                v.x, v.y, v.z = atom.coords[0] * 30., atom.coords[1] * 30., 0.0
            mol.add_vertex(v)

        for bond in ob.OBMolBondIter(workingmol.OBMol):
            e = mol.create_edge()
            e.order = bond.GetBO()
            if bond.IsHash():
                e.type = "h"
            elif bond.IsWedge():
                e.type = "w"
            mol.add_edge(bond.GetBeginAtomIdx() - 1,
                         bond.GetEndAtomIdx() - 1,
                         e)
        # I'm sure there's a more elegant way to do the following, but here goes...
        # let's set the stereochemistry around double bonds
        self.write("can") # Perceive UP/DOWNness
        for bond in ob.OBMolBondIter(workingmol.OBMol):
            ends = bond.GetBeginAtomIdx(), bond.GetEndAtomIdx()
            if bond.GetBO() == 2:
                stereobonds = [[b for b in ob.OBAtomBondIter(workingmol.OBMol.GetAtom(x)) if b.GetIdx() != bond.GetIdx() and (b.IsUp() or b.IsDown())]
                               for x in ends]
                if stereobonds[0] and stereobonds[1]: # Needs to be defined at either end
                    if stereobonds[0][0].IsUp() == stereobonds[1][0].IsUp():
                        # Either both up or both down
                        stereo = oasa.stereochemistry.cis_trans_stereochemistry.SAME_SIDE
                    else:
                        stereo = oasa.stereochemistry.cis_trans_stereochemistry.OPPOSITE_SIDE
                    atomids = [(b[0].GetBeginAtomIdx(), b[0].GetEndAtomIdx()) for b in stereobonds]
                    extremes = []
                    for id, end in zip(ends, atomids):
                        if end[0] == id:
                            extremes.append(end[1])
                        else:
                            extremes.append(end[0])
                    center = mol.get_edge_between(mol.atoms[ends[0] - 1], mol.atoms[ends[1] - 1])
                    st = oasa.stereochemistry.cis_trans_stereochemistry(
                              center = center, value = stereo,
                              references = (mol.atoms[extremes[0] - 1], mol.atoms[ends[0] - 1],
                                            mol.atoms[ends[1] - 1], mol.atoms[extremes[1] - 1]))
                    mol.add_stereochemistry(st)
        
        mol.remove_unimportant_hydrogens()
        if method == "oasa" and not usecoords:
            oasa.coords_generator.calculate_coords(mol, bond_length=30)
            if update:
                newcoords = [(v.x / 30., v.y / 30., 0.0) for v in mol.vertices]
                for atom, newcoord in zip(ob.OBMolAtomIter(self.OBMol), newcoords):
                    atom.SetVector(*newcoord)
        if filename or show:
            maxx = max([v.x for v in mol.vertices])
            minx = min([v.x for v in mol.vertices])
            maxy = max([v.y for v in mol.vertices])
            miny = min([v.y for v in mol.vertices])
            maxcoord = max(maxx - minx, maxy - miny)
            fontsize = 16
            bondwidth = 6
            linewidth = 2
            if maxcoord > 270: # 300  - margin * 2
                for v in mol.vertices:
                    v.x *= 270. / maxcoord
                    v.y *= 270. / maxcoord
                fontsize *= math.sqrt(270. / maxcoord)
                bondwidth *= math.sqrt(270. / maxcoord)
                linewidth *= math.sqrt(270. / maxcoord)
            if filename:
                filedes = None
            else:
                filedes, filename = tempfile.mkstemp()
            
            canvas = oasa.cairo_out.cairo_out()
            canvas.show_hydrogens_on_hetero = True
            canvas.font_size = fontsize
            canvas.bond_width = bondwidth
            canvas.line_width = linewidth
            canvas.mol_to_cairo(mol, filename)
            if show:
                if not tk:
                    errormessage = ("Tkinter or Python Imaging "
                                    "Library not found, but is required for image "
                                    "display. See installation instructions for "
                                    "more information.")
                    raise ImportError(errormessage)
                root = tk.Tk()
                root.title((hasattr(self, "title") and self.title)
                           or self.__str__().rstrip())
                frame = tk.Frame(root, colormap="new", visual='truecolor').pack()
                image = PIL.open(filename)
                imagedata = piltk.PhotoImage(image)
                label = tk.Label(frame, image=imagedata).pack()
                quitbutton = tk.Button(root, text="Close", command=root.destroy).pack(fill=tk.X)
                root.mainloop()
            if filedes:
                os.close(filedes)
                os.remove(filename)
예제 #22
0
def atomTotalBondOrder(atom):
    nBonds = 0
    for bond in ob.OBAtomBondIter(atom):
        nBonds += bond.GetBondOrder()
    return nBonds
예제 #23
0
파일: protein.py 프로젝트: bwbai/bpforms
    def set_termini(self, mol, monomer, i_n, i_c):
        """ Set the C and N terminal bond atoms of a monomer

        Args:
            mol (:obj:`openbabel.OBMol`): molecule
            monomer (:obj:`Monomer`): monomer
            i_n (:obj:`int`): index of N terminus
            i_c (:obj:`int`): index of C terminus
        """
        if i_c:
            c_atom = mol.GetAtom(i_c)
            i_o = None
            for bond in openbabel.OBAtomBondIter(c_atom):
                if bond.GetBondOrder() != 1:
                    continue

                o_atom = bond.GetBeginAtom()
                if o_atom.GetIdx() == c_atom.GetIdx():
                    o_atom = bond.GetEndAtom()

                if o_atom.GetAtomicNum() == 8:
                    other_atoms = sorted([
                        other_atom.GetAtomicNum()
                        for other_atom in openbabel.OBAtomAtomIter(o_atom)
                    ])
                    if len(other_atoms) == 1 or other_atoms[-2] == 1:
                        i_o = o_atom.GetIdx()
                        break

            if i_o:
                monomer.r_bond_atoms.append(
                    Atom(Monomer, element='C', position=i_c))
                if o_atom.GetFormalCharge() == 0:
                    monomer.r_displaced_atoms.append(
                        Atom(Monomer, element='O', position=i_o))
                    monomer.r_displaced_atoms.append(
                        Atom(Monomer, element='H', position=i_o))
                else:
                    monomer.r_displaced_atoms.append(
                        Atom(Monomer, element='O', position=i_o, charge=-1))

        if i_n:
            atom = mol.GetAtom(i_n)
            other_atoms = [
                other_atom.GetAtomicNum()
                for other_atom in openbabel.OBAtomAtomIter(atom)
            ]
            tot_bond_order = sum([
                bond.GetBondOrder() for bond in openbabel.OBAtomBondIter(atom)
            ])
            other_atoms += [1] * (3 + atom.GetFormalCharge() - tot_bond_order)
            n_charge = atom.GetFormalCharge()
            n_h = other_atoms.count(1)

            monomer.l_bond_atoms.append(
                Atom(Monomer, element='N', position=i_n, charge=-n_charge))
            if n_charge >= 0 and n_h >= 1:
                monomer.l_displaced_atoms.append(
                    Atom(Monomer, element='H', position=i_n))
            if n_charge >= 1 and n_h >= 2:
                monomer.l_displaced_atoms.append(
                    Atom(Monomer, element='H', position=i_n, charge=1))
예제 #24
0
파일: protein.py 프로젝트: bwbai/bpforms
    def is_c_terminus(self, mol, atom, residue=True, convert_to_aa=False):
        """ Determine if an atom is an C-terminus

        Args:
            mol (:obj:`openbabel.OBMol`): molecule
            atom (:obj:`openbabel.OBAtom`): atom
            residue (:obj:`bool`, optional): if :obj:`True`, search for a residue (H instead of O- at C terminus)
            convert_to_aa (:obj:`bool`, optional): if :obj:`True`, convert COH to COOH

        Returns:
            :obj:`bool`: :obj:`True` if the atom is an C-terminus
        """
        if atom is None:
            return False

        # check atom is carbon
        if atom.GetAtomicNum() != 6:
            return False

        # check atom has charge 0
        if atom.GetFormalCharge() != 0:
            return False

        # check atom is bonded to 1 oxygen, 1 carbon, and 1 hydrogen atom (residue=True) or 1 oxygen (residue=False) atom
        other_atoms = [
            other_atom.GetAtomicNum()
            for other_atom in openbabel.OBAtomAtomIter(atom)
        ]
        tot_bond_order = sum(
            [bond.GetBondOrder() for bond in openbabel.OBAtomBondIter(atom)])
        other_atoms += [1] * (4 + atom.GetFormalCharge() - tot_bond_order)
        other_atoms.sort()
        if set(other_atoms).difference(set([1, 6, 8])):
            return False
        if 6 not in other_atoms or 8 not in other_atoms:
            return False
        if len(other_atoms) != 3:
            return False
        if residue and other_atoms[0] != 1:
            return False
        if not residue and other_atoms[1] != 8:
            return False

        # check bonds to carbon and hydrogen are single bonds and bond to oxygen is a double bond
        o_single_bonds = []
        o_double_bonds = []
        for bond in openbabel.OBAtomBondIter(atom):
            other_atom = bond.GetBeginAtom()
            if other_atom == atom:
                other_atom = bond.GetEndAtom()
            if other_atom.GetAtomicNum() == 8:
                if bond.GetBondOrder() == 1:
                    o_single_bonds.append((bond, other_atom))
                elif bond.GetBondOrder() == 2:
                    o_double_bonds.append((bond, other_atom))
                else:
                    return False
            elif bond.GetBondOrder() != 1:
                return False

        if residue and (len(o_single_bonds) != 0 or len(o_double_bonds) != 1):
            return False
        if not residue and (len(o_single_bonds) != 1
                            or len(o_double_bonds) != 1):
            return False

        # if not residue, check that single oxygen is bound to H
        if not residue:
            oxygen_atom = o_single_bonds[0][1]
            for bond in openbabel.OBAtomBondIter(oxygen_atom):
                other_atom = bond.GetBeginAtom()
                if other_atom == oxygen_atom:
                    other_atom = bond.GetEndAtom()
                if other_atom.GetIdx() != atom.GetIdx(
                ) and other_atom.GetAtomicNum() != 1:
                    return False

        # correct residue to amino acid
        if convert_to_aa:
            h_atom = None
            for other_atom in openbabel.OBAtomAtomIter(atom):
                if other_atom.GetAtomicNum() == 1:
                    h_atom = other_atom
                    break

            if h_atom is not None:
                h_atom.SetAtomicNum(8)
            else:
                o_atom = mol.NewAtom()
                o_atom.SetAtomicNum(8)
                o_atom.SetFormalCharge(0)

                bond = openbabel.OBBond()
                bond.SetBegin(atom)
                bond.SetEnd(o_atom)
                bond.SetBondOrder(1)
                assert mol.AddBond(bond)

        # return True
        return True