Depicting Fragment Contributions of XLogP

Problem

You want to depict the contribution of fragments to the total XLogP on your molecule diagram. See example in Figure 1.

../_images/fragxlogp2img1.png

Figure 1. Example of depicting the fragment contributions of XLogP

See also

Ingredients

Note

Requires OpenEye toolkits version 2014.Feb or later.

Difficulty Level

../_images/chilly1.png ../_images/chilly1.png

Solution

The code snippet below shows how to calculate the total XLogP of a molecule along with the atom contributions by calling the OEGetXLogP function. Each atom contribution is then attached to the relevant atom as generic data with the given tag.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
def SetAtomProperties(mol, datatag):

    avals = OEFloatArray(mol.GetMaxAtomIdx())
    logp = OEGetXLogP(mol, avals)

    mol.SetTitle(mol.GetTitle() + " -- OEXLogP = %.2f" % logp)

    for atom in mol.GetAtoms():
        val = avals[atom.GetIdx()]
        atom.SetData(datatag, val)

The FragmentMolecule function fragments a molecule by using either the OEGetRingChainFragments, the OEGetRingLinkerSideChainFragments or the OEGetFuncGroupFragments function. Each enumerated fragment is then added to the molecule as a new group with the given tag.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
def FragmentMolecule(mol, fragfunc, grouptag):

    for frag in fragfunc(mol):

        atoms = OEAtomVector()
        for atom in frag.GetAtoms():
            atoms.append(atom)
        bonds = OEBondVector()
        for bond in frag.GetBonds():
            bonds.append(bond)

        mol.NewGroup(grouptag, atoms, bonds)

The SetFragmentProperties function should be called after the atom contributions are calculated (see SetAtomProperties) and the molecule is fragmented (see FragmentMolecule). It iterates over the fragments, adds together the atom contributions and attaches this accumulated value to each group (fragment). It also returns the minimum and maximum fragment contribution.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
def SetFragmentProperties(mol, datatag, grouptag):

    minvalue = float("inf")
    maxvalue = float("-inf")

    for group in mol.GetGroups(OEHasGroupType(grouptag)):

        sumprop = 0.0
        for atom in group.GetAtoms():
            sumprop += atom.GetData(datatag)
        group.SetData(datatag, sumprop)

        minvalue = min(minvalue, sumprop)
        maxvalue = max(maxvalue, sumprop)

    return minvalue, maxvalue

The DepictMoleculeWithFragmentXLogP function below shows how to project the fragment contributions of the total XLogP into a 2D molecular diagram. First the atom contributions are calculated by calling the SetAtomProperties function (see lines 5-7). Then a molecule is fragmented (lines 11-13) and the fragment contributions are calculated (line 17). Using the minimum and maximum fragment contributions a color gradient is constructed (lines 21-23). Since both the molecule and the color gradient will be depicted, the image has to be divided into two image frames (lines 27-29). The molecule display is then initialized (lines 33-34) along with the highlighting style (lines 38-41) and the display option for the color gradient (line 43). Then fragment contributions are visualized by iterating over them and highlighting them on the molecule diagram using the color corresponding to their contributions (line 45-55). Finally, the molecule along with the color gradient is rendered to the image (lines 59-60). You can see the result in Figure 1.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
def DepictMoleculeWithFragmentXLogP(image, mol, fragfunc, opts):

    # calculate atom contributions of XLogP

    sdatatag = "XLogP"
    idatatag = OEGetTag(sdatatag)
    SetAtomProperties(mol, idatatag)

    # fragment molecule

    sgrouptag = "fragment"
    igrouptag = OEGetTag(sgrouptag)
    FragmentMolecule(mol, fragfunc, igrouptag)

    # calculate fragment contributions

    minvalue, maxvalue = SetFragmentProperties(mol, idatatag, igrouptag)

    # initialize color gradient

    colorg = OELinearColorGradient(OEColorStop(0.0, OEColor(240, 240, 240)))  # light grey
    colorg.AddStop(OEColorStop(minvalue, OEDarkGreen))
    colorg.AddStop(OEColorStop(maxvalue, OEDarkPurple))

    # generate image frames

    iwidth, iheight = image.GetWidth(), image.GetHeight()
    mframe = OEImageFrame(image, iwidth, iheight * 0.8, OE2DPoint(0.0, 0.0))
    cframe = OEImageFrame(image, iwidth, iheight * 0.2, OE2DPoint(0.0, iheight * 0.8))

    # initialize molecule display

    opts.SetDimensions(mframe.GetWidth(), mframe.GetHeight(), OEScale_AutoScale)
    disp = OE2DMolDisplay(mol, opts)

    # initialize highlighting style

    highlight = OEHighlightByCogwheel(OEWhite)
    highlight.SetInnerContour(False)
    highlight.SetStickWidthScale(3.5)
    highlight.SetBallRadiusScale(2.5)

    colorgopts = OEColorGradientDisplayOptions()

    for group in mol.GetGroups(OEHasGroupType(igrouptag)):
        groupvalue = group.GetData(idatatag)
        colorgopts.AddMarkedValue(groupvalue)

        # depict fragment contribution

        color = colorg.GetColorAt(groupvalue)
        highlight.SetColor(color)

        abset = OEAtomBondSet(group.GetAtoms(), group.GetBonds())
        OEAddHighlighting(disp, highlight, abset)

    # render molecule and color gradient

    OERenderMolecule(mframe, disp)
    OEDrawColorGradient(cframe, colorg, colorgopts)

Hint

You can easily adapt this example to visualize other atom properties as fragment contributions by writing your own SetAtomProperties and SetFragmentProperties functions.

Download code

fragxlogp2img.py

Usage:

prompt > python3 fragxlogp2img.py molecule.ism fragxlogp.png

Discussion

The example above shows how to visualize the fragment contributions for a single molecule, however you might want to visualize the XLogP data for a set of molecules. In the DepictMoleculesWithFragmentXLogP function below, each molecule is rendered into a cell of an OEReport object. The OEReport class is a layout manager allowing generation of multi-page images in a convenient way. You can see the generated multi-page PDF in Table 1.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
def DepictMoleculesWithFragmentXLogP(report, mollist, fragfunc, opts):

    # calculate atom contributions of XLogP

    sdatatag = "XLogP"
    idatatag = OEGetTag(sdatatag)

    for mol in mollist:
        SetAtomProperties(mol, idatatag)

    # fragment molecules

    sgrouptag = "fragment"
    igrouptag = OEGetTag(sgrouptag)
    for mol in mollist:
        FragmentMolecule(mol, fragfunc, igrouptag)

    # calculate fragment contributions

    minvalue = float("inf")
    maxvalue = float("-inf")
    for mol in mollist:
        minvalue, maxvalue = SetFragmentProperties(mol, idatatag, igrouptag,
                                                   minvalue, maxvalue)

    # initialize color gradient

    colorg = OELinearColorGradient(OEColorStop(0.0, OEColor(240, 240, 240)))  # light grey
    colorg.AddStop(OEColorStop(minvalue, OEDarkGreen))
    colorg.AddStop(OEColorStop(maxvalue, OEDarkPurple))

    # initialize highlighting style

    highlight = OEHighlightByCogwheel(OEWhite)
    highlight.SetInnerContour(False)
    highlight.SetStickWidthScale(3.5)
    highlight.SetBallRadiusScale(2.5)

    for mol in mollist:

        # generate image frames

        cell = report.NewCell()
        cwidth, cheight = cell.GetWidth(), cell.GetHeight()
        mframe = OEImageFrame(cell, cwidth, cheight * 0.8, OE2DPoint(0.0, 0.0))
        cframe = OEImageFrame(cell, cwidth, cheight * 0.2, OE2DPoint(0.0, cheight * 0.8))

        # initialize molecule display

        opts.SetDimensions(mframe.GetWidth(), mframe.GetHeight(), OEScale_AutoScale)
        disp = OE2DMolDisplay(mol, opts)

        colorgopts = OEColorGradientDisplayOptions()

        for group in mol.GetGroups(OEHasGroupType(igrouptag)):
            groupvalue = group.GetData(idatatag)
            colorgopts.AddMarkedValue(groupvalue)

            # depict fragment contribution

            color = colorg.GetColorAt(groupvalue)
            highlight.SetColor(color)

            abset = OEAtomBondSet(group.GetAtoms(), group.GetBonds())
            OEAddHighlighting(disp, highlight, abset)

        # render molecule and color gradient

        OERenderMolecule(mframe, disp)
        OEDrawColorGradient(cframe, colorg, colorgopts)
Table 1. Example of depicting fragment contributions of XLogP for a set of molecules (The pages are reduced here for visualization convenience)
page 1 page 2 page 3
../_images/fragxlogp2pdf-1.png ../_images/fragxlogp2pdf-2.png ../_images/fragxlogp2pdf-3.png

Download code

fragxlogp2pdf.py

Usage:

prompt > python3 fragxlogp2pdf.py molecule.sdf fragxlogp.pdf

See Also in OEChem TK Manual

Theory

API

See Also in MolProp TK Manual

API

See Also in OEMedChem TK Manual

Theory

API

See Also in OEDepict TK Manual

Theory

API

See Also in Grapheme TK Manual

API