def setUp(self): try: cg, = ftmc.CoarseGrainRNA.from_pdb('test/forgi/threedee/data/1y26.pdb', annotation_tool="MC-Annotate") except ftmc.AnnotationToolNotInstalled: self.skipTest("Requires MC-Annotate") # cg.defines['s0']==[1,9,63,71] self.va1 = ftug.virtual_atoms(cg, sidechain=False) self.va2 = ftug.virtual_atoms(cg, sidechain=True)
def setUp(self): try: cg, = ftmc.CoarseGrainRNA.from_pdb( 'test/forgi/threedee/data/1y26.pdb', annotation_tool="MC-Annotate") except ftmc.AnnotationToolNotInstalled: self.skipTest("Requires MC-Annotate") # cg.defines['s0']==[1,9,63,71] self.va1 = ftug.virtual_atoms(cg, sidechain=False) self.va2 = ftug.virtual_atoms(cg, sidechain=True)
def showvirtualAtoms(filename): sm=get_sm(filename) cg=sm.bg clash_energy=fbe.StemVirtualResClashEnergy() clash_energy.eval_energy(sm) forJson={ "virtual_atoms":[]} virtualAtoms = ftug.virtual_atoms(sm.bg, sidechain=True) for residuePos in virtualAtoms.keys(): stem=cg.get_node_from_residue_num(residuePos) if stem[0]!="s": continue #Only virtual res for stems! residue=virtualAtoms[residuePos] for aname in residue.keys(): isClashing=False if stem in clash_energy.bad_bulges: for clashing in clash_energy.bad_atoms[stem]: if np.allclose(residue[aname], clashing): isClashing=True break; atomInfo={ "atomname":aname, "center":residue[aname].tolist(), "is_clashing":isClashing, "loop": stem } forJson["virtual_atoms"].append(atomInfo) return jsonify(forJson)
def showvirtualAtoms(filename): sm = get_sm(filename) cg = sm.bg clash_energy = fbe.StemVirtualResClashEnergy() clash_energy.eval_energy(sm) forJson = {"virtual_atoms": []} virtualAtoms = ftug.virtual_atoms(sm.bg, sidechain=True) for residuePos in virtualAtoms.keys(): stem = cg.get_node_from_residue_num(residuePos) if stem[0] != "s": continue #Only virtual res for stems! residue = virtualAtoms[residuePos] for aname in residue.keys(): isClashing = False if stem in clash_energy.bad_bulges: for clashing in clash_energy.bad_atoms[stem]: if np.allclose(residue[aname], clashing): isClashing = True break atomInfo = { "atomname": aname, "center": residue[aname].tolist(), "is_clashing": isClashing, "loop": stem } forJson["virtual_atoms"].append(atomInfo) return jsonify(forJson)
def reconstruct_from_average(sm): ''' Reconstruct a molecule using the average positions of each atom in the elements comprising this structure. @param sm: A SpatialModel. ''' atoms = ftug.virtual_atoms(sm.bg, given_atom_names = None) c = bpdbc.Chain(' ') anum = 1 for d in sm.bg.defines: for rnum in sm.bg.define_residue_num_iterator(d): rname = " " + sm.bg.seq[rnum-1] r = bpdbr.Residue((' ', rnum, ' '), rname, ' ') for aname in atoms[rnum]: atom = bpdba.Atom(aname, atoms[rnum][aname], 0., 1., ' ', aname, 1) r.add(atom) c.add(r) return c
def setUp(self): cg = ftmc.from_pdb('test/forgi/threedee/data/1y26.pdb') # cg.defines['s0']==[1,9,63,71] self.va1 = ftug.virtual_atoms(cg, sidechain=False) self.va2 = ftug.virtual_atoms(cg, sidechain=True)
def main(): usage = """ ./visualize_cg.py cg_file Display the coarse-grain representation of a structure in pymol. """ num_args = 1 parser = OptionParser(usage=usage) # parser.add_option('-u', '--useless', dest='uselesss', # default=False, action='store_true', help='Another useless option') parser.add_option('-g', '--highlight', dest='highlight', default=None, help="Highlight some elements", type='str') parser.add_option('-o', '--output', dest='output', default=None, help="Create a picture of the scene and exit", type='str') parser.add_option('-r', '--longrange', dest='longrange', default=False, action='store_true', help="Display long-range interactions") parser.add_option('-l', '--loops', dest='loops', default=True, action='store_false', help="Don't display the coarse-grain hairpin loops") parser.add_option('-c', '--cones', dest='cones', default=False, action='store_true', help="Display cones that portrude from the stems") parser.add_option('-x', '--text', dest='text', default=False, action='store_true', help="Add labels to the figure.") parser.add_option('-a', '--align', dest='align', default=False, action='store_true', help='Align all of the structures with the first') parser.add_option( '-e', '--encompassing-stems', dest='encompassing_stems', default=False, action='store_true', help='Show the big stems that encompass the colinear ones.') parser.add_option('-v', '--virtual-atoms', dest='virtual_atoms', default=False, action='store_true', help='Display the virtual atoms') parser.add_option('-d', '--distance', dest='distance', default=None, help="Draw the lines between specified virtual residues") parser.add_option('-b', '--basis', dest='basis', default=False, action='store_true', help='Display the coordinate basis of each element') parser.add_option('', '--batch', dest='batch', default=False, action='store_true', help='Start pymol in batch mode') parser.add_option( '', '--sidechain-atoms', dest='sidechain_atoms', default=False, action='store_true', help= 'Include the sidechain atoms. Automatically enables --virtual-atoms') parser.add_option( '', '--rainbow', dest='rainbow', default=False, action='store_true', help= 'Color each of the nucleotide positions (i.e. average atoms) according to the colors of \ the rainbow and their position') parser.add_option('', '--only-elements', dest='only_elements', default=None, help='Display only these elements ' 'element names should be ' 'separated by commas') parser.add_option('', '--color-gradual', dest='color_gradual', default=None, help='Color the specified elements' 'gradually from one to the other, example (i1,i4,m1)', type='str') (options, args) = parser.parse_args() print "hi" if len(args) < num_args: parser.print_help() sys.exit(1) print "hi1" pp = cvp.PymolPrinter() pp.add_loops = options.loops pp.draw_cones = options.cones # sys.exit(1) pp.add_longrange = options.longrange pp.print_text = options.text pp.encompassing_stems = options.encompassing_stems pp.virtual_atoms = options.virtual_atoms pp.sidechain_atoms = options.sidechain_atoms pp.basis = options.basis pp.rainbow = options.rainbow if options.only_elements is not None: pp.only_elements = options.only_elements.split(',') cgs = [] for a in args: cgs += [cmg.CoarseGrainRNA(a)] if options.align: align_cgs(cgs) if options.color_gradual is not None: pp.element_specific_colors = dict() import matplotlib.pyplot as plt cmap = plt.get_cmap('coolwarm') for d in cgs[0].defines: pp.element_specific_colors[d] = 'black' to_color_nodes = options.color_gradual.split(',') for i, node in enumerate(to_color_nodes): print node, cmap(i / float(len(to_color_nodes))) pp.element_specific_colors[node] = cmap(i / float(len(to_color_nodes))) for i, cg in enumerate(cgs): if i > 0: pp.color_modifier = .3 #pp.override_color = 'middle gray' pp.coordinates_to_pymol(cg) # highlight things in purple if options.highlight is not None: for s in options.highlight.split(','): fud.pv('s') pp.add_twists = False pp.add_stem_like(cg, s, color='purple', width=3.) # display the distances between nucleotides if options.distance is not None: virtual_atoms = ftug.virtual_atoms(cg, sidechain=False) for dist_pair in options.distance.split(':'): fud.pv('dist_pair') fr, to = dist_pair.split(',') fr = int(fr) to = int(to) pp.add_dashed(virtual_atoms[fr]["C1'"], virtual_atoms[to]["C1'"], width=1.2) with tf.NamedTemporaryFile() as f: with tf.NamedTemporaryFile(suffix='.pml') as f1: f.write(pp.pymol_string()) f.flush() pymol_cmd = 'hide all\n' pymol_cmd += 'run %s\n' % (f.name) pymol_cmd += 'show cartoon, all\n' pymol_cmd += 'bg white\n' pymol_cmd += 'clip slab, 10000\n' pymol_cmd += 'orient\n' if options.output is not None: pymol_cmd += 'ray\n' pymol_cmd += 'png %s\n' % (options.output) pymol_cmd += 'quit\n' f1.write(pymol_cmd) f1.flush() print "f1.name:", f1.name if options.batch: p = sp.Popen(['pymol', '-cq', f1.name], stdout=sp.PIPE, stderr=sp.PIPE) else: p = sp.Popen(['pymol', f1.name], stdout=sp.PIPE, stderr=sp.PIPE) out, err = p.communicate() print >> sys.stderr, "err:", err
def add_cg(self, cg, labels, color_modifier=1.0): """ :param labels: A dictionary with element names as keys and labels as values. """ rna_plotter = PyMolRNA(cg.name, color_modifier) for key in cg.coords.keys(): if self.only_elements is not None: if key not in self.only_elements: continue (p, n) = cg.coords[key] color = self.get_element_color(key) if key[0] == 's': try: text = labels[key] except KeyError: text = key self.add_stem_like(rna_plotter, cg, text, key, color=color) if self.show_bounding_boxes: self.draw_bounding_boxes(rna_plotter, cg, key) else: if key[0] == 'h': if self.add_loops: try: text = labels[key] except KeyError: text = key + " " + str(cg.get_length(key)) rna_plotter.add_segment(p, n, color, self.cylinder_width, text, key=key) elif key[0] == 'm': twists = cg.get_twists(key) try: text = labels[key] except KeyError: # check if the multiloop is longer than one. If it's not, then # it has an empty define and its length will be 0 if len(cg.defines[key]) == 0: text = key + " 0" else: text = key + " " + \ str(cg.defines[key][1] - cg.defines[key][0] + 1) rna_plotter.add_segment(p, n, color, self.cylinder_width, text, key=key) elif key[0] in 'ft': try: text = labels[key] except KeyError: text = key + " " + \ str(cg.defines[key][1] - cg.defines[key][0] + 1) if self.visualize_three_and_five_prime: rna_plotter.add_segment(p, n, color, self.cylinder_width, text, key=key) elif key[0] == "i": try: text = labels[key] except KeyError: text = key rna_plotter.add_segment(p, n, color, self.cylinder_width, text, key=key) if self.display_virtual_residues: for i in range(1, cg.seq_length + 1): pos = cg.get_virtual_residue(i, True) if cg.get_node_from_residue_num(i)[0] == "s": c = "cyan" else: c = "magenta" rna_plotter.add_sphere(pos, c, 1.) if self.add_longrange: for key1 in cg.longrange.keys(): for key2 in cg.longrange[key1]: if self.only_elements is not None: if key1 not in self.only_elements or key2 not in self.only_elements: continue try: p = cuv.line_segment_distance(cg.coords[key1][0], cg.coords[key1][1], cg.coords[key2][0], cg.coords[key2][1]) rna_plotter.add_dashed(p[0], p[1]) except: continue if self.encompassing_stems: self.add_encompassing_cylinders(rna_plotter, cg, 7.) if self.max_stem_distances > 0: for (s1, s2) in it.permutations(cg.stem_iterator(), r=2): (i1, i2) = cuv.line_segment_distance(cg.coords[s1][0], cg.coords[s1][1], cg.coords[s2][0], cg.coords[s2][1]) if cuv.magnitude(i2 - i1) < self.max_stem_distances: #self.add_segment(i1, i2, 'cyan', 0.3, s1 + " " + s2, key=key) rna_plotter.add_segment(i1, i2, 'cyan', 0.3, key=key) if self.virtual_atoms or self.sidechain_atoms: cg.add_all_virtual_residues() va = ftug.virtual_atoms(cg, sidechain=self.sidechain_atoms) atom_width = 0.5 for i, r in enumerate(sorted(va.keys())): for a in va[r].keys(): if self.rainbow: import matplotlib matplotlib.use('Agg') import matplotlib.pyplot as plt cmap = plt.get_cmap('gist_rainbow') rna_plotter.add_sphere(va[r][a], color=cmap( i / float(len(va.keys()))), width=atom_width) else: d = cg.get_node_from_residue_num(r) if d[0] == 's': if a in ftup.nonsidechain_atoms: rna_plotter.add_sphere(va[r][a], self.stem_color, width=atom_width) else: rna_plotter.add_sphere(va[r][a], 'forest', width=atom_width) elif d[0] == 'i': rna_plotter.add_sphere(va[r][a], 'yellow', width=atom_width) elif d[0] == 'm': rna_plotter.add_sphere(va[r][a], self.multiloop_color, width=atom_width) elif d[0] == 'h': rna_plotter.add_sphere(va[r][a], 'blue', width=atom_width) if self.basis: for d in cg.defines.keys(): origin, basis = ftug.element_coord_system(cg, d) rna_plotter.add_segment(origin, origin + 7. * basis[1], 'purple', 0.5, key=key) self.plotters.append(rna_plotter)
def main(): usage = """ ./visualize_cg.py cg_file Display the coarse-grain representation of a structure in pymol. """ num_args = 1 parser = OptionParser(usage=usage) # parser.add_option('-u', '--useless', dest='uselesss', # default=False, action='store_true', help='Another useless option') parser.add_option('-g', '--highlight', dest='highlight', default=None, help="Highlight some elements", type='str') parser.add_option('-o', '--output', dest='output', default=None, help="Create a picture of the scene and exit", type='str') parser.add_option('-r', '--longrange', dest='longrange', default=False, action='store_true', help="Display long-range interactions") parser.add_option('-l', '--loops', dest='loops', default=True, action='store_false', help="Don't display the coarse-grain hairpin loops") parser.add_option('-c', '--cones', dest='cones', default=False, action='store_true', help="Display cones that portrude from the stems") parser.add_option('-x', '--text', dest='text', default=False, action='store_true', help="Add labels to the figure.") parser.add_option('-a', '--align', dest='align', default=False, action='store_true', help='Align all of the structures with the first') parser.add_option('-e', '--encompassing-stems', dest='encompassing_stems', default=False, action='store_true', help='Show the big stems that encompass the colinear ones.') parser.add_option('-v', '--virtual-atoms', dest='virtual_atoms', default=False, action='store_true', help='Display the virtual atoms') parser.add_option('-d', '--distance', dest='distance', default=None, help="Draw the lines between specified virtual residues") parser.add_option('-b', '--basis', dest='basis', default=False, action='store_true', help='Display the coordinate basis of each element') parser.add_option('', '--batch', dest='batch', default=False, action='store_true', help='Start pymol in batch mode') parser.add_option('', '--sidechain-atoms', dest='sidechain_atoms', default=False, action='store_true', help='Include the sidechain atoms. Automatically enables --virtual-atoms') parser.add_option('', '--rainbow', dest='rainbow', default=False, action='store_true', help='Color each of the nucleotide positions (i.e. average atoms) according to the colors of \ the rainbow and their position') parser.add_option('', '--only-elements', dest='only_elements', default=None, help='Display only these elements ' 'element names should be ' 'separated by commas') parser.add_option('', '--color-gradual', dest='color_gradual', default=None, help='Color the specified elements' 'gradually from one to the other, example (i1,i4,m1)', type='str') (options, args) = parser.parse_args() print "hi" if len(args) < num_args: parser.print_help() sys.exit(1) print "hi1" pp = cvp.PymolPrinter() pp.add_loops = options.loops pp.draw_cones = options.cones # sys.exit(1) pp.add_longrange = options.longrange pp.print_text = options.text pp.encompassing_stems = options.encompassing_stems pp.virtual_atoms = options.virtual_atoms pp.sidechain_atoms = options.sidechain_atoms pp.basis = options.basis pp.rainbow = options.rainbow if options.only_elements is not None: pp.only_elements = options.only_elements.split(',') cgs = [] for a in args: cgs += [cmg.CoarseGrainRNA(a)] if options.align: align_cgs(cgs) if options.color_gradual is not None: pp.element_specific_colors = dict() import matplotlib.pyplot as plt cmap = plt.get_cmap('coolwarm') for d in cgs[0].defines: pp.element_specific_colors[d]= 'black' to_color_nodes = options.color_gradual.split(',') for i,node in enumerate(to_color_nodes): print node, cmap(i / float(len(to_color_nodes))) pp.element_specific_colors[node] = cmap(i / float(len(to_color_nodes))) for i, cg in enumerate(cgs): if i > 0: pp.color_modifier = .3 #pp.override_color = 'middle gray' pp.coordinates_to_pymol(cg) # highlight things in purple if options.highlight is not None: for s in options.highlight.split(','): fud.pv('s') pp.add_twists = False pp.add_stem_like(cg, s, color='purple', width=3.) # display the distances between nucleotides if options.distance is not None: virtual_atoms = ftug.virtual_atoms(cg, sidechain=False) for dist_pair in options.distance.split(':'): fud.pv('dist_pair') fr, to = dist_pair.split(',') fr = int(fr) to = int(to) pp.add_dashed(virtual_atoms[fr]["C1'"], virtual_atoms[to]["C1'"], width=1.2) with tf.NamedTemporaryFile() as f: with tf.NamedTemporaryFile(suffix='.pml') as f1: f.write(pp.pymol_string()) f.flush() pymol_cmd = 'hide all\n' pymol_cmd += 'run %s\n' % (f.name) pymol_cmd += 'show cartoon, all\n' pymol_cmd += 'bg white\n' pymol_cmd += 'clip slab, 10000\n' pymol_cmd += 'orient\n' if options.output is not None: pymol_cmd += 'ray\n' pymol_cmd += 'png %s\n' % (options.output) pymol_cmd += 'quit\n' f1.write(pymol_cmd) f1.flush() print "f1.name:", f1.name if options.batch: p = sp.Popen(['pymol', '-cq', f1.name], stdout=sp.PIPE, stderr=sp.PIPE) else: p = sp.Popen(['pymol', f1.name], stdout=sp.PIPE, stderr=sp.PIPE) out, err = p.communicate() print >>sys.stderr, "err:", err
def setUp(self): cg = ftmc.from_pdb('test/forgi/threedee/data/1y26.pdb') # cg.defines['s0']==[1,9,63,71] self.va1=ftug.virtual_atoms(cg, sidechain=False) self.va2=ftug.virtual_atoms(cg, sidechain=True)
def coordinates_to_pymol(self, cg): loops = list(cg.hloop_iterator()) for key in cg.coords.keys(): if self.constraints is not None: if key not in self.constraints: continue (p, n) = cg.coords[key] color = self.get_element_color(key) if key[0] == 's': self.add_stem_like(cg, key) self.draw_bounding_boxes(cg, key) else: if key[0] == 'h': if self.add_loops: if key in loops: self.add_segment(p, n, color, 1.0, key + " " + str(cg.get_length(key))) elif key[0] == 'm': twists = cg.get_twists(key) # check if the multiloop is longer than one. If it's not, then # it has an empty define and we its length will be 1 if len(cg.defines[key]) == 0: self.add_segment(p, n, color, 1.0, key + " 1") else: self.add_segment(p, n, color, 1.0, key + " " + str(cg.defines[key][1] - cg.defines[key][0] + 1)) self.add_segment(p, p+ 7 * twists[0], 'light gray', 0.3) self.add_segment(n, n+ 7 * twists[1], 'light gray', 0.3) x = (p + n) / 2 t = ftuv.normalize((twists[0] + twists[1]) / 2.) self.add_segment(x, x + 7 * t, 'middle gray', 0.3) elif key[0] == 'f': if self.visualize_three_and_five_prime: self.add_segment(p, n, color, 1.0, key + " " + str(cg.defines[key][1] - cg.defines[key][0] + 1) + "") elif key[0] == 't': if self.visualize_three_and_five_prime: self.add_segment(p, n, color, 1.0, key + " " + str(cg.defines[key][1] - cg.defines[key][0]) + "") else: #self.add_stem_like(cg, key, "yellow", 1.0) self.add_segment(p, n, color, 1.0, key) if self.add_longrange: for key1 in cg.longrange.keys(): for key2 in cg.longrange[key1]: try: p = cuv.line_segment_distance(cg.coords[key1][0], cg.coords[key1][1], cg.coords[key2][0], cg.coords[key2][1]) (point1, point2) = p #point1 = cg.get_point(key1) #point2 = cg.get_point(key2) dash_length = 0.6 gap_length = dash_length * 2 direction = ftuv.normalize(point2 - point1) num_dashes = ftuv.magnitude(point2 - point1) / (dash_length + gap_length) fud.pv('num_dashes') for i in range(int(num_dashes)): self.add_segment(point1 + i * (dash_length + gap_length) * direction, point1 + (i * (dash_length + gap_length) + dash_length) * direction, "purple", 0.3, "") ''' self.add_segment(point1, point2, "purple", 0.3, key1 + " " + key2) ''' except: continue if self.encompassing_stems: self.add_encompassing_cylinders(cg, 7.) if self.max_stem_distances > 0: for (s1, s2) in it.permutations(cg.stem_iterator(), r=2): (i1, i2) = cuv.line_segment_distance(cg.coords[s1][0], cg.coords[s1][1], cg.coords[s2][0], cg.coords[s2][1]) if cuv.magnitude(i2 - i1) < self.max_stem_distances: #self.add_segment(i1, i2, 'cyan', 0.3, s1 + " " + s2) self.add_segment(i1, i2, 'cyan', 0.3) if self.virtual_atoms: va = ftug.virtual_atoms(cg, sidechain=False) atom_width = 0.5 for i,r in enumerate(sorted(va.keys())): for a in va[r].keys(): if self.rainbow: import matplotlib matplotlib.use('Agg') import matplotlib.pyplot as plt cmap = plt.get_cmap('gist_rainbow') self.add_sphere(va[r][a], color_rgb = cmap(i / float(len(va.keys()))), width=atom_width) else: d = cg.get_node_from_residue_num(r) if d[0] == 's': self.add_sphere(va[r][a], 'green', width=atom_width) elif d[0] == 'i': self.add_sphere(va[r][a], 'yellow', width=atom_width) elif d[0] == 'm': self.add_sphere(va[r][a], 'red', width=atom_width) elif d[0] == 'h': self.add_sphere(va[r][a], 'blue', width=atom_width) if self.basis: for d in cg.defines.keys(): origin, basis = ftug.element_coord_system(cg, d) self.add_segment(origin, origin + 7. * basis[1], 'purple', 2.) print >>sys.stderr, "energy_function:", self.energy_function # print the contributions of the energy function, if one is specified if self.energy_function is not None: print >>sys.stderr, "key" sum_energy = 0. e_func = self.energy_function e_func_iter = e_func.interaction_energy_iter(cg, background=False) int_energies = list(e_func_iter) max_energy = max(int_energies, key=lambda x: x[1]) print >>sys.stderr, "max_energy:", max_energy for (interaction, energy) in int_energies: (p, n) = (cg.get_point(interaction[0]), cg.get_point(interaction[1])) scaled_energy = - max_energy[1] + energy self.add_segment(p, n, 'purple', 3 * np.exp(scaled_energy)) sum_energy += energy if self.stem_stem_orientations is not None: for (s1, s2) in it.permutations(cg.stem_iterator(), 2): ''' if cg.are_adjacent_stems(s1, s2): continue ''' if s1 != 's65': if s2 != 's65': continue s1_vec = cg.coords[s1][1] - cg.coords[s1][0] s2_vec = cg.coords[s2][1] - cg.coords[s2][0] (i1, i2) = cuv.line_segment_distance(cg.coords[s1][0], cg.coords[s1][1], cg.coords[s2][0], cg.coords[s2][1]) i_vec = i2 - i1 #i_rej will be orthogonal to s1_vec in the direction #of s2 i_rej = cuv.vector_rejection(i_vec, s1_vec) #plane_vec will be orthogonal to s1_vec and to the direction # of s2 plane_vec = np.cross(i_rej, s1_vec) # s2_proj is in the intersection plane s2_proj_in = cuv.vector_rejection(s2_vec, plane_vec) # s2 proj_out is out of the intersection plane #s2_proj_out = cuv.vector_rejection(s2_vec, i_rej) start_point = cg.coords[s1][0] + 5 * cg.twists[s1][0] ortho_offset = cuv.magnitude(i_rej) dist = cuv.magnitude(i_vec) + 0.0001 lateral_offset = m.sqrt(dist ** 2 - ortho_offset ** 2) if lateral_offset > 10: continue ''' #self.add_segment(start_point, start_point + 10 * cuv.normalize(s2_vec), 'white', 0.5) #self.add_segment(start_point, start_point + 5 * cuv.normalize(plane_vec), 'magenta', 0.5) #self.add_segment(start_point, start_point + 5 * cuv.normalize(i_vec), 'cyan', 0.5) #self.add_segment(i1, i1 + i_rej, 'cyan', 0.5) ''' self.add_segment(start_point, start_point + 7 * cuv.normalize(s2_proj_in), 'white', 1.5) '''
def add_cg(self, cg, labels, color_modifier=1.0): """ :param labels: A dictionary with element names as keys and labels as values. """ rna_plotter = PyMolRNA(cg.name, color_modifier) for key in cg.coords.keys(): if self.only_elements is not None: if key not in self.only_elements: continue (p, n) = cg.coords[key] color = self.get_element_color(key) if key[0] == 's': try: text = labels[key] except KeyError: text = key self.add_stem_like(rna_plotter, cg, text, key, color=color) if self.show_bounding_boxes: self.draw_bounding_boxes(rna_plotter, cg, key) else: if key[0] == 'h': if self.add_loops: try: text = labels[key] except KeyError: text = key + " " + str(cg.get_length(key)) rna_plotter.add_segment(p, n, color, self.cylinder_width, text, key=key) elif key[0] == 'm': twists = cg.get_twists(key) try: text = labels[key] except KeyError: # check if the multiloop is longer than one. If it's not, then # it has an empty define and its length will be 0 if len(cg.defines[key]) == 0: text = key + " 0" else: text = key + " " + \ str(cg.defines[key][1] - cg.defines[key][0] + 1) rna_plotter.add_segment(p, n, color, self.cylinder_width, text, key=key) elif key[0] in 'ft': try: text = labels[key] except KeyError: text = key + " " + \ str(cg.defines[key][1] - cg.defines[key][0] + 1) if self.visualize_three_and_five_prime: rna_plotter.add_segment(p, n, color, self.cylinder_width, text, key=key) elif key[0] == "i": try: text = labels[key] except KeyError: text = key rna_plotter.add_segment( p, n, color, self.cylinder_width, text, key=key) if self.display_virtual_residues: for i in range(1, cg.seq_length + 1): pos = cg.get_virtual_residue(i, True) if cg.get_node_from_residue_num(i)[0] == "s": c = "cyan" else: c = "magenta" rna_plotter.add_sphere(pos, c, 1.) if self.add_longrange: for key1 in cg.longrange.keys(): for key2 in cg.longrange[key1]: if self.only_elements is not None: if key1 not in self.only_elements or key2 not in self.only_elements: continue try: p = cuv.line_segment_distance(cg.coords[key1][0], cg.coords[key1][1], cg.coords[key2][0], cg.coords[key2][1]) rna_plotter.add_dashed(p[0], p[1]) except: continue if self.encompassing_stems: self.add_encompassing_cylinders(rna_plotter, cg, 7.) if self.max_stem_distances > 0: for (s1, s2) in it.permutations(cg.stem_iterator(), r=2): (i1, i2) = cuv.line_segment_distance(cg.coords[s1][0], cg.coords[s1][1], cg.coords[s2][0], cg.coords[s2][1]) if cuv.magnitude(i2 - i1) < self.max_stem_distances: #self.add_segment(i1, i2, 'cyan', 0.3, s1 + " " + s2, key=key) rna_plotter.add_segment(i1, i2, 'cyan', 0.3, key=key) if self.virtual_atoms or self.sidechain_atoms: cg.add_all_virtual_residues() va = ftug.virtual_atoms(cg, sidechain=self.sidechain_atoms) atom_width = 0.5 for i, r in enumerate(sorted(va.keys())): for a in va[r].keys(): if self.rainbow: import matplotlib matplotlib.use('Agg') import matplotlib.pyplot as plt cmap = plt.get_cmap('gist_rainbow') rna_plotter.add_sphere(va[r][a], color=cmap( i / float(len(va.keys()))), width=atom_width) else: d = cg.get_node_from_residue_num(r) if d[0] == 's': if a in ftup.nonsidechain_atoms: rna_plotter.add_sphere( va[r][a], self.stem_color, width=atom_width) else: rna_plotter.add_sphere( va[r][a], 'forest', width=atom_width) elif d[0] == 'i': rna_plotter.add_sphere( va[r][a], 'yellow', width=atom_width) elif d[0] == 'm': rna_plotter.add_sphere( va[r][a], self.multiloop_color, width=atom_width) elif d[0] == 'h': rna_plotter.add_sphere( va[r][a], 'blue', width=atom_width) if self.basis: for d in cg.defines.keys(): origin, basis = ftug.element_coord_system(cg, d) rna_plotter.add_segment( origin, origin + 7. * basis[1], 'purple', 0.5, key=key) self.plotters.append(rna_plotter)