Molecule Depiction

The previous chapter introduced how to create images and draw basic geometric elements (such as text, lines rectangles, etc.) Drawing these basic graphical elements provides a framework to construct more complex images such as molecular diagrams.

The molecule depiction is divided into two separate steps (see Figure: Process of Molecule Depiction ):

  1. Generating 2D coordinates

  2. Rendering molecule that involves

    • transforming and scaling coordinates in order to fit the molecule into an image with a specific width and height

    • setting atom and bond display properties based on depiction style

    • creating an image (such as drawing lines for bonds, drawing text for atomic labels)

../_images/Depiction.png

Process of molecule depiction

The next example (Listing 1) demonstrates how easy is to depict a molecule using the OEDepict TK. After creating a molecule (for example by parsing a SMILES string) the image can be generated by calling two functions.

  1. The OEPrepareDepiction function prepares the molecule for depiction. This process may involve perceiving atom and bond stereo information and suppressing or adding hydrogens. It also calls the OEDepictCoordinates function to generate the 2D coordinates of the molecule.

  2. The OERenderMolecule function generates the image of the molecule using the default depiction styles and then writes the image into the given file.

The image created by Listing 1 is shown in Figure: Example of depicting a molecule.

Listing 1: Example of molecule depiction

int main()
{
  OEGraphMol mol;
  OESmilesToMol(mol, "c1cc(N)cc(S(=O)(=O)O)c1 3-aminobenzenesulfonic acid");
  OEPrepareDepiction(mol);
  OERenderMolecule("DepictMolSimple.png", mol);
  return 0;
}
../_images/DepictMolSimple.png

Example of molecule depiction

See also

Customizing Molecule Depiction

The previous example showed how to generate a molecule diagram with default parameters. OEDepict TK provides the ability to customize molecule depiction. The Listing 2 example shows how to depict a molecule width specific width and height parameters.

Listing 2: Example of depicting a molecule

int main()
{
  OEGraphMol mol;
  OESmilesToMol(mol, "c1cc(N)cc(S(=O)(=O)O)c1 3-aminobenzenesulfonic acid");
  OEPrepareDepiction(mol);

  const auto width  = 300u;
  const auto height = 300u;
  OE2DMolDisplayOptions opts(width, height, OEScale::AutoScale);
  OE2DMolDisplay disp(mol, opts);
  OERenderMolecule("DepictMolSize.png", disp);
  return 0;
}

See also

Apart from defining the dimensions of a depicted molecule, the OE2DMolDisplayOptions class stores all properties that determine how a molecule is depicted. The following example shows how to set various depiction styles before initializing the OE2DMolDisplay object. The image created by Listing 3 is shown in Figure: Example of customizing depiction style.

Listing 3: Example of customizing the depiction style

int main()
{
  OEGraphMol mol;
  OESmilesToMol(mol, "c1cc(N)cc(S(=O)(=O)O)c1 3-aminobenzenesulfonic acid");
  OEPrepareDepiction(mol);

  const auto width  = 200u;
  const auto height = 200u;
  OE2DMolDisplayOptions opts(width, height, OEScale::AutoScale);

  opts.SetAromaticStyle(OEAromaticStyle::Circle);
  opts.SetAtomColorStyle(OEAtomColorStyle::BlackCPK);
  opts.SetTitleLocation(OETitleLocation::Bottom);

  OE2DMolDisplay disp(mol, opts);
  OERenderMolecule("DepictMolStyle.png", disp);
  return 0;
}
../_images/DepictMolStyle.png

Example of customizing the depiction style

Apart from controlling the depiction style through the OE2DMolDisplayOptions class, OEDepict TK also provides access to manipulate individual atom and bond 2D display properties. The OE2DMolDisplay::GetAtomDisplays method returns an iterator over OE2DAtomDisplay objects that store atom display information. Similarly, the OE2DMolDisplay::GetBondDisplays method returns an iterator over OE2DBondDisplay objects that store bond display information.

The following example demonstrates how to change atom and bond display properties and depict the graph of the molecule by ignoring atom labels and setting bond display styles. The image created by Listing 4 is shown in Figure: Example of molecule graph depiction.

Listing 4: Example of molecule graph depiction

int main()
{
  OEGraphMol mol;
  OESmilesToMol(mol, "c1cc(N)cc(S(=O)(=O)O)c1");
  OEPrepareDepiction(mol);

  const auto width  = 200u;
  const auto height = 200u;
  OE2DMolDisplayOptions opts(width, height, OEScale::AutoScale);

  opts.SetAtomColorStyle(OEAtomColorStyle::WhiteMonochrome);
  opts.SetTitleLocation(OETitleLocation::Hidden);
  opts.SetAtomColor(OEElemNo::C, OEDarkGreen);
  OEPen pen(OEBlack, OEBlack, OEFill::On, 3.0);
  opts.SetDefaultBondPen(pen);

  OE2DMolDisplay disp(mol, opts);

  for (OEIter<OE2DAtomDisplay> adisp = disp.GetAtomDisplays(); adisp; ++adisp)
    adisp->SetLabel("");

  for (OEIter<OE2DBondDisplay> bdisp = disp.GetBondDisplays(); bdisp; ++bdisp)
    bdisp->SetDisplayType(OEBondDisplayType::Single);

  OERenderMolecule("DepictMolGraph.png", disp);
  return 0;
}
../_images/DepictMolGraph.png

Example of molecule graph depiction

Hint

Even though OEDepict TK provides the ability to manipulate atom and bond display properties of after the OE2DMolDisplay object is constructed, it is highly recommended to set the depiction properties using the OE2DMolDisplayOptions class. Only by knowing all properties (such as labels, font styles and sizes etc.) in advance can one ensure the best depiction layout i.e. that the molecule diagram is rendered without any label clippings and the labels are displayed with the minimum number of overlaps.

See also

Controlling the Size of Depicted Molecules

The dimensions of a depicted molecule are controlled by the width, height and scale parameters of the OE2DMolDisplayOptions that is used to initialized the OE2DMolDisplay object. (See example in Listing 2)

If the width and the height of the image is not specified (set to be zero), then scaling value determine the dimensions of the image. (See examples in Examples of image scaling). The default scale is defined to be OEScale::Default constant, and the image may be enlarged or shrunk by specifying a floating point scaling value. For example, the scaling OEScale::Default * 0.5 generates an image a half of the default size, and scaling OEScale::Default * 1.5 generates an image one and a half times the default.

Examples of image scaling (width = 0.0, height = 0.0)

OEScale::Default * 0.5

OEScale::Default

OEScale::Default * 1.5

../_images/DepictMol-Size-0-0-Half.png ../_images/DepictMol-Size-0-0-Default.png ../_images/DepictMol-Size-0-0-OneAndHalf.png

If an OE2DMolDisplayOptions object is initialized with zero width and / or height, then the real dimensions of the image can be accessed after creating an OE2DMolDisplay object.

const double width  = 0.0;
const double height = 0.0;
const double scale  = 50.0;
OE2DMolDisplayOptions opts(width, height, scale);
OE2DMolDisplay disp(mol, opts);
std::cout.precision(1);
cout << fixed << "width  " << disp.GetWidth() << endl;
cout << fixed << "height " << disp.GetHeight() << endl;
cout << fixed << "scale  " << disp.GetScale() << endl;

The output of the preceding snippet is the following:

width  137.0
height 181.0
scale  50.0

If both the width and the height of are specified, then OEScale::AutoScale scaling indicates that the molecule is scaled to maximally fit the given dimensions. The specified width and height will not be altered, not even if the given scaling would require it i.e if necessary the scaling will be reduced in order to fit the molecule into the given dimension. (See examples in Examples of image scaling).

Examples of fixed sized image (width = 120.0, height = 120.0)

OEScale::Default * 0.5

OEScale::Default

OEScale::Default * 1.5

../_images/DepictMol-Size-120-120-Half.png ../_images/DepictMol-Size-120-120-Default.png ../_images/DepictMol-Size-120-120-OneAndHalf.png

Note

Specifying a width and / or height larger than what is required by the scale, causes the molecule to float in the middle of the image of the requested size.

If only either the width or the height of the image is specified, then the unspecified dimension will be set based on the scaling and the specified width / height, respectively.

OEScale::Default, width = 250.0, height = 0.0

OEScale::Default, width = 0.0, height = 250.0

../_images/DepictMol-Size-250-0-Default.png ../_images/DepictMol-Size-0-250-Default.png

Molecule Depiction with Transparent Background

The following code snippet shows how to generate a molecule depiction with transparent background. First, the OEImage object, onto which the depiction is going to be rendered, has to be constructed with the OETransparentColor color. Then the OERenderMolecule function has to be called with a parameter that ensures that the background in not cleared prior to rendering the molecule.

const double width  = 200.0;
const double height = 200.0;
const double scale  = OEScale::AutoScale;
OEImage image(width, height, OESystem::OETransparentColor);

OE2DMolDisplayOptions opts(width, height, scale);
OE2DMolDisplay disp(mol, opts);

const bool clearbackground = true;
OERenderMolecule("DepictMolTransparent.png", disp, !clearbackground);

Displaying Atom Properties

OEDepict TK provides ability the display atom properties as strings. When a OE2DMolDisplay object is created, the positions where atom properties can be displayed are calculated. (see Figure: Example of generating atom property positions.)

../_images/OE2DAtomDisplay-GetPropertyOffset.png

Example of generating atom property positions

The following example shows how to display the atom indices by using the OEDisplayAtomIdx functor. The font used to depict the atom property strings also can be modified by using the OE2DMolDisplayOptions::SetAtomPropLabelFont method. The image created by Listing 5 is shown in Figure: Example of displaying atom indices.

Listing 5: Example of depicting atom indices

int main()
{
  OEGraphMol mol;
  OESmilesToMol(mol, "c1cc(N)cc(S(=O)(=O)O)c1");
  OEPrepareDepiction(mol);

  const double width  = 300.0;
  const double height = 200.0;
  OE2DMolDisplayOptions opts(width, height, OEScale::AutoScale);
  opts.SetAtomPropertyFunctor(OEDisplayAtomIdx());
  opts.SetAtomPropLabelFont(OEFont(OEDarkGreen));

  OE2DMolDisplay disp(mol, opts);
  OERenderMolecule("AtomPropIndex.png", disp);
  return 0;
}
../_images/AtomPropIndex.png

Example of displaying atom indices

Hint

It is recommended to use the OE2DMolDisplayOptions::SetAtomPropertyFunctor method to define the atom property labels when the OE2DMolDisplay object is constructed. All labels displayed on the molecule diagram have to be known in advance in order to be able to minimize the number of label clashes and clippings when calculating the positions of the atom property labels.

See also

OEDepict TK provides the following built-in atom property functors:

In order to display user-defined atom properties, the functor that is passed to the OE2DMolDisplayOptions::SetAtomPropertyFunctor method has to be derived from the OEDisplayAtomPropBase abstract base class. The Listing 6 example shows how to implement a user-defined functor that marks aromatic atoms. The image created by Listing 6 is shown in Figure: Example of displaying user-defined atom properties.

Listing 6: Example of depicting user-defined atom properties

class LabelAromaticAtoms : public OEDisplayAtomPropBase
{
public:
  LabelAromaticAtoms() {}
  string operator () (const OEChem::OEAtomBase& atom) const
  {
    return string(atom.IsAromatic() ? "(A)" : "");
  }
  OEDisplayAtomPropBase *CreateCopy() const
  {
    return new  LabelAromaticAtoms(*this);
  }
};

int main()
{
  OEGraphMol mol;
  OESmilesToMol(mol, "c1cc(N)cc(S(=O)(=O)O)c1");
  OEPrepareDepiction(mol);

  const double width  = 300.0;
  const double height = 200.0;
  OE2DMolDisplayOptions opts(width, height, OEScale::AutoScale);

  LabelAromaticAtoms atomlabel;
  opts.SetAtomPropertyFunctor(atomlabel);

  OE2DMolDisplay disp(mol, opts);
  OERenderMolecule("AtomPropUser.png", disp);
  return 0;
}
../_images/AtomPropUser.png

Example of displaying user-defined atom properties

See also

Displaying Bond Properties

Similarly to atom properties, bond properties can be displayed as strings. (see Figure: Example of generating bond property positions.)

../_images/OE2DBondDisplay-GetPropertyOffset.png

Example of generating bond property positions

The Listing 7 demonstrates how to display bond indices by using the OEDisplayBondIdx functor. The font used to depict the bond property strings can be set by using the OE2DMolDisplayOptions::SetBondPropLabelFont method. The image created by Listing 7 is shown in Figure: Example of displaying bond indices.

Listing 7: Example of depicting bond indices

int main()
{
  OEGraphMol mol;
  OESmilesToMol(mol, "c1cc(N)cc(S(=O)(=O)O)c1");
  OEPrepareDepiction(mol);

  const double width  = 300.0;
  const double height = 200.0;
  OE2DMolDisplayOptions opts(width, height, OEScale::AutoScale);
  opts.SetBondPropertyFunctor(OEDisplayBondIdx());
  opts.SetBondPropLabelFont(OEFont(OEDarkBlue));

  OE2DMolDisplay disp(mol, opts);
  OERenderMolecule("BondPropIndex.png", disp);
  return 0;
}
../_images/BondPropIndex.png

Example of displaying bond indices

Hint

It is recommended to use the OE2DMolDisplayOptions::SetBondPropertyFunctor method to define the bond property labels when the OE2DMolDisplay object is constructed. All labels displayed on the molecule diagram have to be known in advance in order to be able to minimize the number of label clashes and clippings when calculating the positions of the bond property labels.

See also

OEDepict TK provides the following built-in bond property functors:

In order to display user-defined bond properties, the functor that is passed to the OE2DMolDisplayOptions::SetBondPropertyFunctor method has to be derived from the OEDisplayBondPropBase abstract base class. The Listing 8 example shows how to implement a user-defined functor that marks chain and ring bonds. The image created by Listing 8 is shown in Figure: Example of displaying user-defined bond properties.

Listing 8: Example of depicting user-defined bond properties

class LabelRingChainBonds : public OEDisplayBondPropBase
{
public:
  LabelRingChainBonds() {}
  string operator () (const OEChem::OEBondBase& bond) const
  {
    return string(bond.IsInRing() ? "R" : "C");
  }
  OEDisplayBondPropBase *CreateCopy() const
  {
    return new LabelRingChainBonds(*this);
  }
};

int main()
{
  OEGraphMol mol;
  OESmilesToMol(mol, "c1cc(N)cc(S(=O)(=O)O)c1");
  OEPrepareDepiction(mol);

  const double width  = 300.0;
  const double height = 200.0;
  OE2DMolDisplayOptions opts(width, height, OEScale::AutoScale);

  LabelRingChainBonds bondlabel;
  opts.SetBondPropertyFunctor(bondlabel);

  OE2DMolDisplay disp(mol, opts);
  OERenderMolecule("BondPropUser.png", disp);
  return 0;
}
../_images/BondPropUser.png

Example of displaying user-defined bond properties

See also

Hiding Atoms and Bonds

OEDepict TK provides ability the suppress the display of specific atom and bonds. When a OE2DMolDisplay object is created, the visibility of every atom is evaluated. Bonds with both atom endpoints visible are also displayed. (see Figure: Example of hiding a portion of a structure.)

The following example shows how to selectively display only a portion of the structure by using a custom class derived from the OEUnaryAtomPred functor. The images created by Listing 9 is shown in Figure: Example of hiding a portion of a structure.

Hint

It is recommended to use the OE2DMolDisplayOptions::SetAtomVisibilityFunctor method to identify the visible atoms when the OE2DMolDisplay object is constructed. All objects displayed on the molecule diagram have to be known in advance in order to be able to correctly size and scale the molecule.

Listing 9: Example of selectively displaying atoms

class OEAtomVisibilityShowRxnRole : public OEUnaryPredicate<OEAtomBase>
{
protected:
  unsigned int rxnrole;
public:
  OEAtomVisibilityShowRxnRole(unsigned int role)
    : rxnrole(role)
  {}
  bool operator () (const OEChem::OEAtomBase& atom) const
  {
    return (rxnrole == OERxnRole::None ||
            atom.GetRxnRole() == rxnrole);
  }
  OEUnaryFunction<OEAtomBase,bool> *CreateCopy() const
  {
    return new OEAtomVisibilityShowRxnRole(rxnrole);
  }
};

int main(int argc,  char* argv[])
{
  if (argc != 3)
    OEThrow.Usage("%s <rxnfile> <imagefile>", argv[0]);

  oemolistream ifs(argv[1]);
  OEGraphMol mol;
  if (!OEReadRxnFile(ifs,mol))
    OEThrow.Fatal("error reading rxnfile");

  OEPrepareDepiction(mol);

  OEImage image(900, 100);

  const auto rows = 1u;
  const auto cols = 3u;
  OEImageGrid grid(image, rows, cols);

  OE2DMolDisplayOptions opts(grid.GetCellWidth(), grid.GetCellHeight(), OEScale::AutoScale);

  OEImageBase* cell = grid.GetCell(1u, 1u);
  mol.SetTitle("Reaction display");
  opts.SetAtomVisibilityFunctor(OEIsTrueAtom());  // explicitly set the default

  OE2DMolDisplay disp(mol, opts);
  double rxnscale = disp.GetScale();
  OERenderMolecule(*cell, disp);

  cell = grid.GetCell(1u, 2u);
  mol.SetTitle("Reactant display");
  opts.SetAtomVisibilityFunctor(OEAtomVisibilityShowRxnRole(OERxnRole::Reactant));
  opts.SetScale(rxnscale);
  disp = OE2DMolDisplay(mol, opts);
  OERenderMolecule(*cell, disp);

  cell = grid.GetCell(1u, 3u);
  mol.SetTitle("Product display");
  opts.SetAtomVisibilityFunctor(OEAtomVisibilityShowRxnRole(OERxnRole::Product));
  opts.SetScale(rxnscale);
  disp = OE2DMolDisplay(mol, opts);
  OERenderMolecule(*cell, disp);

  OEWriteImage(argv[2], image);

  return 0;
}
../_images/AtomVisibility.png

Example of hiding a portion of a structure

Configuring Molecule Display

OEDepict TK provides a mechanism to generate a standard interface that allows configuration of molecule displays. By calling the OEConfigureImageOptions function, “-height” and “width” parameters are added to the interface (OEInterface), at run-time the value of these parameters can be obtained by calling the OEGetImageHeight and OEGetImageWidth functions, respectively. (See the standard interface displayed when calling the Listing 10 example with the “–help” parameter)

The OEConfigure2DMolDisplayOptions function generates an interface that allows setting of various molecule display options (such as aromatic style, atom and bond coloring etc.) The OE2DMolDisplayOptions object, that stores properties determine the molecule depiction style, can initialized based on to the command line parameters by calling the OESetup2DMolDisplayOptions function.

Listing 10: Example of configuring mol display

int main(int argc, char* argv[])
{
  OEInterface itf;
  // import configuration file
  OEConfigure(itf, InterfaceData);
  // add configuration for image size and display options
  OEConfigureImageOptions(itf);
  OEConfigure2DMolDisplayOptions(itf);

  if(!OEParseCommandLine(itf, argc, argv))
    OEThrow.Fatal("Unable to interpret command line!");

  const string ifname = itf.Get<string>("-in");
  const string ofname = itf.Get<string>("-out");

  oemolistream ifs(ifname);
  OEGraphMol mol;
  OEReadMolecule(ifs, mol);
  OEPrepareDepiction(mol);

  const double width = OEGetImageWidth (itf);
  const double height= OEGetImageHeight(itf);
  OE2DMolDisplayOptions opts(width, height, OEScale::AutoScale);
  // set up display options from command line parameters
  OESetup2DMolDisplayOptions(opts, itf);

  OE2DMolDisplay disp(mol, opts);
  OERenderMolecule(ofname, disp);

  return 0;
}
prompt> DepictMolConfigure --help

will generate the following standard interface:

Simple parameter list
    image options
      -height : Height of output image
      -width : Width of output image

    input/output
      -in : Input filename
      -out : Output filename

    molecule display options
      -aromstyle : Aromatic ring display style
      -atomcolor : Atom coloring style
      -atomprop : Atom property display
      -atomstereostyle : Atom stereo display style
      -bondcolor : Bond coloring style
      -bondprop : Bond property display
      -bondstereostyle : Bond stereo display style
      -hydrstyle : Hydrogen display style
      -linewidth : Default bond line width
      -protgroupdisp : Protective group display style
      -scale : Scaling of the depicted molecule
      -superdisp : Super atom display style
      -titleloc : Location of the molecule title

See also

OEDepict TK provides the following high-level functions to build standard interface of depiction applications:

Function name

Builds standard interface for ..

OEConfigure2DMolDisplayOptions

molecule depiction style

OEConfigureHighlightParams

highlighting

OEConfigureImageGridParams

image grid

OEConfigureImageOptions

image

OEConfigureMultiPageParams

multi-page image

OEConfigurePrepareDepictionOptions

preparing molecules for 2D depiction

OEConfigureReportOptions

multi-page report