def MolToJSON(mol, size=(300, 300), kekulize=True, wedgeBonds=True, fitImage=False, options=None, **kwargs): if not mol: raise ValueError, 'Null molecule provided' canvas = Canvas(size=size) if options is None: options = DrawingOptions() if fitImage: options.dotsPerAngstrom = int(min(size) / 10) options.wedgeDashedBonds = wedgeBonds try: drawer = MolDrawing(canvas=canvas, drawingOptions=options) except TypeError: drawer = MolDrawing(canvas=canvas) if kekulize: mol = Chem.Mol(mol.ToBinary()) Chem.Kekulize(mol) if not mol.GetNumConformers(): Compute2DCoords(mol) drawer.AddMol(mol, **kwargs) try: drawer.AddLegend(kwargs.get('legend', '')) except AttributeError: pass canvas.flush() return canvas.json
def draw_molecule_with_highlights(filename, smiles, highlight_atoms): drawoptions = DrawingOptions() drawoptions.selectColor = (255.0/255.0, 0.0/255.0, 0.0/255.0) # A nice light blue. drawoptions.elemDict = {} # Don't color nodes based on their element. drawoptions.bgColor=None mol = Chem.MolFromSmiles(smiles) fig = Draw.MolToImage(mol, highlightAtoms=highlight_atoms, size=(500, 500), options=drawoptions) fig.save(filename, bbox_inches='tight')
def draw_molecule_with_highlights(filename, smiles, highlight_atoms): drawoptions = DrawingOptions() drawoptions.selectColor = highlight_color drawoptions.elemDict = {} # Don't color nodes based on their element. drawoptions.bgColor=None mol = Chem.MolFromSmiles(smiles) fig = Draw.MolToMPL(mol, highlightAtoms=highlight_atoms, size=figsize, options=drawoptions,fitImage=False) fig.gca().set_axis_off() fig.savefig(filename, bbox_inches='tight') plt.close(fig)
def MolToMPL(mol, size=(300, 300), kekulize=True, wedgeBonds=True, imageType=None, fitImage=False, options=None, **kwargs): if not mol: raise ValueError('Null molecule provided') from rdkit.Chem.Draw.mplCanvas import Canvas canvas = Canvas(size) if options is None: options = DrawingOptions() options.bgColor = None if fitImage: options.dotsPerAngstrom = int(min(size) / 10) options.atomLabelFontSize = 7 options.bondLineWidth = 2 options.coordScale = 1 options.wedgeDashedBonds = wedgeBonds drawer = MolDrawing(canvas=canvas, drawingOptions=options) omol = mol if kekulize: from rdkit import Chem mol = Chem.Mol(mol.ToBinary()) Chem.Kekulize(mol) if not mol.GetNumConformers(): from rdkit.Chem import AllChem AllChem.Compute2DCoords(mol) drawer.AddMol(mol, **kwargs) omol._atomPs = drawer.atomPs[mol] for k, v in omol._atomPs.items(): omol._atomPs[k] = canvas.rescalePt(v) canvas._figure.set_size_inches(float(size[0]) / 100, float(size[1]) / 100) return canvas._figure
def draw(mol, quality=1, ax=None): """Draw a molecule on a matplotlib axis. Args: mol (skchem.Mol): The molecule to be drawn. quality (int): The level of quality. Higher quality takes more time, but will look better (so long as matplotlib's savefig.dpi is high enough). ax (plt.Axes or None): An existing axis on which to draw the molecule. Returns: plt.AxesImage: A matplotlib AxesImage object with the molecule drawn. """ if not ax: ax = plt.gca() ax.grid('off') ax.axis('off') opts = DrawingOptions() opts.dotsPerAngstrom *= quality opts.atomLabelFontSize *= quality opts.bondLineWidth *= quality size = 300 * quality img, canvas, drawer = MolToImage(mol, size=(size, size), options=opts, returnCanvas=True) canvas.flush() return ax.imshow(img, extent=(0, 1, 0, 1))
def compute_mol_attributes(graph, labels_dict, actions_history_smi_pop, actions_history_smi_removed, actions_history_scores_pop, actions_history_scores_removed, legend_scores_keys_strat=None): images_attributes = {} scores_attributes = {} draw_opt = DrawingOptions() draw_opt.coordScale = 0.9 draw_opt.dotsPerAngstrom = 30 for action_history_k in labels_dict.keys(): if action_history_k in actions_history_smi_pop: smi = actions_history_smi_pop[action_history_k] img = MolToImage(MolFromSmiles(smi), size=(800, 800), options=draw_opt) images_attributes[action_history_k] = crop_image_with_transparency( img) legend, _ = compute_mol_legend(action_history_k, smi, actions_history_scores_pop, legend_scores_keys_strat) scores_attributes[action_history_k] = legend else: smi = actions_history_smi_removed[action_history_k] img = MolToImage(MolFromSmiles(smi), size=(800, 800), options=draw_opt) images_attributes[action_history_k] = crop_image_with_transparency( img) legend, _ = compute_mol_legend(action_history_k, smi, actions_history_scores_removed, legend_scores_keys_strat) scores_attributes[action_history_k] = legend nx.set_node_attributes(graph, images_attributes, "image") nx.set_node_attributes(graph, scores_attributes, "score_label")
def plot_weights(mol, weights, quality=1, l=0.4, step=50, levels=20, contour_opacity=0.5, cmap='RdBu', ax=None, **kwargs): """ Plot weights as a sum of gaussians across a structure image. Args: mol (skchem.Mol): Molecule to visualize weights for. weights (iterable<float>): Array of weights in atom index order. l (float): Lengthscale of gaussians to visualize as a multiple of bond length. step (int): Size of grid edge to calculate the gaussians. levels (int): Number of contours to plot. contour_opacity (float): Alpha applied to the contour layer. ax (plt.axis): Axis to apply the plot to. Defaults to current axis. cmap (plt.cm): Colormap to use for the contour. **kwargs: Passed to contourf function. Returns: matplotlib.AxesSubplot: The plot. """ if not ax: ax = plt.gca() ax.grid('off') ax.axis('off') opts = DrawingOptions() opts.dotsPerAngstrom *= quality opts.atomLabelFontSize *= quality opts.bondLineWidth *= quality size = 300 * quality img, canvas, drawer = MolToImage(mol, size=(size, size), options=opts, returnCanvas=True) canvas.flush() coords = [[i / size, 1 - j / size] for k, (i, j) in list(drawer.atomPs.values())[0].items()] coords = np.array(coords) b = mol.bonds[0] begin, end = b.GetBeginAtom().GetIdx(), b.GetEndAtom().GetIdx() length = np.linalg.norm(coords[end] - coords[begin]) x = np.linspace(0, 1, 500) y = np.linspace(0, 1, 500) x, y = np.meshgrid(x, y) def gaussian(x, y, mu=np.zeros(2), sigma=np.identity(2), size=50): return (1 / (2 * np.pi * sigma[0, 0] * sigma[1, 1]) * np.exp(-((x - mu[0]) ** 2 / (2 * sigma[0, 0] ** 2) + (y - mu[1]) ** 2 / (2 * sigma[1, 1] ** 2)))) if not np.max(weights) == np.min(weights) == 0: z = sum([w * gaussian(x, y, mu, sigma=l * length * np.identity(2)) for mu, w in zip(coords, weights)]) v = np.max((np.abs(z.min()), np.abs(z.max()))) else: z = np.zeros(x.shape) v = 1 if z.min() >= 0: levels = int(levels/2) ax.contourf(x, y, z, levels, alpha=contour_opacity, extent=(0, 1, 0, 1), vmin=-v, vmax=v, cmap=cmap, **kwargs) ax.imshow(img, extent=(0, 1, 0, 1)) return ax
def get_image(self, request, **kwargs): try: if kwargs.get('chemblid', False): chemblid = kwargs['chemblid'] if not validateChemblId(chemblid): raise BadRequest("Invalid Chembl Identifier supplied:%s" % chemblid) try: molfile = MoleculeDictionary.objects.filter(chembl_id=chemblid).values_list( "compoundstructures__molfile")[0][0] except IndexError: return http.HttpNotFound() else: return http.HttpNotFound() except ObjectDoesNotExist: return http.HttpNotFound() size = int(kwargs.get("dimensions", 500)) engine = kwargs.get("engine", 'rdkit') engine = engine.lower() ignoreCoords = kwargs.get("ignoreCoords", False) if size < 1 or size > 500: return self.answerBadRequest(request, "Image dimensions supplied are invalid, max value is 500") response = HttpResponse(mimetype="image/png") if engine == 'rdkit': fontSize = int(size / 33) if size < 200: fontSize = 1 mol = Chem.MolFromMolBlock(str(molfile)) if ignoreCoords: AllChem.Compute2DCoords(mol) if DrawingOptions: options = DrawingOptions() options.useFraction = 1.0 options.dblBondOffset = .13 options.atomLabelFontSize = fontSize else: options={"useFraction": 1.0, "dblBondOffset": .13, 'atomLabelFontSize': fontSize,} image = Draw.MolToImage(mol, size=(size, size), fitImage=True, options=options) image.save(response, "PNG") elif engine == 'indigo': indigoObj = indigo.Indigo() renderer = indigo_renderer.IndigoRenderer(indigoObj) indigoObj.setOption("render-output-format", "png") indigoObj.setOption("render-margins", 10, 10) indigoObj.setOption("render-image-size", size, size) indigoObj.setOption("render-coloring", True) indigoObj.setOption("ignore-stereochemistry-errors", "true") mol = indigoObj.loadMolecule(str(molfile)) if ignoreCoords: mol.layout() image = renderer.renderToBuffer(mol) response.write(image.tostring()) else: return self.answerBadRequest(request, "Unsupported engine %s" % engine) return response