Permalink
Browse files

Merge branch 'master' of https://github.com/jaredsampson/Pymol-script…

…-repo into testscript
  • Loading branch information...
tlinnet committed Jun 8, 2012
2 parents 7d6ee92 + c79f982 commit 874bc44779630a3c8036b4eb3b30345f3f385de3
Showing with 2,191 additions and 0 deletions.
  1. +227 −0 elbow_angle.py
  2. +53 −0 examples/elbow_angle.pml
  3. +1,911 −0 transformations.py
View
@@ -0,0 +1,227 @@
+'''
+More information at: http://www.pymolwiki.org/index.php/elbow_angle
+
+Calculate the elbow angle of an antibody Fab complex and optionally draw a
+graphical representation of the vectors used to determine the angle.
+
+NOTE: There is no automatic checking of the validity of limit_l and limit_h
+values or of the assignment of light and heavy chain IDs. If these are entered
+incorrectly or omitted, the reported angle will likely be incorrect.
+
+As always with these things, your mileage may vary. Use at your own risk!
+
+REQUIREMENTS
+
+ numpy, version 1.6
+ http://numpy.scipy.org
+
+ transformations.py, version 2012.01.01
+ by Christoph Gohlke
+ www.lfd.uci.edu/~gohlke/code
+
+ May also require an edit to transformations.py:
+ Changes `1e-8` to `1e-7` in lines 357 & 363 to avoid a numerical error.
+
+ com.py
+ by Jason Vertrees
+ http://www.pymolwiki.org/index.php/com
+'''
+
+__author__ = 'Jared Sampson'
+__version__ = '0.1'
+
+
+from pymol import cmd
+import transformations
+import com
+import numpy
+
+
+################################################################################
+def calc_super_matrix(mobile,static):
+ '''
+
+DESCRIPTION
+
+ Aligns two objects (or selections), returns the transformation matrix,
+ and resets the matrix of the mobile object.
+
+ Uses CEAlign PyMOL function for alignment.
+
+ARGUMENTS
+
+ mobile = string: selection describing the mobile object whose rotation
+ matrix will be reported
+
+ static = string: selection describing the static object onto which the
+ mobile object will be aligned
+
+REQUIRES: numpy
+ '''
+
+ cmd.cealign(static,mobile)
+# cmd.super(mobile,static)
+ T = cmd.get_object_matrix(mobile)
+
+ R = numpy.identity(4)
+ k=0
+ for i in range (0,4):
+ for j in range (0,4):
+ R[i][j] = T[k]
+ k+=1
+
+ return R
+
+
+
+################################################################################
+def elbow_angle(obj,light='L',heavy='H',limit_l=107,limit_h=113,draw=0):
+
+ """
+
+DESCRIPTION
+
+ Calculates the integer elbow angle of an antibody Fab complex and
+ optionally draws a graphical representation of the vectors used to
+ determine the angle.
+
+ARGUMENTS
+
+ obj = string: object
+
+ light/heavy = strings: chain ID of light and heavy chains, respectively
+
+ limit_l/limit_h = integers: residue numbers of the last residue in the
+ light and heavy chain variable domains, respectively
+
+ draw = boolean: Choose whether or not to draw the angle visualization
+
+REQUIRES: com.py, transformations.py, numpy (see above)
+
+
+ """
+
+ # store current view
+ orig_view = cmd.get_view()
+
+ limit_l = int(limit_l)
+ limit_h = int(limit_h)
+ draw = int(draw)
+
+
+ # for temp object names
+ tmp_prefix = "tmp_elbow_"
+
+ prefix = tmp_prefix + obj + '_'
+
+ # names
+ vl = prefix + 'VL'
+ vh = prefix + 'VH'
+ cl = prefix + 'CL'
+ ch = prefix + 'CH'
+
+ # selections
+ vl_sel = 'polymer and %s and chain %s and resi 1-%i' % (obj, light, limit_l)
+ vh_sel = 'polymer and %s and chain %s and resi 1-%i' % (obj, heavy, limit_h)
+ cl_sel = 'polymer and %s and chain %s and not resi 1-%i' % (obj, light, limit_l)
+ ch_sel = 'polymer and %s and chain %s and not resi 1-%i' % (obj, heavy, limit_h)
+ v_sel = '(('+vl_sel+') or ('+vh_sel+'))'
+ c_sel = '(('+cl_sel+') or ('+ch_sel+'))'
+
+
+ # create temp objects
+ cmd.create(vl,vl_sel)
+ cmd.create(vh,vh_sel)
+ cmd.create(cl,cl_sel)
+ cmd.create(ch,ch_sel)
+
+ # superimpose vl onto vh, calculate axis and angle
+ Rv = calc_super_matrix(vl,vh)
+ angle_v,direction_v,point_v = transformations.rotation_from_matrix(Rv)
+
+ # superimpose cl onto ch, calculate axis and angle
+ Rc = calc_super_matrix(cl,ch)
+ angle_c,direction_c,point_c = transformations.rotation_from_matrix(Rc)
+
+ # delete temporary objects
+ cmd.delete(vl)
+ cmd.delete(vh)
+ cmd.delete(cl)
+ cmd.delete(ch)
+
+ if (numpy.dot(direction_v,direction_c)>0):
+ direction_c = direction_c * -1 # ensure angle is > 90 (need to standardize this)
+
+ elbow = int(numpy.degrees(numpy.arccos(numpy.dot(direction_v,direction_c))))
+# while (elbow < 90):
+# elbow = 180 - elbow # limit to physically reasonable range
+
+
+ # compare the direction_v and direction_c axes to the vector defined by
+ # the C-alpha atoms of limit_l and limit_h of the original fab
+ hinge_l_sel = "%s//%s/%s/CA" % (obj,light,limit_l)
+ hinge_h_sel = "%s//%s/%s/CA" % (obj,heavy,limit_h)
+ hinge_l = cmd.get_atom_coords(hinge_l_sel)
+ hinge_h = cmd.get_atom_coords(hinge_h_sel)
+ hinge_vec = numpy.array(hinge_h) - numpy.array(hinge_l)
+
+ test = numpy.dot(hinge_vec,numpy.cross(direction_v,direction_c))
+ if (test > 0):
+ elbow = 360 - elbow
+
+ print " Elbow angle: %i degrees" % elbow
+
+ if (draw==1):
+ # there is probably a more elegant way to do this, but
+ # it works so I'm not going to mess with it for now
+
+ pre = obj+'_elbow_'
+
+ # draw hinge vector
+ cmd.pseudoatom(pre+"hinge_l",pos=hinge_l)
+ cmd.pseudoatom(pre+"hinge_h",pos=hinge_h)
+ cmd.distance(pre+"hinge_vec",pre+"hinge_l",pre+"hinge_h")
+ cmd.set("dash_gap",0)
+
+ # draw the variable domain axis
+ com_v = com.COM(v_sel)
+ start_v = [a - 10*b for a, b in zip(com_v, direction_v)]
+ end_v = [a + 10*b for a, b in zip(com_v, direction_v)]
+ cmd.pseudoatom(pre+"start_v",pos=start_v)
+ cmd.pseudoatom(pre+"end_v",pos=end_v)
+ cmd.distance(pre+"v_vec",pre+"start_v",pre+"end_v")
+
+ # draw the constant domain axis
+ com_c = com.COM(c_sel)
+ start_c = [a - 10*b for a, b in zip(com_c, direction_c)]
+ end_c = [a + 10*b for a, b in zip(com_c, direction_c)]
+ cmd.pseudoatom(pre+"start_c",pos=start_c)
+ cmd.pseudoatom(pre+"end_c",pos=end_c)
+ cmd.distance(pre+"c_vec",pre+"start_c",pre+"end_c")
+
+ # customize appearance
+ cmd.hide("labels",pre+"hinge_vec");cmd.hide("labels",pre+"v_vec");cmd.hide("labels",pre+"c_vec");
+ cmd.color("green",pre+"hinge_l");cmd.color("red",pre+"hinge_h");cmd.color("black",pre+"hinge_vec");
+ cmd.color("black",pre+"start_v");cmd.color("black",pre+"end_v");cmd.color("black",pre+"v_vec");
+ cmd.color("black",pre+"start_c");cmd.color("black",pre+"end_c");cmd.color("black",pre+"c_vec")
+ # draw spheres
+ cmd.show("spheres",pre+"hinge_l or "+pre+"hinge_h")
+ cmd.show("spheres",pre+"start_v or "+pre+"start_c")
+ cmd.show("spheres",pre+"end_v or "+pre+"end_c")
+ cmd.set("sphere_scale",2)
+ cmd.set("dash_gap",0,pre+"hinge_vec")
+ cmd.set("dash_width",5)
+ cmd.set("dash_radius",0.3)
+
+ # group drawing objects
+ cmd.group(pre,pre+"*")
+
+ # restore original view
+ cmd.set_view(orig_view)
+
+ return 0
+
+cmd.extend("elbow_angle",elbow_angle)
+
+
+
View
@@ -0,0 +1,53 @@
+reinitialize
+import elbow_angle
+
+bg_color white
+
+# example structures from Stanfield, et al. JMB 2006
+# doi:10.1016/j.jmb.2006.01.023
+fetch 1bbd, async=0
+fetch 7fab, async=0
+fetch 1dba, async=0
+fetch 1plg, async=0
+fetch 1nl0, async=0
+
+dss
+as cartoon
+set cartoon_transparency, 0.7
+
+remove all and not chain L+H
+util.mass_align("1bbd and ((chain L and resi 1-114) or (chain H and resi 1-118))")
+
+# adopt a similar view to Figure 1 in Stanfield, et al.
+set_view (\
+ -0.953261435, -0.226005003, 0.200535893,\
+ -0.230026290, 0.112494141, -0.966659248,\
+ 0.195909262, -0.967606425, -0.159222543,\
+ 0.000000000, 0.000000000, -230.122619629,\
+ 62.279075623, 48.879341125, 138.177505493,\
+ 181.430419922, 278.814819336, -20.000000000 )
+
+# 1bbd
+# Stanfield: 127 deg
+# elbow_angle.py: 125 deg
+elbow_angle 1bbd, limit_l=114, limit_h=118, draw=1
+
+# 7fab
+# Stanfield: 132 deg
+# elbow_angle.py: 126 deg
+elbow_angle 7fab, limit_l=104, limit_h=117, draw=1
+
+# 1dba
+# Stanfield: 183 deg
+# elbow_angle.py: 176 deg
+elbow_angle 1dba, draw=1
+
+# 1plg
+# Stanfield: 190 deg
+# elbow_angle.py: 189 deg
+elbow_angle 1plg, limit_l=112, limit_h=117, draw=1
+
+# 1nl0
+# Stanfield: 220 deg
+# elbow_angle.py: 221 deg
+elbow_angle 1nl0, draw=1
Oops, something went wrong.

0 comments on commit 874bc44

Please sign in to comment.