diff options
author | Piotr Rotkiewicz <piotr@pirx.com> | 2008-09-05 21:52:26 +0000 |
---|---|---|
committer | Piotr Rotkiewicz <piotr@pirx.com> | 2008-09-05 21:52:26 +0000 |
commit | 2271b377573ef0b0653373d47042dd223a78b92a (patch) | |
tree | 6b8ce879ad507dd50c205f1ce660d0e4ed2b2a68 | |
parent | 8aff664f2ded4d672a1c6b83837554bc8021b039 (diff) | |
download | nanoengineer-theirix-2271b377573ef0b0653373d47042dd223a78b92a.tar.gz nanoengineer-theirix-2271b377573ef0b0653373d47042dd223a78b92a.zip |
=ProteinChunks.py for review.
-rw-r--r-- | cad/src/graphics/display_styles/ProteinChunks.py | 394 |
1 files changed, 300 insertions, 94 deletions
diff --git a/cad/src/graphics/display_styles/ProteinChunks.py b/cad/src/graphics/display_styles/ProteinChunks.py index 72493c4db..559c02a23 100644 --- a/cad/src/graphics/display_styles/ProteinChunks.py +++ b/cad/src/graphics/display_styles/ProteinChunks.py @@ -22,6 +22,8 @@ piotr 080729: Code cleanup. piotr 080804: Further code cleanup, adding docstrings. +piotr 080904: Added missing docstrings, prepared for review. + """ import foundation.env as env @@ -66,6 +68,17 @@ from utilities.constants import yellow from graphics.drawing.CS_workers import drawcylinder_worker from graphics.drawing.CS_workers import drawsphere_worker +# Protein display style preferences +from utilities.prefs_constants import proteinStyle_prefs_key +from utilities.prefs_constants import proteinStyleColors_prefs_key +from utilities.prefs_constants import proteinStyleQuality_prefs_key +from utilities.prefs_constants import proteinStyleScaleFactor_prefs_key +from utilities.prefs_constants import proteinStyleScaling_prefs_key +from utilities.prefs_constants import proteinStyleHelixColor_prefs_key +from utilities.prefs_constants import proteinStyleStrandColor_prefs_key +from utilities.prefs_constants import proteinStyleCoilColor_prefs_key +from utilities.prefs_constants import proteinStyleSmooth_prefs_key + try: from OpenGL.GLE import glePolyCone from OpenGL.GLE import gleGetNumSides @@ -128,6 +141,10 @@ PROTEIN_STYLE_SIMPLE_CARTOONS = 9 PROTEIN_STYLE_FANCY_CARTOONS = 10 PROTEIN_STYLE_PEPTIDE_TILES = 11 +# I plan to change the following color schemes so they use less +# intrusive colors (maybe just blue-to-white-to-red scale instad +# of red-green-blue spectrum). piotr 080902 + # coloring according to amino acid hydropathy scale (Kyte-Doolittle) AA_COLORS_HYDROPATHY = { "ALA" : orange, @@ -175,6 +192,7 @@ AA_COLORS_POLARITY = { "VAL" : red } # coloring according to amino acid acidity + AA_COLORS_ACIDITY = { "ALA" : green, "ARG" : blue, @@ -199,9 +217,23 @@ AA_COLORS_ACIDITY = { def compute_spline(data, idx, t): """ - Implements a Catmull-Rom spline. - Interpolates between data[idx] and data[idx+1]. - 0.0 <= t <= 1.0. + Implements a Catmull-Rom spline. Interpolates between data[idx] and + data[idx+1] using data[idx-1], data[idx], data[idx+1] and data[idx+2] + points. + + @param data: list of data points to interpolate. it needs to have at least + data points, otherwise will cause an exception + + @param idx: index of data points to be interpolated between + @type idx: int + + @param t: interpolation ratio (0.0 <= t <= 1.0) + @type t: float + + @note: this method is basically identical to the one in DnaCylinderChunks, + so it should be splitted out from here and moved to another, more general + file + """ t2 = t*t t3 = t2*t @@ -215,10 +247,35 @@ def compute_spline(data, idx, t): t3 * (-x0 + 3.0 * x1 - 3.0 * x2 + x3)) return res -def make_tube(points, colors, radii, dpos, resolution=8, trim=True): +def make_tube(points, colors, radii, dpos, resolution=3): """ - Converts a polycylinder tube into a smooth, curved tube - using spline interpolation of points, colors and radii. + Converts a polycylinder tube into a smooth, curved tube using spline + interpolation of points, colors and radii. + + If there is not enough data points, returns the original lists. + Thus, it can be used in the following way: + + pos, col, rad, dpos = make_tube(pos, col, rad, dpos, resolution) + + Assumes that len(points) == len(colors) == len(radii) + + @param points: consecutive points to be interpolated + @type points: list of V or list of float[3] + + @param colors: colors corresponding to the points + @type colors: list of colors + + @param radii: radii correspoding to individual points + @type radii: list of radii + + @param dpos: dpos vectors correspoding to individual points + @type dpos: list of dpos vectors + + @param resolution: specifies a number of points intepolated in-between + two consecutive input points + @type resolution: integer + + @return: tuple of interpolated (points, colors, radii, dpos) """ n = len(points) if n > 3: @@ -260,9 +317,23 @@ def make_tube(points, colors, radii, dpos, resolution=8, trim=True): else: return (points, colors, radii, dpos) +# These two methods are identical to these found in DnaCylinderChunks. + def get_rainbow_color(hue, saturation, value): """ Gets a color of a hue range limited to 0 - 0.667 (red - blue) + + @param hue: color hue (0..1) + @type hue: float + + @param saturation: color saturation (0..1) + @type saturation: float + + @param value: color value (0..1) + @type value: float + + @return: color for given (h,s,v) + """ hue = 0.666 * (1.0 - hue) @@ -274,7 +345,22 @@ def get_rainbow_color(hue, saturation, value): def get_rainbow_color_in_range(pos, count, saturation, value): """ - Create a rainbow color from a range (0, pos/count). + Gets a color of a hue range limited to 0 - 0.667 (red - blue color range) + correspoding to a "pos" value from (0..count) range. + + @param pos: position in (0..count range) + @type pos: integer + + @param count: limits the range of allowable values + @type count: integer + + @param saturation: color saturation (0..1) + @type saturation: float + + @param value: color value (0..1) + @type value: float + + @return: color for given (pos, s, v) """ if count > 1: count -= 1 @@ -305,7 +391,31 @@ class ProteinChunks(ChunkDisplayMode): def _get_aa_color(self, chunk, pos, n_pos, sec, aa, c_sec, n_sec): """ - Returns an amino acid color according to current colormode. + Returns an amino acid color according to the current color mode. + + @param chunk: Protein chunk + @type chunk: Chunk with protein attribute available + + @param pos: residue sequence position + @type pos: int + + @param n_pos: length of the protein sequence + @type n_pos: int + + @param sec: secondary structure type (SS_HELIX, SS_STRAND, or SS_COIL) + @type sec: int + + @param aa: amino acid name (3-letter code) + @type aa: string + + @param c_sec: index of secondary structure element + @type c_sec: int + + @param n_sec: number of secondary structure elements + @type n_sec: int + + @return: residue color according to curreny color mode, or gray + if wrong parameters were specified """ color = gray @@ -348,14 +458,21 @@ class ProteinChunks(ChunkDisplayMode): def drawchunk(self, glpane, chunk, memo, highlighted): """ - Draws reduced representation of a protein chunk. This method is called - per chunk, but in fact draws individual secondary structure elements, + Draws a reduced representation of a protein chunk. This method is called + per chunk, but in fact it draws individual secondary structure elements, i.e. consecutive part of the protein chain composed of a single type - of secondary structure. + of secondary structure. """ + # Note: If the protein model is going to be re-factored in the future + # so that every individual chunk corresponds to a single, homogenoeous + # secondary structure element, this method could be used without + # much changes. + + # Retrieve parameters from memo structure, total_length, ca_list, n_sec = memo + # Get display style settings style = self.proteinStyle scaleFactor = self.proteinStyleScaleFactor resolution = self.proteinStyleQuality @@ -363,7 +480,8 @@ class ProteinChunks(ChunkDisplayMode): smooth = self.proteinStyleSmooth # Set nice joint style for gle Polycone primitives. - gleSetJoinStyle(TUBE_JN_ANGLE | TUBE_NORM_PATH_EDGE | TUBE_JN_CAP | TUBE_CONTOUR_CLOSED ) + gleSetJoinStyle(TUBE_JN_ANGLE | TUBE_NORM_PATH_EDGE \ + | TUBE_JN_CAP | TUBE_CONTOUR_CLOSED ) # Iterate over consecutive secondary structure elements. current_sec = 0 @@ -373,6 +491,7 @@ class ProteinChunks(ChunkDisplayMode): # The length should be at least 3. if n_atoms >= 3: # Alpha carbon trace styles. Simple but fast. + # Use either lines or cylinder to connect consecutive alpha carbons. if style == PROTEIN_STYLE_CA_WIRE or \ style == PROTEIN_STYLE_CA_CYLINDER or \ style == PROTEIN_STYLE_CA_BALL_STICK: @@ -396,12 +515,6 @@ class ProteinChunks(ChunkDisplayMode): width=5, isSmooth=True) - #drawline(color, - # pos1, - # pos1 + dpos1, - # width=5, - # isSmooth=True) - if pos2: drawline(color, pos1, @@ -430,7 +543,10 @@ class ProteinChunks(ChunkDisplayMode): capped=1) elif style == PROTEIN_STYLE_PEPTIDE_TILES: - # Peptide tiles (not implemented yet) + # Peptide tiles: not implemented yet. + # piotr 080903: this option should be removed + # from Protein Display Style PM. + """ for n in range( 1, n_atoms-2 ): pos0, ss0, aa0, idx0, dpos0, cbpos0 = sec[n - 1] pos1, ss1, aa1, idx1, dpos1, cbpos1 = sec[n] @@ -444,7 +560,7 @@ class ProteinChunks(ChunkDisplayMode): tri = [] nor = [] col = [] - + """ elif style == PROTEIN_STYLE_TUBE or \ style == PROTEIN_STYLE_LADDER or \ @@ -454,7 +570,7 @@ class ProteinChunks(ChunkDisplayMode): style == PROTEIN_STYLE_SIMPLE_CARTOONS or \ style == PROTEIN_STYLE_FANCY_CARTOONS: - # All these styles use the same interpolated cubic spline + # All of these styles use the same interpolated cubic spline # that connects alpha carbon atoms. # The following lists store positions, colors, radii and @@ -466,6 +582,9 @@ class ProteinChunks(ChunkDisplayMode): tube_rad = [] tube_dpos = [] + # Fill-in the position, color, radius and peptide position + # lists. + for n in range( 2, n_atoms-2 ): pos00, ss00, a00, idx00, dpos00, cbpos00 = sec[n - 2] pos0, ss0, aa0, idx0, dpos0, cbpos0 = sec[n - 1] @@ -584,7 +703,6 @@ class ProteinChunks(ChunkDisplayMode): # Strands just shrink at the C-terminal end. width = scaleFactor * 1.0 dw = (1.5 * scaleFactor) / ((1.5 * resolution) - 3) - print "dw = ", dw if style == PROTEIN_STYLE_FLAT_RIBBON or \ style == PROTEIN_STYLE_SOLID_RIBBON or \ @@ -611,7 +729,7 @@ class ProteinChunks(ChunkDisplayMode): nor_arr3 = [] col_arr3 = [] - # This should be done faster... are separate + # This should be done faster... are individual # copies of the tube positions really necessary? ###from copy import copy @@ -636,13 +754,32 @@ class ProteinChunks(ChunkDisplayMode): reset = False if self.proteinStyle == PROTEIN_STYLE_ZIGZAG: - drawline(col, last_pos-dpos1, pos-dpos2, width=3) - drawline(col, last_pos+dpos1, pos+dpos2, width=3) - drawline(col, last_pos-dpos1, pos+dpos2, width=1) - drawline(col, pos-dpos2, pos+dpos2, width=1) - drawline(col, last_pos-dpos1, last_pos+dpos1, width=1) + # The line calls below draw an outline + # of ribbon triangles. + drawline(col, + last_pos-dpos1, + pos-dpos2, + width=3) + drawline(col, + last_pos+dpos1, + pos+dpos2, + width=3) + drawline(col, + last_pos-dpos1, + pos+dpos2, + width=1) + drawline(col, + pos-dpos2, + pos+dpos2, + width=1) + drawline(col, + last_pos-dpos1, + last_pos+dpos1, + width=1) if self.proteinStyle == PROTEIN_STYLE_FLAT_RIBBON: + # Flat ribbon only draws a single + # layer of triangles. if pos != last_pos: nvec1 = norm(cross(dpos1, pos-last_pos)) @@ -669,9 +806,22 @@ class ProteinChunks(ChunkDisplayMode): if self.proteinStyle == PROTEIN_STYLE_SOLID_RIBBON or \ self.proteinStyle == PROTEIN_STYLE_SIMPLE_CARTOONS or \ self.proteinStyle == PROTEIN_STYLE_FANCY_CARTOONS: - + # These three styles are similar. + # The difference between "solid ribbon" + # and "fancy cartoons" is that the + # cartoons mode uses rounded edges + # on helices, while solid ribbon uses + # just a flat edge. The difference between + # simple cartoons and fancy cartoons or + # solid ribbon is that the simple cartoons + # mode use simple straight cylinders to + # represent alpha helices. if secondary > 0: - + + # Prepare traiangle strips positioned + # along interpolated curve connecting + # consecutive alpha carbon atoms + col3 = col4 = V(gray) if pos != last_pos: @@ -781,27 +931,43 @@ class ProteinChunks(ChunkDisplayMode): width -= dw ###new_tube_dpos[n] = dpos1 - + # Append dummy positions at both ends for + # GLE polycone rendering. tube_pos_left.append(tube_pos[-2]) tube_pos_right.append(tube_pos[-2]) tube_pos_left.append(tube_pos[-1]) tube_pos_right.append(tube_pos[-1]) if self.proteinStyle == PROTEIN_STYLE_FLAT_RIBBON: - drawtriangle_strip([1.0,1.0,0.0,-2.0], tri_arr0, nor_arr0, col_arr0) + # Note: the "-2" opacity component in the color list + # tells the ColorSorter that this is a multi color + # object and "color material" should be enabled + # while rendering it. + drawtriangle_strip( + [1.0,1.0,0.0,-2.0], tri_arr0, nor_arr0, col_arr0) if self.proteinStyle == PROTEIN_STYLE_SOLID_RIBBON or \ self.proteinStyle == PROTEIN_STYLE_SIMPLE_CARTOONS or \ self.proteinStyle == PROTEIN_STYLE_FANCY_CARTOONS: if secondary == 0: - drawpolycone_multicolor([0,0,0,-2], tube_pos, tube_col, tube_rad) + drawpolycone_multicolor( + [0,0,0,-2], tube_pos, tube_col, tube_rad) else: - if (secondary == 1 and self.proteinStyle == PROTEIN_STYLE_SOLID_RIBBON) or \ + if (secondary == 1 and + self.proteinStyle == PROTEIN_STYLE_SOLID_RIBBON) or \ secondary == 2: - drawtriangle_strip([1.0,1.0,0.0,-2.0], tri_arr0, nor_arr0, col_arr0) - drawtriangle_strip([1.0,1.0,0.0,-2.0], tri_arr1, nor_arr1, col_arr1) - drawtriangle_strip([1.0,1.0,0.0,-2.0], tri_arr2, nor_arr2, col_arr2) - drawtriangle_strip([1.0,1.0,0.0,-2.0], tri_arr3, nor_arr3, col_arr3) + drawtriangle_strip( + [1.0,1.0,0.0,-2.0], + tri_arr0, nor_arr0, col_arr0) + drawtriangle_strip( + [1.0,1.0,0.0,-2.0], + tri_arr1, nor_arr1, col_arr1) + drawtriangle_strip( + [1.0,1.0,0.0,-2.0], + tri_arr2, nor_arr2, col_arr2) + drawtriangle_strip([1.0,1.0,0.0,-2.0], + tri_arr3, nor_arr3, col_arr3) + # Fill in the strand N-terminal end. quad_tri = [] quad_nor = [] @@ -818,25 +984,40 @@ class ProteinChunks(ChunkDisplayMode): quad_col.append(col_arr3[0]) quad_col.append(col_arr2[1]) quad_col.append(col_arr3[1]) - drawtriangle_strip([1.0,1.0,1.0,-2.0],quad_tri,quad_nor,quad_col) + drawtriangle_strip( + [1.0,1.0,1.0,-2.0], quad_tri, quad_nor,quad_col) if (secondary == 1 and self.proteinStyle == PROTEIN_STYLE_FANCY_CARTOONS): # Draw smooth tubes at the edges of the - # helices. - drawtriangle_strip([1.0,1.0,0.0,-2.0], tri_arr0, nor_arr0, col_arr0) - drawtriangle_strip([1.0,1.0,0.0,-2.0], tri_arr1, nor_arr1, col_arr1) - drawpolycone_multicolor([0,0,0,-2], tube_pos_left, tube_col, tube_rad) - drawpolycone_multicolor([0,0,0,-2], tube_pos_right, tube_col, tube_rad) + # helices. + drawtriangle_strip( + [1.0,1.0,0.0,-2.0], + tri_arr0, nor_arr0, col_arr0) + drawtriangle_strip([ + 1.0,1.0,0.0,-2.0], + tri_arr1, nor_arr1, col_arr1) + drawpolycone_multicolor( + [0,0,0,-2], + tube_pos_left, tube_col, tube_rad) + drawpolycone_multicolor( + [0,0,0,-2], + tube_pos_right, tube_col, tube_rad) if (secondary == 1 and style == PROTEIN_STYLE_SIMPLE_CARTOONS): - drawcylinder(tube_col[0][0], tube_pos[1], tube_pos[-3], 2.5, capped=1) + drawcylinder(tube_col[0][0], + tube_pos[1], + tube_pos[-3], 2.5, capped=1) if style == PROTEIN_STYLE_LADDER or \ style == PROTEIN_STYLE_TUBE: - # Draw the tube. - drawpolycone_multicolor([0,0,0,-2], tube_pos, tube_col, tube_rad) - - # increase secondary structure element counter + # Draw a smooth tube connecting alpha carbon positions. + drawpolycone_multicolor([0,0,0,-2], + tube_pos, + tube_col, + tube_rad) + + # Increase secondary structure element counter (for coloring + # by "secondary structure elements order"). current_sec += 1 def drawchunk_selection_frame(self, glpane, chunk, selection_frame_color, memo, highlighted): @@ -872,12 +1053,26 @@ class ProteinChunks(ChunkDisplayMode): piotr 080801: Backbone atoms are omitted. """ + # Draw rotamers using a display list. Create it if necessary. + + # Note: the only command that uses this feature is Edit + # Rotamers. The purpose of this feature is to have + # an atomistic-like display style on top of a reduced + # representation. + + # Note: this implementation may have bugs. The major problem + # is that the display list is never explicitly deleted, + # so using this feature may introduce memory leaks (I am + # not sure about that). + + # The rotamer is rendered using a style resembling "Tubes". + if chunk.protein: if highlighted: # If highlighhting, just draw everything without using # the display list. - aa_list = chunk.protein.get_amino_acids() color = yellow + aa_list = chunk.protein.get_amino_acids() glMaterialfv( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, @@ -906,17 +1101,19 @@ class ProteinChunks(ChunkDisplayMode): 0.2, True)) else: - # Draw rotamers using a display list. Create it if necessary. + """ from PyQt4.Qt import QFont, QString, QColor, QFontMetrics - labelFont = QFont( QString("Lucida Grande"), 16) fm = QFontMetrics(labelFont) - + """ if not chunk.protein.residues_dl: + # Create a new residues display list if one is not present. chunk.protein.residues_dl = glGenLists(1) glNewList(chunk.protein.residues_dl, GL_COMPILE) aa_list = chunk.protein.get_amino_acids() for aa in aa_list: + # Iterate over amino acids and check if any rotamer + # is in 'expanded' state. if chunk.protein.is_expanded(aa): aa_atom_list = aa.get_side_chain_atom_list() for atom in aa_atom_list: @@ -929,14 +1126,15 @@ class ProteinChunks(ChunkDisplayMode): GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, color[:3]) - drawsphere_worker((pos1, 0.2, 1)) - _name = aa.get_atom_name(atom) - textpos = chunk.abs_to_base(atom.posn()) + 2.0 * glpane.out - glColor3f(1,1,1) - - chunk.glpane.renderText(textpos[0], textpos[1], textpos[2], _name, labelFont) + drawsphere_worker((pos1, 0.2, 1, 1)) + ### _name = aa.get_atom_name(atom) + ### textpos = chunk.abs_to_base(atom.posn()) + 2.0 * glpane.out + ### glColor3f(1,1,1) + ### chunk.glpane.renderText(textpos[0], textpos[1], textpos[2], _name, labelFont) + + # Draw bonds for bond in atom.bonds: if bond.atom2 in aa_atom_list: if atom == bond.atom1: @@ -959,6 +1157,7 @@ class ProteinChunks(ChunkDisplayMode): True)) glEndList() + # Call the residues display list glCallList(chunk.protein.residues_dl) return @@ -1000,48 +1199,48 @@ class ProteinChunks(ChunkDisplayMode): def _get_ss(aa): """ - Returns secondary structure for an amino acid. + Returns secondary structure for a residue, or SS_COIL if + aa is None + + @param aa: amino acid + @type aa: Residue """ if aa: return aa.get_secondary_structure() - return 0 + return SS_COIL def _get_aa(aa): """ - Returns a three-letter amino acid code. + Returns a three-letter amino acid code for a residue, + or "UNK" if aa is None. + + @param aa: amino acid + @type aa: Residue """ if aa: return aa.get_three_letter_code() + return "UNK" + # Return None if the chunk is None if chunk is None: return None + # Return None if the chunk is not a protein. if chunk.protein is None: return None + # List of secondary structure elements structure = [] - from utilities.prefs_constants import proteinStyle_prefs_key - from utilities.prefs_constants import proteinStyleColors_prefs_key - from utilities.prefs_constants import proteinStyleQuality_prefs_key - from utilities.prefs_constants import proteinStyleScaleFactor_prefs_key - from utilities.prefs_constants import proteinStyleScaling_prefs_key - from utilities.prefs_constants import proteinStyleHelixColor_prefs_key - from utilities.prefs_constants import proteinStyleStrandColor_prefs_key - from utilities.prefs_constants import proteinStyleCoilColor_prefs_key - from utilities.prefs_constants import proteinStyleSmooth_prefs_key - + # Retrieve protein style properties from user preferences. self.proteinStyle = env.prefs[proteinStyle_prefs_key] + 1 - self.proteinStyleSmooth = env.prefs[proteinStyleSmooth_prefs_key] self.proteinStyleQuality = 2 * env.prefs[proteinStyleQuality_prefs_key] self.proteinStyleScaling = env.prefs[proteinStyleScaling_prefs_key] self.proteinStyleScaleFactor = env.prefs[proteinStyleScaleFactor_prefs_key] - self.proteinStyleColors = env.prefs[proteinStyleColors_prefs_key] - self.proteinStyleAuxColors = 0 self.proteinStyleCustomColor = gray self.proteinStyleAuxCustomColor = gray @@ -1051,10 +1250,10 @@ class ProteinChunks(ChunkDisplayMode): self.proteinStyleCoilColor = env.prefs[proteinStyleCoilColor_prefs_key] # Extract secondary structure elements - # Every element is a list of consecutive, non-broken C-alpha atoms - # in the same secondary structure conformation. The list also includes + # Every element is a list of consecutive C-alpha atoms of the same + # secondary structure conformation. The list also includes # two "dummy" atoms - either preceding and following residues, or - # pre-computed chain extensions. + # pre-computed dummy atoms extensions. # Empty SS element. sec = [] @@ -1069,7 +1268,8 @@ class ProteinChunks(ChunkDisplayMode): # "dpos" vectors can be flipped so the angle between consecutive # "dpos" vectors is less than 90 degree to avoid visual problems. - # dictionary of corresponding Ca-Cb atoms for rendering "Ladder" style. + # dictionary of corresponding Ca-Cb atoms for rendering of the + # "Ladder" style. ca_cb = {} n_ca = 0 @@ -1078,6 +1278,8 @@ class ProteinChunks(ChunkDisplayMode): last_dpos = None last_ca_atom = None + # Calculate "dpos" vectors paralles to the peptide planes. + for aa in chunk.protein.get_amino_acids(): last_c_atom = aa.get_c_atom() last_o_atom = aa.get_o_atom() @@ -1094,7 +1296,8 @@ class ProteinChunks(ChunkDisplayMode): n0 = last_dpos n1 = dpos d = dot(n0, n1) - # Flip dpos if > 90 deg. + # Flip dpos if the angle between consecutive planes + # is > 90 deg. if d < 0.0: dpos = -1.0 * dpos last_dpos = dpos @@ -1120,8 +1323,10 @@ class ProteinChunks(ChunkDisplayMode): anum = 0 - # Smoothing of helices and beta-strands. - + # Smoothing alpha-helices and beta-strands. The consecutive "dpos" + # vectors are smoothed using a sliding windows and weighted average. + # Beta-strands use longer averaging window than alpha-helices. + if self.proteinStyleSmooth and \ (self.proteinStyle == PROTEIN_STYLE_TUBE or self.proteinStyle == PROTEIN_STYLE_LADDER or @@ -1154,23 +1359,23 @@ class ProteinChunks(ChunkDisplayMode): next_aa = None next_dpos = None - if (ss == 2 or prev_ss == 2 or next_ss == 2) and prev_ca and next_ca: - ca_pos = 0.5 * (0.5 * (prev_ca_pos + next_ca_pos) + ca_pos) - if next_ss == 2 and prev_ss == 2: + if (ss == 1 or prev_ss == 1 or next_ss == 1) and prev_ca and next_ca: + if prev_dpos and next_dpos: dpos = norm(prev_dpos + dpos + next_dpos) smooth_list.append((ca, ca_pos, ss, aa, dpos, i)) - #if ss == 1: - if (ss == 1 or prev_ss == 1 or next_ss == 1) and prev_ca and next_ca: - if prev_dpos and next_dpos: + if (ss == 2 or prev_ss == 2 or next_ss == 2) and prev_ca and next_ca: + ca_pos = 0.5 * (0.5 * (prev_ca_pos + next_ca_pos) + ca_pos) + if next_ss == 2 and prev_ss == 2: dpos = norm(prev_dpos + dpos + next_dpos) smooth_list.append((ca, ca_pos, ss, aa, dpos, i)) for ca, ca_pos, ss, aa, dpos, i in smooth_list: ca_list[i] = (ca, ca_pos, ss, aa, dpos) + # Build the list of secondary structure elements. + n_sec = 0 - for i in range( n_ca ): ca, ca_pos, ss, aa, dpos = ca_list[i] @@ -1223,8 +1428,8 @@ class ProteinChunks(ChunkDisplayMode): # inside a continuous secondary structure chain fragment # (ss element) and FOUR dummy atom positions (two at # each of both terminals). - # - # The dummy atom positions can be None and therefore + + # The dummy atom positions can't be None and therefore # the spline interpolator has to compute fake positions # of the terminal atoms. @@ -1235,7 +1440,7 @@ class ProteinChunks(ChunkDisplayMode): pos1, ss1, aa1, idx1, dpos1, cbpos1 = sec[1] pos2, ss2, aa2, idx2, dpos2, cbpos2 = sec[2] pos3, ss3, aa3, idx3, dpos3, cbpos3 = sec[3] - #pos4, ss4, aa4, idx4, dpos4, cbpos4 = sec[4] + ### pos4, ss4, aa4, idx4, dpos4, cbpos4 = sec[4] if pos1 == pos2: pos1 = pos1 - (pos3 - pos2) sec[1] = (pos1, ss1, aa1, idx1, dpos1, cbpos1) @@ -1243,13 +1448,14 @@ class ProteinChunks(ChunkDisplayMode): pos1, ss1, aa1, idx1, dpos1, cbpos1 = sec[-2] pos2, ss2, aa2, idx2, dpos2, cbpos2 = sec[-3] pos3, ss3, aa3, idx3, dpos3, cbpos3 = sec[-4] - #pos4, ss4, aa4, idx4, dpos4, cbpos4 = sec[-5] + ### pos4, ss4, aa4, idx4, dpos4, cbpos4 = sec[-5] if pos1 == pos2: pos1 = pos1 - (pos3 - pos2) sec[-2] = (pos1, ss1, aa1, idx1, dpos1, cbpos1) # Make sure that the interior surface of helices - # is properly oriented. + # is properly oriented. This is important for "Fancy Cartoons" + # display style. if ss == 1: pos2, ss2, aa2, idx2, dpos2, cbpos2 = sec[2] |