https://wiki.pymol.org/api.php?action=feedcontributions&user=Srballard&feedformat=atom
PyMOL Wiki - User contributions [en]
2024-03-29T06:24:51Z
User contributions
MediaWiki 1.35.1
https://wiki.pymol.org/index.php?title=SuperSym&diff=5624
SuperSym
2010-06-30T17:36:48Z
<p>Srballard: /author Feedback section added</p>
<hr />
<div>[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
[[File:SuperSymExample2.png|300px|thumb|right|Full cell of symmetry partners with symmetry axes displayed]]<br />
SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for all versions is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/], and the most recent code is available in regular text format from [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
Symmetry axes are not defined for all space groups, and do not display properly for some.<br />
<br />
This plugin requires cctbx and numeric python (numpy).<br />
<br />
Primary coding and development was done by Stuart Ballard. All comments, questions, and issues should be directed to him at srballard@wisc.edu.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym v1.2, download SuperSymPlugin12.py from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/]. In PyMOL, go to:<br />
*Plugin > Manage Plugins > Install...<br />
A file selector dialog will appear. Select SuperSymPlugin12.py. PyMOL will direct you to restart, and upon doing so SuperSym will be accessible through the Plugin menu.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, use the run command in PyMOL on SuperSymPlugin12.py.<br />
<br />
Note: previous errors resulting from incorrect naming of the plugin file have been resolved in v1.2.<br />
<br />
==Feedback==<br />
<br />
Please post any comments, complaints, bug fix requests, useful tricks, or cool adaptations of SuperSym here.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
**'''By Partner'''<br />
***Generates only those symmetry partners which the user specifies by their defining symmetry operators<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Cartoon'''<br />
***Convenience function to display symmetry partners as cartoons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSymSource&diff=9002
SuperSymSource
2010-01-11T21:42:22Z
<p>Srballard: /* Source Code */</p>
<hr />
<div>This page contains source files for the [[SuperSym]] plugin. For documentation and use instructions, see [[SuperSym]].<br />
<br />
==Source Code==<br />
<br />
File: SuperSymPlugin12.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import tkFileDialog<br />
import sys<br />
import string, re<br />
from pymol import stored, cmd, selector<br />
import math<br />
from pymol.cgo import *<br />
from pymol.vfont import plain<br />
try:<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
from cctbx import uctbx, sgtbx<br />
except:<br />
quit("Oops! SuperSym requires cctbx and numeric python to function. Please install these.")<br />
<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addcascademenu('Plugin','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Cartoon',<br />
label = 'Cartoon',<br />
command = lambda s = self: graphicsDialog(s, 2))<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 4))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("white", prefix + "0" + str(i) + "*")<br />
cmd.center(prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("white", prefix + str(i) + "*")<br />
cmd.center(prefix + str(i) + "*")<br />
<br />
except:<br />
pass<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)] + " (currently white)",<br />
parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # show cartoon<br />
cmd.show("cartoon", prefix + "*")<br />
if mode == 3: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 4: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell(object, 3.0)<br />
else:<br />
draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_symops(object, 2.0)<br />
else:<br />
draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym \nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
opMatrices = []<br />
vars = ["x","y","z"]<br />
i = 0<br />
j = 0<br />
k = 0<br />
#CREATE 4X4 MATRICES FOR SYMMETRY OPERATORS<br />
for raw_op in raw_ops:<br />
ops = raw_op.split(",")<br />
matrix = [[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,1]]<br />
for j in range(len(ops)):<br />
for k in range(len(vars)):<br />
index = ops[j].find(vars[k])<br />
if index != -1:<br />
if index == 0:<br />
matrix[k][j] = 1<br />
elif ops[j][index - 1] == "-":<br />
matrix[k][j] = -1<br />
else:<br />
matrix[k][j] = 1<br />
index = ops[j].find("/")<br />
if index != -1:<br />
matrix[3][j] = float(ops[j][index - 1]) / float(ops[j][index + 1])<br />
opMatrices.append(matrix)<br />
i=i+1<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb, 0.0], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg, 0.0], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2), 0.0],<br />
[0.0,0.0,0.0,1.0]])<br />
fracToOrt = fracToOrt.transpose()<br />
ortToFrac = inv(fracToOrt)<br />
stored.atoms = []<br />
cmd.iterate_state(1,object,"stored.atoms.append([x,y,z,1])")<br />
stored.atoms = N.array(stored.atoms)<br />
fracCoords = N.dot(stored.atoms,ortToFrac)<br />
for i in opList:<br />
try:<br />
op = opMatrices[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
newCoordsFrac = N.dot(fracCoords, op)<br />
stored.newCoords = N.dot(newCoordsFrac, fracToOrt)<br />
stored.j = 0<br />
cmd.alter_state(1,copy,"x,y,z = stored.newCoords[stored.j][0], stored.newCoords[stored.j][1], stored.newCoords[stored.j][2]; stored.j = stored.j + 1")<br />
xSum=ySum=zSum=0.0<br />
for k in range(len(newCoordsFrac)):<br />
xSum = newCoordsFrac[k][0] + xSum<br />
ySum = newCoordsFrac[k][1] + ySum<br />
zSum = newCoordsFrac[k][2] + zSum<br />
center = N.array([xSum,ySum,zSum])<br />
center = center/len(stored.newCoords)<br />
shift = [-math.floor(center[0]) + cell[0], -math.floor(center[1]) + cell[1], -math.floor(center[2]) + cell[2]]<br />
cell_shift(copy,shift[0],shift[1],shift[2],0)<br />
'''<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
#cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
#stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
#atoms = cmd.count_atoms(copy)<br />
#cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
#xMean = (stored.xSum / atoms)<br />
#yMean = (stored.ySum / atoms)<br />
#zMean = (stored.zSum / atoms)<br />
#xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
#dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
#cell_shift(copy,dX,dY,dZ, 0)<br />
'''<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
'''<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
'''<br />
<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
<br />
#CELL DRAWING<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
<br />
#AXES DRAWING<br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
#import string, math<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
<br />
#! /usr/bin/env python<br />
# List all axes in the unit cell.<br />
<br />
# usage:<br />
# python all_axes.py - show axes for the 230 reference settings.<br />
# python all_axes.py P2 - show axes for (e.g.) space group P2<br />
<br />
# RWGK = Ralf W. Grosse-Kunstleve<br />
# RWGK Some further refinement is required:<br />
# RWGK - List only the axes of highest order (e.g. only 4, not 4 and 2).<br />
# RWGK - List only the axes with the smallest intrinsic component<br />
# RWGK (e.g. list only 3(1), not both 3(1) and 3(2)).<br />
# RWGK See also: comment regarding shift_range below.<br />
<br />
def list_plus(lhs, rhs):<br />
return [l + r for l, r in zip(lhs, rhs)]<br />
<br />
def list_minus(lhs, rhs):<br />
return [l - r for l, r in zip(lhs, rhs)]<br />
<br />
def list_multiplies(lhs, rhs):<br />
return [l * r for l, r in zip(lhs, rhs)]<br />
<br />
def list_divides(lhs, rhs):<br />
return [l / r for l, r in zip(lhs, rhs)]<br />
<br />
def list_modulus(lhs, rhs):<br />
return [l % r for l, r in zip(lhs, rhs)]<br />
<br />
def list_dot_product(lhs, rhs=0):<br />
if (rhs == 0): rhs = lhs<br />
result = 0<br />
for l, r in zip(lhs, rhs): result += l * r<br />
return result<br />
<br />
def str_ev(EV):<br />
return "[%d,%d,%d]" % EV<br />
<br />
###def fract_2_dec(fraction):<br />
### list = fraction.split('/')<br />
### if len(list) == 2 and list[1] != 0:<br />
### decimal = string.atof(list[0])/string.atof(list[1])<br />
### else:<br />
### decimal = string.atof(fraction)<br />
### return decimal<br />
<br />
def rlc_RTMxAnalysis(M):<br />
r_info = sgtbx.rot_mx_info(M.r())<br />
t_info = sgtbx.translation_part_info(M)<br />
t_intrinsic = t_info.intrinsic_part().mod_positive().as_double()<br />
t_shift = t_info.origin_shift().mod_positive().as_double()<br />
<br />
#End = list_plus(Start + map(None,r_info.ev()))<br />
####debug<br />
### trans = 0<br />
### length = 0<br />
####debug<br />
<br />
#if (r_info.type() == 1):<br />
if (r_info.type() < 2):<br />
#(rt, start, end) = ('1',(0,0,0),(0,0,0))<br />
return None<br />
#elif (r_info.type() == -1):<br />
# (rt, start, end) = (str(r_info.type()),t_shift,())<br />
elif (abs(r_info.type()) == 2):<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
elif (r_info.type() == 3):<br />
if (r_info.sense() >= 0) :<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),(0,0,0),t_intrinsic))))<br />
# trans = N.sqrt(t_intrinsic[0]**2 + t_intrinsic[1]**2 + t_intrinsic[2]**2)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
# fudge to make sure that PyMOL actually draws the axis (move it slightly off [1,-1,1]) !!!<br />
r[0] = r[0]*1.000001<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
#(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
(start, end) = (t_shift,tuple(list_plus(t_shift,r)))<br />
length = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),start, end))))<br />
<br />
# r_info.sense() for 3^1 and 3^2 seems always to be "1" ???<br />
# if r_info.sense() < 0:<br />
# subscript = str(1-r_info.sense())<br />
# else:<br />
# subscript = str(r_info.sense())<br />
<br />
# use ratio of trans to length to get the correct axis symbol:<br />
# fudged the value to get the right numbers. (using length/2., rather than length/3.)<br />
if trans < length*0.5 :<br />
subscript = '1'<br />
else:<br />
subscript = '2'<br />
<br />
rt = str(r_info.type())+ "^" + subscript <br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
### print "Type, sense, Start, End, length, trans", rt, r_info.sense(), start, end, length, trans<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length)<br />
# print "(rt, start, end)", (rt,start,end)<br />
else:<br />
return None<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
elif (r_info.sense() > 0):<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
subscript = str(int(trans*r_info.type()+.5)) # add 0.5 to fix rounding errors<br />
(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
else:<br />
return None<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length),<br />
# print "(rt, start, end)", (rt,start,end)<br />
return (rt, start, end)<br />
<br />
def get_all_axes(space_group_symbol=None, space_group_info=None, extension=0):<br />
assert space_group_symbol is None or space_group_info is None<br />
shift_range = 1 # RWGK Works for the 230 reference settings; it is not<br />
# RWGK clear to me (rwgk) what value is needed in general.<br />
if (space_group_symbol is not None):<br />
space_group_info = sgtbx.space_group_info(symbol=space_group_symbol)<br />
#space_group_info.show_summary()<br />
<br />
axes_dict = {}<br />
for smx in space_group_info.group():<br />
r = smx.r()<br />
t = smx.t()<br />
shift = [0,0,0]<br />
for shift[0] in range(-shift_range,shift_range+1):<br />
for shift[1] in range(-shift_range,shift_range+1):<br />
for shift[2] in range(-shift_range,shift_range+1):<br />
ts = t.plus(sgtbx.tr_vec(shift, 1)).new_denominator(t.den())<br />
m = sgtbx.rt_mx(r, ts)<br />
#print m<br />
rtmxanal = rlc_RTMxAnalysis(m)<br />
#print r, t, shift, ts, m<br />
if rtmxanal:<br />
#print rtmxanal<br />
axes_dict[rtmxanal] = 0<br />
axes_list = axes_dict.keys()<br />
axes_list.sort()<br />
<br />
# reject nonenantiomorphic space groups<br />
if len(axes_list) > 0 and not re.compile("[A-z]").search(space_group_symbol[1:]):<br />
try:<br />
sgtbx.space_group_info(space_group_symbol).show_summary(), <br />
#print len(axes_list), space_group_symbol<br />
except:<br />
print space_group, space_group_symbol<br />
print<br />
sys.exit(1)<br />
axes = []<br />
for a in axes_list:<br />
if len(a) == 3 and len(a[1]) == 3 and len(a[2]) == 3:<br />
tmp_dict = {}<br />
print "%4s %7.4f %7.4f %7.4f %7.4f %7.4f %7.4f " % (a[0],a[1][0],a[1][1],a[1][2],a[2][0],a[2][1],a[2][2])<br />
tmp_dict['symb'] = a[0]<br />
start_array = N.asarray(a[1])<br />
end_array = N.asarray(a[2])<br />
start_vec = start_array - (end_array - start_array)*extension<br />
end_vec = end_array + (end_array - start_array)*extension<br />
tmp_dict['start'] = start_vec<br />
tmp_dict['end'] = end_vec<br />
#rlc# tmp_dict['start'] = a[1]<br />
#rlc# tmp_dict['end'] = a[2]<br />
axes.append(tmp_dict)<br />
else:<br />
print a<br />
else:<br />
return None<br />
<br />
return axes<br />
<br />
if (__name__ == "__main__"):<br />
import sys<br />
if (len(sys.argv) == 1):<br />
for i in range(230):<br />
get_all_axes(i + 1)<br />
else:<br />
for symbol in sys.argv[1:]:<br />
get_all_axes(symbol)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5623
SuperSym
2010-01-11T20:56:46Z
<p>Srballard: /* Installing SuperSym */ updated to reflect v1.2</p>
<hr />
<div>[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
[[File:SuperSymExample2.png|300px|thumb|right|Full cell of symmetry partners with symmetry axes displayed]]<br />
SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for all versions is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/], and the most recent code is available in regular text format from [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
Symmetry axes are not defined for all space groups, and do not display properly for some.<br />
<br />
This plugin requires cctbx and numeric python (numpy).<br />
<br />
Primary coding and development was done by Stuart Ballard. All comments, questions, and issues should be directed to him at srballard@wisc.edu.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym v1.2, download SuperSymPlugin12.py from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/]. In PyMOL, go to:<br />
*Plugin > Manage Plugins > Install...<br />
A file selector dialog will appear. Select SuperSymPlugin12.py. PyMOL will direct you to restart, and upon doing so SuperSym will be accessible through the Plugin menu.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, use the run command in PyMOL on SuperSymPlugin12.py.<br />
<br />
Note: previous errors resulting from incorrect naming of the plugin file have been resolved in v1.2.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
**'''By Partner'''<br />
***Generates only those symmetry partners which the user specifies by their defining symmetry operators<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Cartoon'''<br />
***Convenience function to display symmetry partners as cartoons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSymSource&diff=9001
SuperSymSource
2010-01-11T20:55:28Z
<p>Srballard: /* Source Code */ Updated to v1.2</p>
<hr />
<div>This page contains source files for the [[SuperSym]] plugin. For documentation and use instructions, see [[SuperSym]].<br />
<br />
==Source Code==<br />
<br />
File: SuperSymPlugin12.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import tkFileDialog<br />
import sys<br />
import string, re<br />
from pymol import stored, cmd, selector<br />
import math<br />
from pymol.cgo import *<br />
from pymol.vfont import plain<br />
try:<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
from cctbx import uctbx, sgtbx<br />
except:<br />
quit("Oops! SuperSym requires cctbx and numeric python to function. Please install these.")<br />
<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addcascademenu('Plugin','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Cartoon',<br />
label = 'Cartoon',<br />
command = lambda s = self: graphicsDialog(s, 2))<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 4))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("white", prefix + "0" + str(i) + "*")<br />
cmd.center(prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("white", prefix + str(i) + "*")<br />
cmd.center(prefix + str(i) + "*")<br />
<br />
except:<br />
pass<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)] + " (currently white)",<br />
parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # show cartoon<br />
cmd.show("cartoon", prefix + "*")<br />
if mode == 3: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 4: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell(object, 3.0)<br />
else:<br />
draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_symops(object, 2.0)<br />
else:<br />
draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
opMatrices = []<br />
vars = ["x","y","z"]<br />
i = 0<br />
j = 0<br />
k = 0<br />
#CREATE 4X4 MATRICES FOR SYMMETRY OPERATORS<br />
for raw_op in raw_ops:<br />
ops = raw_op.split(",")<br />
matrix = [[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,1]]<br />
for j in range(len(ops)):<br />
for k in range(len(vars)):<br />
index = ops[j].find(vars[k])<br />
if index != -1:<br />
if index == 0:<br />
matrix[k][j] = 1<br />
elif ops[j][index - 1] == "-":<br />
matrix[k][j] = -1<br />
else:<br />
matrix[k][j] = 1<br />
index = ops[j].find("/")<br />
if index != -1:<br />
matrix[3][j] = float(ops[j][index - 1]) / float(ops[j][index + 1])<br />
opMatrices.append(matrix)<br />
i=i+1<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb, 0.0], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg, 0.0], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2), 0.0],<br />
[0.0,0.0,0.0,1.0]])<br />
fracToOrt = fracToOrt.transpose()<br />
ortToFrac = inv(fracToOrt)<br />
stored.atoms = []<br />
cmd.iterate_state(1,object,"stored.atoms.append([x,y,z,1])")<br />
stored.atoms = N.array(stored.atoms)<br />
fracCoords = N.dot(stored.atoms,ortToFrac)<br />
for i in opList:<br />
try:<br />
op = opMatrices[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
newCoordsFrac = N.dot(fracCoords, op)<br />
stored.newCoords = N.dot(newCoordsFrac, fracToOrt)<br />
stored.j = 0<br />
cmd.alter_state(1,copy,"x,y,z = stored.newCoords[stored.j][0], stored.newCoords[stored.j][1], stored.newCoords[stored.j][2]; stored.j = stored.j + 1")<br />
xSum=ySum=zSum=0.0<br />
for k in range(len(newCoordsFrac)):<br />
xSum = newCoordsFrac[k][0] + xSum<br />
ySum = newCoordsFrac[k][1] + ySum<br />
zSum = newCoordsFrac[k][2] + zSum<br />
center = N.array([xSum,ySum,zSum])<br />
center = center/len(stored.newCoords)<br />
shift = [-math.floor(center[0]) + cell[0], -math.floor(center[1]) + cell[1], -math.floor(center[2]) + cell[2]]<br />
cell_shift(copy,shift[0],shift[1],shift[2],0)<br />
'''<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
#cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
#stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
#atoms = cmd.count_atoms(copy)<br />
#cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
#xMean = (stored.xSum / atoms)<br />
#yMean = (stored.ySum / atoms)<br />
#zMean = (stored.zSum / atoms)<br />
#xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
#dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
#cell_shift(copy,dX,dY,dZ, 0)<br />
'''<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
'''<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
'''<br />
<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
<br />
#CELL DRAWING<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
<br />
#AXES DRAWING<br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
#import string, math<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
<br />
#! /usr/bin/env python<br />
# List all axes in the unit cell.<br />
<br />
# usage:<br />
# python all_axes.py - show axes for the 230 reference settings.<br />
# python all_axes.py P2 - show axes for (e.g.) space group P2<br />
<br />
# RWGK = Ralf W. Grosse-Kunstleve<br />
# RWGK Some further refinement is required:<br />
# RWGK - List only the axes of highest order (e.g. only 4, not 4 and 2).<br />
# RWGK - List only the axes with the smallest intrinsic component<br />
# RWGK (e.g. list only 3(1), not both 3(1) and 3(2)).<br />
# RWGK See also: comment regarding shift_range below.<br />
<br />
def list_plus(lhs, rhs):<br />
return [l + r for l, r in zip(lhs, rhs)]<br />
<br />
def list_minus(lhs, rhs):<br />
return [l - r for l, r in zip(lhs, rhs)]<br />
<br />
def list_multiplies(lhs, rhs):<br />
return [l * r for l, r in zip(lhs, rhs)]<br />
<br />
def list_divides(lhs, rhs):<br />
return [l / r for l, r in zip(lhs, rhs)]<br />
<br />
def list_modulus(lhs, rhs):<br />
return [l % r for l, r in zip(lhs, rhs)]<br />
<br />
def list_dot_product(lhs, rhs=0):<br />
if (rhs == 0): rhs = lhs<br />
result = 0<br />
for l, r in zip(lhs, rhs): result += l * r<br />
return result<br />
<br />
def str_ev(EV):<br />
return "[%d,%d,%d]" % EV<br />
<br />
###def fract_2_dec(fraction):<br />
### list = fraction.split('/')<br />
### if len(list) == 2 and list[1] != 0:<br />
### decimal = string.atof(list[0])/string.atof(list[1])<br />
### else:<br />
### decimal = string.atof(fraction)<br />
### return decimal<br />
<br />
def rlc_RTMxAnalysis(M):<br />
r_info = sgtbx.rot_mx_info(M.r())<br />
t_info = sgtbx.translation_part_info(M)<br />
t_intrinsic = t_info.intrinsic_part().mod_positive().as_double()<br />
t_shift = t_info.origin_shift().mod_positive().as_double()<br />
<br />
#End = list_plus(Start + map(None,r_info.ev()))<br />
####debug<br />
### trans = 0<br />
### length = 0<br />
####debug<br />
<br />
#if (r_info.type() == 1):<br />
if (r_info.type() < 2):<br />
#(rt, start, end) = ('1',(0,0,0),(0,0,0))<br />
return None<br />
#elif (r_info.type() == -1):<br />
# (rt, start, end) = (str(r_info.type()),t_shift,())<br />
elif (abs(r_info.type()) == 2):<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
elif (r_info.type() == 3):<br />
if (r_info.sense() >= 0) :<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),(0,0,0),t_intrinsic))))<br />
# trans = N.sqrt(t_intrinsic[0]**2 + t_intrinsic[1]**2 + t_intrinsic[2]**2)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
# fudge to make sure that PyMOL actually draws the axis (move it slightly off [1,-1,1]) !!!<br />
r[0] = r[0]*1.000001<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
#(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
(start, end) = (t_shift,tuple(list_plus(t_shift,r)))<br />
length = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),start, end))))<br />
<br />
# r_info.sense() for 3^1 and 3^2 seems always to be "1" ???<br />
# if r_info.sense() < 0:<br />
# subscript = str(1-r_info.sense())<br />
# else:<br />
# subscript = str(r_info.sense())<br />
<br />
# use ratio of trans to length to get the correct axis symbol:<br />
# fudged the value to get the right numbers. (using length/2., rather than length/3.)<br />
if trans < length*0.5 :<br />
subscript = '1'<br />
else:<br />
subscript = '2'<br />
<br />
rt = str(r_info.type())+ "^" + subscript <br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
### print "Type, sense, Start, End, length, trans", rt, r_info.sense(), start, end, length, trans<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length)<br />
# print "(rt, start, end)", (rt,start,end)<br />
else:<br />
return None<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
elif (r_info.sense() > 0):<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
subscript = str(int(trans*r_info.type()+.5)) # add 0.5 to fix rounding errors<br />
(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
else:<br />
return None<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length),<br />
# print "(rt, start, end)", (rt,start,end)<br />
return (rt, start, end)<br />
<br />
def get_all_axes(space_group_symbol=None, space_group_info=None, extension=0):<br />
assert space_group_symbol is None or space_group_info is None<br />
shift_range = 1 # RWGK Works for the 230 reference settings; it is not<br />
# RWGK clear to me (rwgk) what value is needed in general.<br />
if (space_group_symbol is not None):<br />
space_group_info = sgtbx.space_group_info(symbol=space_group_symbol)<br />
#space_group_info.show_summary()<br />
<br />
axes_dict = {}<br />
for smx in space_group_info.group():<br />
r = smx.r()<br />
t = smx.t()<br />
shift = [0,0,0]<br />
for shift[0] in range(-shift_range,shift_range+1):<br />
for shift[1] in range(-shift_range,shift_range+1):<br />
for shift[2] in range(-shift_range,shift_range+1):<br />
ts = t.plus(sgtbx.tr_vec(shift, 1)).new_denominator(t.den())<br />
m = sgtbx.rt_mx(r, ts)<br />
#print m<br />
rtmxanal = rlc_RTMxAnalysis(m)<br />
#print r, t, shift, ts, m<br />
if rtmxanal:<br />
#print rtmxanal<br />
axes_dict[rtmxanal] = 0<br />
axes_list = axes_dict.keys()<br />
axes_list.sort()<br />
<br />
# reject nonenantiomorphic space groups<br />
if len(axes_list) > 0 and not re.compile("[A-z]").search(space_group_symbol[1:]):<br />
try:<br />
sgtbx.space_group_info(space_group_symbol).show_summary(), <br />
#print len(axes_list), space_group_symbol<br />
except:<br />
print space_group, space_group_symbol<br />
print<br />
sys.exit(1)<br />
axes = []<br />
for a in axes_list:<br />
if len(a) == 3 and len(a[1]) == 3 and len(a[2]) == 3:<br />
tmp_dict = {}<br />
print "%4s %7.4f %7.4f %7.4f %7.4f %7.4f %7.4f " % (a[0],a[1][0],a[1][1],a[1][2],a[2][0],a[2][1],a[2][2])<br />
tmp_dict['symb'] = a[0]<br />
start_array = N.asarray(a[1])<br />
end_array = N.asarray(a[2])<br />
start_vec = start_array - (end_array - start_array)*extension<br />
end_vec = end_array + (end_array - start_array)*extension<br />
tmp_dict['start'] = start_vec<br />
tmp_dict['end'] = end_vec<br />
#rlc# tmp_dict['start'] = a[1]<br />
#rlc# tmp_dict['end'] = a[2]<br />
axes.append(tmp_dict)<br />
else:<br />
print a<br />
else:<br />
return None<br />
<br />
return axes<br />
<br />
if (__name__ == "__main__"):<br />
import sys<br />
if (len(sys.argv) == 1):<br />
for i in range(230):<br />
get_all_axes(i + 1)<br />
else:<br />
for symbol in sys.argv[1:]:<br />
get_all_axes(symbol)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSymSource&diff=8999
SuperSymSource
2009-11-16T21:50:37Z
<p>Srballard: </p>
<hr />
<div>This page contains source files for the [[SuperSym]] plugin. For documentation and use instructions, see [[SuperSym]].<br />
<br />
==Source Code==<br />
<br />
File: SuperSymPlugin v1.1.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import tkFileDialog<br />
import sys<br />
import string, re<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol.vfont import plain<br />
<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addcascademenu('Plugin','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Cartoon',<br />
label = 'Cartoon',<br />
command = lambda s = self: graphicsDialog(s, 2))<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 4))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("white", prefix + "0" + str(i) + "*")<br />
cmd.center(prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("white", prefix + str(i) + "*")<br />
cmd.center(prefix + str(i) + "*")<br />
<br />
except:<br />
pass<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)] + " (currently white)",<br />
parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # show cartoon<br />
cmd.show("cartoon", prefix + "*")<br />
if mode == 3: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 4: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell(object, 3.0)<br />
else:<br />
draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_symops(object, 2.0)<br />
else:<br />
draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
opMatrices = []<br />
vars = ["x","y","z"]<br />
i = 0<br />
j = 0<br />
k = 0<br />
#CREATE 4X4 MATRICES FOR SYMMETRY OPERATORS<br />
for raw_op in raw_ops:<br />
ops = raw_op.split(",")<br />
matrix = [[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,1]]<br />
for j in range(len(ops)):<br />
for k in range(len(vars)):<br />
index = ops[j].find(vars[k])<br />
if index != -1:<br />
if index == 0:<br />
matrix[k][j] = 1<br />
elif ops[j][index - 1] == "-":<br />
matrix[k][j] = -1<br />
else:<br />
matrix[k][j] = 1<br />
index = ops[j].find("/")<br />
if index != -1:<br />
matrix[3][j] = float(ops[j][index - 1]) / float(ops[j][index + 1])<br />
opMatrices.append(matrix)<br />
i=i+1<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb, 0.0], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg, 0.0], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2), 0.0],<br />
[0.0,0.0,0.0,1.0]])<br />
fracToOrt = fracToOrt.transpose()<br />
ortToFrac = inv(fracToOrt)<br />
stored.atoms = []<br />
cmd.iterate_state(1,object,"stored.atoms.append([x,y,z,1])")<br />
stored.atoms = N.array(stored.atoms)<br />
fracCoords = N.dot(stored.atoms,ortToFrac)<br />
for i in opList:<br />
try:<br />
op = opMatrices[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
newCoordsFrac = N.dot(fracCoords, op)<br />
stored.newCoords = N.dot(newCoordsFrac, fracToOrt)<br />
stored.j = 0<br />
cmd.alter_state(1,copy,"x,y,z = stored.newCoords[stored.j][0], stored.newCoords[stored.j][1], stored.newCoords[stored.j][2]; stored.j = stored.j + 1")<br />
xSum=ySum=zSum=0.0<br />
for k in range(len(newCoordsFrac)):<br />
xSum = newCoordsFrac[k][0] + xSum<br />
ySum = newCoordsFrac[k][1] + ySum<br />
zSum = newCoordsFrac[k][2] + zSum<br />
center = N.array([xSum,ySum,zSum])<br />
center = center/len(stored.newCoords)<br />
shift = [-math.floor(center[0]) + cell[0], -math.floor(center[1]) + cell[1], -math.floor(center[2]) + cell[2]]<br />
cell_shift(copy,shift[0],shift[1],shift[2],0)<br />
'''<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
#cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
#stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
#atoms = cmd.count_atoms(copy)<br />
#cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
#xMean = (stored.xSum / atoms)<br />
#yMean = (stored.ySum / atoms)<br />
#zMean = (stored.zSum / atoms)<br />
#xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
#dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
#cell_shift(copy,dX,dY,dZ, 0)<br />
'''<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
'''<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
'''<br />
<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
<br />
#CELL DRAWING<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
<br />
#AXES DRAWING<br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
#import string, math<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
<br />
#! /usr/bin/env python<br />
# List all axes in the unit cell.<br />
<br />
# usage:<br />
# python all_axes.py - show axes for the 230 reference settings.<br />
# python all_axes.py P2 - show axes for (e.g.) space group P2<br />
<br />
# RWGK = Ralf W. Grosse-Kunstleve<br />
# RWGK Some further refinement is required:<br />
# RWGK - List only the axes of highest order (e.g. only 4, not 4 and 2).<br />
# RWGK - List only the axes with the smallest intrinsic component<br />
# RWGK (e.g. list only 3(1), not both 3(1) and 3(2)).<br />
# RWGK See also: comment regarding shift_range below.<br />
<br />
def list_plus(lhs, rhs):<br />
return [l + r for l, r in zip(lhs, rhs)]<br />
<br />
def list_minus(lhs, rhs):<br />
return [l - r for l, r in zip(lhs, rhs)]<br />
<br />
def list_multiplies(lhs, rhs):<br />
return [l * r for l, r in zip(lhs, rhs)]<br />
<br />
def list_divides(lhs, rhs):<br />
return [l / r for l, r in zip(lhs, rhs)]<br />
<br />
def list_modulus(lhs, rhs):<br />
return [l % r for l, r in zip(lhs, rhs)]<br />
<br />
def list_dot_product(lhs, rhs=0):<br />
if (rhs == 0): rhs = lhs<br />
result = 0<br />
for l, r in zip(lhs, rhs): result += l * r<br />
return result<br />
<br />
def str_ev(EV):<br />
return "[%d,%d,%d]" % EV<br />
<br />
###def fract_2_dec(fraction):<br />
### list = fraction.split('/')<br />
### if len(list) == 2 and list[1] != 0:<br />
### decimal = string.atof(list[0])/string.atof(list[1])<br />
### else:<br />
### decimal = string.atof(fraction)<br />
### return decimal<br />
<br />
def rlc_RTMxAnalysis(M):<br />
r_info = sgtbx.rot_mx_info(M.r())<br />
t_info = sgtbx.translation_part_info(M)<br />
t_intrinsic = t_info.intrinsic_part().mod_positive().as_double()<br />
t_shift = t_info.origin_shift().mod_positive().as_double()<br />
<br />
#End = list_plus(Start + map(None,r_info.ev()))<br />
####debug<br />
### trans = 0<br />
### length = 0<br />
####debug<br />
<br />
#if (r_info.type() == 1):<br />
if (r_info.type() < 2):<br />
#(rt, start, end) = ('1',(0,0,0),(0,0,0))<br />
return None<br />
#elif (r_info.type() == -1):<br />
# (rt, start, end) = (str(r_info.type()),t_shift,())<br />
elif (abs(r_info.type()) == 2):<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
elif (r_info.type() == 3):<br />
if (r_info.sense() >= 0) :<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),(0,0,0),t_intrinsic))))<br />
# trans = N.sqrt(t_intrinsic[0]**2 + t_intrinsic[1]**2 + t_intrinsic[2]**2)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
# fudge to make sure that PyMOL actually draws the axis (move it slightly off [1,-1,1]) !!!<br />
r[0] = r[0]*1.000001<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
#(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
(start, end) = (t_shift,tuple(list_plus(t_shift,r)))<br />
length = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),start, end))))<br />
<br />
# r_info.sense() for 3^1 and 3^2 seems always to be "1" ???<br />
# if r_info.sense() < 0:<br />
# subscript = str(1-r_info.sense())<br />
# else:<br />
# subscript = str(r_info.sense())<br />
<br />
# use ratio of trans to length to get the correct axis symbol:<br />
# fudged the value to get the right numbers. (using length/2., rather than length/3.)<br />
if trans < length*0.5 :<br />
subscript = '1'<br />
else:<br />
subscript = '2'<br />
<br />
rt = str(r_info.type())+ "^" + subscript <br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
### print "Type, sense, Start, End, length, trans", rt, r_info.sense(), start, end, length, trans<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length)<br />
# print "(rt, start, end)", (rt,start,end)<br />
else:<br />
return None<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
elif (r_info.sense() > 0):<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
subscript = str(int(trans*r_info.type()+.5)) # add 0.5 to fix rounding errors<br />
(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
else:<br />
return None<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length),<br />
# print "(rt, start, end)", (rt,start,end)<br />
return (rt, start, end)<br />
<br />
def get_all_axes(space_group_symbol=None, space_group_info=None, extension=0):<br />
assert space_group_symbol is None or space_group_info is None<br />
shift_range = 1 # RWGK Works for the 230 reference settings; it is not<br />
# RWGK clear to me (rwgk) what value is needed in general.<br />
if (space_group_symbol is not None):<br />
space_group_info = sgtbx.space_group_info(symbol=space_group_symbol)<br />
#space_group_info.show_summary()<br />
<br />
axes_dict = {}<br />
for smx in space_group_info.group():<br />
r = smx.r()<br />
t = smx.t()<br />
shift = [0,0,0]<br />
for shift[0] in range(-shift_range,shift_range+1):<br />
for shift[1] in range(-shift_range,shift_range+1):<br />
for shift[2] in range(-shift_range,shift_range+1):<br />
ts = t.plus(sgtbx.tr_vec(shift, 1)).new_denominator(t.den())<br />
m = sgtbx.rt_mx(r, ts)<br />
#print m<br />
rtmxanal = rlc_RTMxAnalysis(m)<br />
#print r, t, shift, ts, m<br />
if rtmxanal:<br />
#print rtmxanal<br />
axes_dict[rtmxanal] = 0<br />
axes_list = axes_dict.keys()<br />
axes_list.sort()<br />
<br />
# reject nonenantiomorphic space groups<br />
if len(axes_list) > 0 and not re.compile("[A-z]").search(space_group_symbol[1:]):<br />
try:<br />
sgtbx.space_group_info(space_group_symbol).show_summary(), <br />
#print len(axes_list), space_group_symbol<br />
except:<br />
print space_group, space_group_symbol<br />
print<br />
sys.exit(1)<br />
axes = []<br />
for a in axes_list:<br />
if len(a) == 3 and len(a[1]) == 3 and len(a[2]) == 3:<br />
tmp_dict = {}<br />
print "%4s %7.4f %7.4f %7.4f %7.4f %7.4f %7.4f " % (a[0],a[1][0],a[1][1],a[1][2],a[2][0],a[2][1],a[2][2])<br />
tmp_dict['symb'] = a[0]<br />
start_array = N.asarray(a[1])<br />
end_array = N.asarray(a[2])<br />
start_vec = start_array - (end_array - start_array)*extension<br />
end_vec = end_array + (end_array - start_array)*extension<br />
tmp_dict['start'] = start_vec<br />
tmp_dict['end'] = end_vec<br />
#rlc# tmp_dict['start'] = a[1]<br />
#rlc# tmp_dict['end'] = a[2]<br />
axes.append(tmp_dict)<br />
else:<br />
print a<br />
else:<br />
return None<br />
<br />
return axes<br />
<br />
if (__name__ == "__main__"):<br />
import sys<br />
if (len(sys.argv) == 1):<br />
for i in range(230):<br />
get_all_axes(i + 1)<br />
else:<br />
for symbol in sys.argv[1:]:<br />
get_all_axes(symbol)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5622
SuperSym
2009-10-20T02:39:16Z
<p>Srballard: </p>
<hr />
<div>[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
[[File:SuperSymExample2.png|300px|thumb|right|Full cell of symmetry partners with symmetry axes displayed]]<br />
SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for all versions is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/], and the most recent code is available in regular text format from [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
Symmetry axes are not defined for all space groups, and do not display properly for some.<br />
<br />
This plugin requires cctbx and numeric python (numpy).<br />
<br />
Primary coding and development was done by Stuart Ballard. All comments, questions, and issues should be directed to him at srballard@wisc.edu.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym v1.1, download SuperSymPlugin v1.1.py from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/]. In PyMOL, go to:<br />
*Plugin > Manage Plugins > Install...<br />
A file selector dialog will appear. Select SuperSymPlugin v1.1.py. PyMOL will direct you to restart, and upon doing so SuperSym will be accessible through the Plugin menu.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, use the run command in PyMOL on SuperSymPlugin v1.1.py.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
**'''By Partner'''<br />
***Generates only those symmetry partners which the user specifies by their defining symmetry operators<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Cartoon'''<br />
***Convenience function to display symmetry partners as cartoons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5621
SuperSym
2009-10-19T22:58:58Z
<p>Srballard: /* The Menu */</p>
<hr />
<div>[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
[[File:SuperSymExample2.png|300px|thumb|right|Full cell of symmetry partners with symmetry axes displayed]]<br />
SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for all versions is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/], and the most recent code is available in regular text format from [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
Symmetry axes are not defined for all space groups, and do not display properly for some.<br />
<br />
This plugin requires cctbx and numeric python (numpy).<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym v1.1, download SuperSymPlugin v1.1.py from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/]. In PyMOL, go to:<br />
*Plugin > Manage Plugins > Install...<br />
A file selector dialog will appear. Select SuperSymPlugin v1.1.py. PyMOL will direct you to restart, and upon doing so SuperSym will be accessible through the Plugin menu.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, use the run command in PyMOL on SuperSymPlugin v1.1.py.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
**'''By Partner'''<br />
***Generates only those symmetry partners which the user specifies by their defining symmetry operators<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Cartoon'''<br />
***Convenience function to display symmetry partners as cartoons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSymSource&diff=8998
SuperSymSource
2009-10-19T22:11:02Z
<p>Srballard: /* Source Files */ Updated code to v1.1</p>
<hr />
<div>This page contains source files for the [[SuperSym]] plugin. For documentation and use instructions, see [[SuperSym]].<br />
<br />
==Source Code==<br />
<br />
File: SuperSymPlugin v1.1.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import tkFileDialog<br />
import sys<br />
import string, re<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol.vfont import plain<br />
<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addcascademenu('Plugin','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Cartoon',<br />
label = 'Cartoon',<br />
command = lambda s = self: graphicsDialog(s, 2))<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 4))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("white", prefix + "0" + str(i) + "*")<br />
cmd.center(prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("white", prefix + str(i) + "*")<br />
cmd.center(prefix + str(i) + "*")<br />
<br />
except:<br />
pass<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)] + " (currently white)",<br />
parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # show cartoon<br />
cmd.show("cartoon", prefix + "*")<br />
if mode == 3: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 4: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell(object, 3.0)<br />
else:<br />
draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_symops(object, 2.0)<br />
else:<br />
draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
opMatrices = []<br />
vars = ["x","y","z"]<br />
i = 0<br />
j = 0<br />
k = 0<br />
#CREATE 4X4 MATRICES FOR SYMMETRY OPERATORS<br />
for raw_op in raw_ops:<br />
ops = raw_op.split(",")<br />
matrix = [[0,0,0,0],[0,0,0,0],[0,0,0,0],[0,0,0,1]]<br />
for j in range(len(ops)):<br />
for k in range(len(vars)):<br />
index = ops[j].find(vars[k])<br />
if index != -1:<br />
if index == 0:<br />
matrix[k][j] = 1<br />
elif ops[j][index - 1] == "-":<br />
matrix[k][j] = -1<br />
else:<br />
matrix[k][j] = 1<br />
index = ops[j].find("/")<br />
if index != -1:<br />
matrix[3][j] = float(ops[j][index - 1]) / float(ops[j][index + 1])<br />
opMatrices.append(matrix)<br />
i=i+1<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb, 0.0], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg, 0.0], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2), 0.0],<br />
[0.0,0.0,0.0,1.0]])<br />
fracToOrt = fracToOrt.transpose()<br />
ortToFrac = inv(fracToOrt)<br />
stored.atoms = []<br />
cmd.iterate_state(1,object,"stored.atoms.append([x,y,z,1])")<br />
stored.atoms = N.array(stored.atoms)<br />
fracCoords = N.dot(stored.atoms,ortToFrac)<br />
for i in opList:<br />
try:<br />
op = opMatrices[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
newCoordsFrac = N.dot(fracCoords, op)<br />
stored.newCoords = N.dot(newCoordsFrac, fracToOrt)<br />
stored.j = 0<br />
cmd.alter_state(1,copy,"x,y,z = stored.newCoords[stored.j][0], stored.newCoords[stored.j][1], stored.newCoords[stored.j][2]; stored.j = stored.j + 1")<br />
xSum=ySum=zSum=0.0<br />
for k in range(len(newCoordsFrac)):<br />
xSum = newCoordsFrac[k][0] + xSum<br />
ySum = newCoordsFrac[k][1] + ySum<br />
zSum = newCoordsFrac[k][2] + zSum<br />
center = N.array([xSum,ySum,zSum])<br />
center = center/len(stored.newCoords)<br />
shift = [-math.floor(center[0]) + cell[0], -math.floor(center[1]) + cell[1], -math.floor(center[2]) + cell[2]]<br />
cell_shift(copy,shift[0],shift[1],shift[2],0)<br />
'''<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
#cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
#stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
#atoms = cmd.count_atoms(copy)<br />
#cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
#xMean = (stored.xSum / atoms)<br />
#yMean = (stored.ySum / atoms)<br />
#zMean = (stored.zSum / atoms)<br />
#xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
#dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
#cell_shift(copy,dX,dY,dZ, 0)<br />
'''<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
'''<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
'''<br />
<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
<br />
#CELL DRAWING<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
<br />
#AXES DRAWING<br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
#import string, math<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
<br />
#! /usr/bin/env python<br />
# List all axes in the unit cell.<br />
<br />
# usage:<br />
# python all_axes.py - show axes for the 230 reference settings.<br />
# python all_axes.py P2 - show axes for (e.g.) space group P2<br />
<br />
# RWGK = Ralf W. Grosse-Kunstleve<br />
# RWGK Some further refinement is required:<br />
# RWGK - List only the axes of highest order (e.g. only 4, not 4 and 2).<br />
# RWGK - List only the axes with the smallest intrinsic component<br />
# RWGK (e.g. list only 3(1), not both 3(1) and 3(2)).<br />
# RWGK See also: comment regarding shift_range below.<br />
<br />
def list_plus(lhs, rhs):<br />
return [l + r for l, r in zip(lhs, rhs)]<br />
<br />
def list_minus(lhs, rhs):<br />
return [l - r for l, r in zip(lhs, rhs)]<br />
<br />
def list_multiplies(lhs, rhs):<br />
return [l * r for l, r in zip(lhs, rhs)]<br />
<br />
def list_divides(lhs, rhs):<br />
return [l / r for l, r in zip(lhs, rhs)]<br />
<br />
def list_modulus(lhs, rhs):<br />
return [l % r for l, r in zip(lhs, rhs)]<br />
<br />
def list_dot_product(lhs, rhs=0):<br />
if (rhs == 0): rhs = lhs<br />
result = 0<br />
for l, r in zip(lhs, rhs): result += l * r<br />
return result<br />
<br />
def str_ev(EV):<br />
return "[%d,%d,%d]" % EV<br />
<br />
###def fract_2_dec(fraction):<br />
### list = fraction.split('/')<br />
### if len(list) == 2 and list[1] != 0:<br />
### decimal = string.atof(list[0])/string.atof(list[1])<br />
### else:<br />
### decimal = string.atof(fraction)<br />
### return decimal<br />
<br />
def rlc_RTMxAnalysis(M):<br />
r_info = sgtbx.rot_mx_info(M.r())<br />
t_info = sgtbx.translation_part_info(M)<br />
t_intrinsic = t_info.intrinsic_part().mod_positive().as_double()<br />
t_shift = t_info.origin_shift().mod_positive().as_double()<br />
<br />
#End = list_plus(Start + map(None,r_info.ev()))<br />
####debug<br />
### trans = 0<br />
### length = 0<br />
####debug<br />
<br />
#if (r_info.type() == 1):<br />
if (r_info.type() < 2):<br />
#(rt, start, end) = ('1',(0,0,0),(0,0,0))<br />
return None<br />
#elif (r_info.type() == -1):<br />
# (rt, start, end) = (str(r_info.type()),t_shift,())<br />
elif (abs(r_info.type()) == 2):<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
elif (r_info.type() == 3):<br />
if (r_info.sense() >= 0) :<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),(0,0,0),t_intrinsic))))<br />
# trans = N.sqrt(t_intrinsic[0]**2 + t_intrinsic[1]**2 + t_intrinsic[2]**2)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
# fudge to make sure that PyMOL actually draws the axis (move it slightly off [1,-1,1]) !!!<br />
r[0] = r[0]*1.000001<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
#(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
(start, end) = (t_shift,tuple(list_plus(t_shift,r)))<br />
length = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),start, end))))<br />
<br />
# r_info.sense() for 3^1 and 3^2 seems always to be "1" ???<br />
# if r_info.sense() < 0:<br />
# subscript = str(1-r_info.sense())<br />
# else:<br />
# subscript = str(r_info.sense())<br />
<br />
# use ratio of trans to length to get the correct axis symbol:<br />
# fudged the value to get the right numbers. (using length/2., rather than length/3.)<br />
if trans < length*0.5 :<br />
subscript = '1'<br />
else:<br />
subscript = '2'<br />
<br />
rt = str(r_info.type())+ "^" + subscript <br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
### print "Type, sense, Start, End, length, trans", rt, r_info.sense(), start, end, length, trans<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length)<br />
# print "(rt, start, end)", (rt,start,end)<br />
else:<br />
return None<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
elif (r_info.sense() > 0):<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
subscript = str(int(trans*r_info.type()+.5)) # add 0.5 to fix rounding errors<br />
(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
else:<br />
return None<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length),<br />
# print "(rt, start, end)", (rt,start,end)<br />
return (rt, start, end)<br />
<br />
def get_all_axes(space_group_symbol=None, space_group_info=None, extension=0):<br />
assert space_group_symbol is None or space_group_info is None<br />
shift_range = 1 # RWGK Works for the 230 reference settings; it is not<br />
# RWGK clear to me (rwgk) what value is needed in general.<br />
if (space_group_symbol is not None):<br />
space_group_info = sgtbx.space_group_info(symbol=space_group_symbol)<br />
#space_group_info.show_summary()<br />
<br />
axes_dict = {}<br />
for smx in space_group_info.group():<br />
r = smx.r()<br />
t = smx.t()<br />
shift = [0,0,0]<br />
for shift[0] in range(-shift_range,shift_range+1):<br />
for shift[1] in range(-shift_range,shift_range+1):<br />
for shift[2] in range(-shift_range,shift_range+1):<br />
ts = t.plus(sgtbx.tr_vec(shift, 1)).new_denominator(t.den())<br />
m = sgtbx.rt_mx(r, ts)<br />
#print m<br />
rtmxanal = rlc_RTMxAnalysis(m)<br />
#print r, t, shift, ts, m<br />
if rtmxanal:<br />
#print rtmxanal<br />
axes_dict[rtmxanal] = 0<br />
axes_list = axes_dict.keys()<br />
axes_list.sort()<br />
<br />
# reject nonenantiomorphic space groups<br />
if len(axes_list) > 0 and not re.compile("[A-z]").search(space_group_symbol[1:]):<br />
try:<br />
sgtbx.space_group_info(space_group_symbol).show_summary(), <br />
#print len(axes_list), space_group_symbol<br />
except:<br />
print space_group, space_group_symbol<br />
print<br />
sys.exit(1)<br />
axes = []<br />
for a in axes_list:<br />
if len(a) == 3 and len(a[1]) == 3 and len(a[2]) == 3:<br />
tmp_dict = {}<br />
print "%4s %7.4f %7.4f %7.4f %7.4f %7.4f %7.4f " % (a[0],a[1][0],a[1][1],a[1][2],a[2][0],a[2][1],a[2][2])<br />
tmp_dict['symb'] = a[0]<br />
start_array = N.asarray(a[1])<br />
end_array = N.asarray(a[2])<br />
start_vec = start_array - (end_array - start_array)*extension<br />
end_vec = end_array + (end_array - start_array)*extension<br />
tmp_dict['start'] = start_vec<br />
tmp_dict['end'] = end_vec<br />
#rlc# tmp_dict['start'] = a[1]<br />
#rlc# tmp_dict['end'] = a[2]<br />
axes.append(tmp_dict)<br />
else:<br />
print a<br />
else:<br />
return None<br />
<br />
return axes<br />
<br />
if (__name__ == "__main__"):<br />
import sys<br />
if (len(sys.argv) == 1):<br />
for i in range(230):<br />
get_all_axes(i + 1)<br />
else:<br />
for symbol in sys.argv[1:]:<br />
get_all_axes(symbol)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5620
SuperSym
2009-10-19T22:09:44Z
<p>Srballard: /* Dependencies, Bugs, and Acknowledgments */</p>
<hr />
<div>[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
[[File:SuperSymExample2.png|300px|thumb|right|Full cell of symmetry partners with symmetry axes displayed]]<br />
SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for all versions is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/], and the most recent code is available in regular text format from [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
Symmetry axes are not defined for all space groups, and do not display properly for some.<br />
<br />
This plugin requires cctbx and numeric python (numpy).<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym v1.1, download SuperSymPlugin v1.1.py from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/]. In PyMOL, go to:<br />
*Plugin > Manage Plugins > Install...<br />
A file selector dialog will appear. Select SuperSymPlugin v1.1.py. PyMOL will direct you to restart, and upon doing so SuperSym will be accessible through the Plugin menu.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, use the run command in PyMOL on SuperSymPlugin v1.1.py.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5619
SuperSym
2009-10-19T22:08:12Z
<p>Srballard: </p>
<hr />
<div>[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
[[File:SuperSymExample2.png|300px|thumb|right|Full cell of symmetry partners with symmetry axes displayed]]<br />
SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for all versions is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/], and the most recent code is available in regular text format from [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python (numpy).<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym v1.1, download SuperSymPlugin v1.1.py from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/]. In PyMOL, go to:<br />
*Plugin > Manage Plugins > Install...<br />
A file selector dialog will appear. Select SuperSymPlugin v1.1.py. PyMOL will direct you to restart, and upon doing so SuperSym will be accessible through the Plugin menu.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, use the run command in PyMOL on SuperSymPlugin v1.1.py.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5618
SuperSym
2009-09-26T20:33:22Z
<p>Srballard: /* Dependencies, Bugs, and Acknowledgments */</p>
<hr />
<div>[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
[[File:SuperSymExample2.png|300px|thumb|right|Full cell of symmetry partners with symmetry axes displayed]]<br />
SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python (numpy).<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5617
SuperSym
2009-09-26T19:24:55Z
<p>Srballard: </p>
<hr />
<div>[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
[[File:SuperSymExample2.png|300px|thumb|right|Full cell of symmetry partners with symmetry axes displayed]]<br />
SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5616
SuperSym
2009-09-26T19:24:19Z
<p>Srballard: </p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
[[File:SuperSymExample2.png|300px|thumb|right|Full cell of symmetry partners with symmetry axes displayed]]<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=File:SuperSymExample2.png&diff=2604
File:SuperSymExample2.png
2009-09-26T19:22:48Z
<p>Srballard: </p>
<hr />
<div></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5615
SuperSym
2009-09-26T19:20:22Z
<p>Srballard: </p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
[[File:SuperSymExample.png|300px|thumb|right|Symmetry partners for 1hpv showing 6-1 screw axis]]<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=File:SuperSymExample.png&diff=2851
File:SuperSymExample.png
2009-09-26T19:17:26Z
<p>Srballard: </p>
<hr />
<div></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5614
SuperSym
2009-09-17T19:25:18Z
<p>Srballard: /* Using SuperSym */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==The Menu==<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5613
SuperSym
2009-09-11T23:41:06Z
<p>Srballard: /* Using SuperSym */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==Using SuperSym==<br />
<br />
The SuperSym dropdown menu options:<br />
*'''Default Symmetry Partner Set'''<br />
** See '''Build Symmetry Partners > Cell [0,0,0] (default)'''<br />
*'''Draw Unit Cell'''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*'''Build Symmetry Partners >'''<br />
**All options in this submenu generate sets of symmetry partners<br />
**'''Cell [0,0,0] (default)'''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**'''Cell [x,y,z] (custom)'''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**'''2x2x2 Block'''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**'''3x3x3 Block'''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
*'''Coloring >'''<br />
**'''Default Rainbow'''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**'''Select color for each operation'''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**'''Select one color for custom set of operations'''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*'''Graphics >'''<br />
**'''Lines'''<br />
***Convenience function to display symmetry partners as lines<br />
**'''Ribbon'''<br />
**Convenience function to display symmetry partners as ribbons<br />
**'''Sphere Surface (best for printing)'''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**'''Surface (high load render)'''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*'''Symmetry Axes >'''<br />
**'''Build Axes'''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*'''Move symmetry partners'''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*'''About'''<br />
**Developer info<br />
*'''Help'''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5612
SuperSym
2009-09-11T23:39:44Z
<p>Srballard: /* Using SuperSym */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==Using SuperSym==<br />
<br />
The SuperSym dropdown menu options:<br />
*''Default Symmetry Partner Set''<br />
** See ''Build Symmetry Partners > Cell [0,0,0] (default)''<br />
*''Draw Unit Cell''<br />
**Creates a cgo object with unit cell axes as cylinders. This functions similarly to ''show cell'', but the cell axes are cylinders instead of lines, allowing for printing.<br />
*''Build Symmetry Partners >''<br />
**All options in this submenu generate sets of symmetry partners<br />
**''Cell [0,0,0] (default)''<br />
***Generates a suite of symmetry partners for a given object for the default unit cell, which is lattice position [0,0,0]<br />
**''Cell [x,y,z] (custom)''<br />
***Generates a suite of symmetry partners for a given object for a lattice position which you specify<br />
**''2x2x2 Block''<br />
***Generates 8 sets of symmetry partners for a given object, filling lattice positions [0,0,0] through [1,1,1]<br />
**''3x3x3 Block''<br />
***Generates 27 sets of symmetry partners for a given object, filling lattice positions [-1,-1,-1] through [1,1,1]. This option may take a long time to execute<br />
*''Coloring >''<br />
**''Default Rainbow''<br />
***Colors all symmetry objects with a specified by their symmetry operations automatically<br />
**''Select color for each operation''<br />
***Select symmetry partners to color by their defining symmetry operation and select the color for each<br />
**''Select one color for custom set of operations''<br />
***Select a set of symmetry partners defined by symmetry operations and select one color for all of them<br />
*''Graphics >''<br />
**''Lines''<br />
***Convenience function to display symmetry partners as lines<br />
**''Ribbon''<br />
**Convenience function to display symmetry partners as ribbons<br />
**''Sphere Surface (best for printing)''<br />
***Uses the findSurfaceResidues function and shows surface residues as spheres. If printing, this option saves at least 60% of materials relative to regular surfaces, with minimal loss in resolution<br />
**''Surface (high load render)''<br />
***Displays symmetry partners as surfaces. This option may take a very long time to execute<br />
*''Symmetry Axes >''<br />
**''Build Axes''<br />
***Builds all symmetry axes for the given object. This functionality will be customizable and extended in future versions<br />
*''Move symmetry partners''<br />
**Merely displays instructions for using built in hotkeys to move symmetry partners<br />
*''About''<br />
**Developer info<br />
*''Help''<br />
**Reference to this page<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5611
SuperSym
2009-09-11T23:22:36Z
<p>Srballard: </p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==Using SuperSym==<br />
<br />
The SuperSym dropdown menu options:<br />
*''Default Symmetry Partner Set'': ''See Build Symmetry Partners > Cell [0,0,0] (default)''<br />
*''Draw Unit Cell''<br />
*''Build Symmetry Partners >''<br />
**''Cell [0,0,0] (default)''<br />
**''Cell [x,y,z] (custom)''<br />
**''2x2x2 Block''<br />
**''3x3x3 Block''<br />
*''Coloring >''<br />
**''Default Rainbow''<br />
**''Select color for each operation''<br />
**''Select one color for custom set of operations''<br />
*''Graphics >''<br />
**''Lines''<br />
**''Ribbon''<br />
**''Sphere Surface (best for printing)''<br />
**''Surface (high load render)''<br />
*''Symmetry Axes >''<br />
**''Build Axes''<br />
*''Move symmetry partners''<br />
*''About''<br />
*''Help''<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5610
SuperSym
2009-09-11T23:15:40Z
<p>Srballard: /* Using SuperSym */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==Using SuperSym==<br />
<br />
The SuperSym dropdown menu on the PyMOL GUI provides the following options:<br />
*Default Symmetry Partner Set<br />
*Draw Unit Cell<br />
*Build Symmetry Partners ><br />
**Cell [0,0,0] (default)<br />
**Cell [x,y,z] (custom)<br />
**2x2x2 Block<br />
**3x3x3 Block<br />
*Coloring ><br />
**Default Rainbow<br />
**Select color for each operation<br />
**Select one color for custom set of operations<br />
*Graphics ><br />
**Lines<br />
**Ribbon<br />
**Sphere Surface (best for printing)<br />
**Surface (high load render)<br />
*Symmetry Axes ><br />
**Build Axes<br />
*Move symmetry partners<br />
*About<br />
*Help<br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5609
SuperSym
2009-09-11T22:51:43Z
<p>Srballard: /* Dependencies and Acknowledgments */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
==Dependencies, Bugs, and Acknowledgments==<br />
<br />
This plugin has only been tested for PyMOL version 1.2b6pre and 1.2r1.<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly, even if the pse file displays normally in other versions. Use at your own risk.<br />
<br />
SuperSym has failed to load properly in OSX 10.6 (Snow Leopard), but functions normally in OSX 10.5. Bug fixing is underway.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==Using SuperSym==<br />
<br />
The SuperSym dropdown menu on the PyMOL GUI provides the following options:<br />
*Default Symmetry Partner Set<br />
*Draw Unit Cell<br />
*Build Symmetry Partners ><br />
**Cell [0,0,0] (default)<br />
**Cell [x,y,z] (custom)<br />
**2x2x2 Block<br />
**3x3x3 Block<br />
*Coloring ><br />
**Default Rainbow<br />
**Select color for each operation<br />
**Select one color for custom set of operations<br />
*Graphics ><br />
**Lines<br />
**Ribbon<br />
**Sphere Surface (best for printing)<br />
**Surface (high load render)<br />
*Symmetry Axes ><br />
**Build Axes<br />
*Move symmetry partners<br />
*About<br />
*Help<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5608
SuperSym
2009-09-11T22:45:36Z
<p>Srballard: </p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] or [[SuperSymSource]].<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==Using SuperSym==<br />
<br />
The SuperSym dropdown menu on the PyMOL GUI provides the following options:<br />
*Default Symmetry Partner Set<br />
*Draw Unit Cell<br />
*Build Symmetry Partners ><br />
**Cell [0,0,0] (default)<br />
**Cell [x,y,z] (custom)<br />
**2x2x2 Block<br />
**3x3x3 Block<br />
*Coloring ><br />
**Default Rainbow<br />
**Select color for each operation<br />
**Select one color for custom set of operations<br />
*Graphics ><br />
**Lines<br />
**Ribbon<br />
**Sphere Surface (best for printing)<br />
**Surface (high load render)<br />
*Symmetry Axes ><br />
**Build Axes<br />
*Move symmetry partners<br />
*About<br />
*Help<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5607
SuperSym
2009-09-11T22:44:31Z
<p>Srballard: </p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] and displayed below.<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==Using SuperSym==<br />
<br />
The SuperSym dropdown menu on the PyMOL GUI provides the following options:<br />
*Default Symmetry Partner Set<br />
*Draw Unit Cell<br />
*Build Symmetry Partners ><br />
**Cell [0,0,0] (default)<br />
**Cell [x,y,z] (custom)<br />
**2x2x2 Block<br />
**3x3x3 Block<br />
*Coloring ><br />
**Default Rainbow<br />
**Select color for each operation<br />
**Select one color for custom set of operations<br />
*Graphics ><br />
**Lines<br />
**Ribbon<br />
**Sphere Surface (best for printing)<br />
**Surface (high load render)<br />
*Symmetry Axes ><br />
**Build Axes<br />
*Move symmetry partners<br />
*About<br />
*Help<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSymSource&diff=8997
SuperSymSource
2009-09-11T22:44:17Z
<p>Srballard: Created page with 'This page contains source files for the SuperSym plugin. For documentation and use instructions, see SuperSym. ==Source Files== File: SuperSym.py <source lang="python">…'</p>
<hr />
<div>This page contains source files for the [[SuperSym]] plugin. For documentation and use instructions, see [[SuperSym]].<br />
<br />
==Source Files==<br />
<br />
File: SuperSym.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import sys<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
import draw_cell as draw_cell<br />
import draw_symops_cctbx as sym_axes<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)], parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 3: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell.draw_cell(object, 3.0)<br />
else:<br />
draw_cell.draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
sym_axes.draw_symops(object, 2.0)<br />
else:<br />
sym_axes.draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
for i in opList:<br />
try:<br />
stored.tmpOp = raw_ops[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
atoms = cmd.count_atoms(copy)<br />
cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
xMean = (stored.xSum / atoms)<br />
yMean = (stored.ySum / atoms)<br />
zMean = (stored.zSum / atoms)<br />
xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
cell_shift(copy,dX,dY,dZ, 0)<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def shift_and_copy(object, dX, dY, dZ):<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
copy = oldPre + newX + newY + newZ<br />
if cmd.count_atoms(copy) != 0:<br />
print "Symmetry partner already exists in destination position!"<br />
quit()<br />
cmd.copy(newName, object)<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, newName, "x,y,z = cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
# this function is borrowed from findSurfaceResidues script on PyMOL wiki<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
</source><br />
File: SuperSymMenu.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkFileDialog<br />
from pymol import cmd, selector<br />
from SuperSym import *<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addmenu('SuperSym','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
</source><br />
File: draw_cell.py<br />
<source lang="python"><br />
#original code written by Robert Campbell<br />
#modified by Stuart Ballard<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
from pymol.vfont import plain<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
cmd.extend("draw_cell",draw_cell)<br />
</source><br />
File: draw_symops_cctbx.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
from cctbx import uctbx, sgtbx<br />
#import string, math<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
<br />
from all_axes_new import get_all_axes<br />
<br />
import numpy as N<br />
#import numarray as N<br />
<br />
print "Finished importing for draw_symops_cctbx.py"<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
cmd.extend("draw_symops",draw_symops)<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
</source><br />
File: all_axes_new.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# List all axes in the unit cell.<br />
<br />
# usage:<br />
# python all_axes.py - show axes for the 230 reference settings.<br />
# python all_axes.py P2 - show axes for (e.g.) space group P2<br />
<br />
# RWGK = Ralf W. Grosse-Kunstleve<br />
# RWGK Some further refinement is required:<br />
# RWGK - List only the axes of highest order (e.g. only 4, not 4 and 2).<br />
# RWGK - List only the axes with the smallest intrinsic component<br />
# RWGK (e.g. list only 3(1), not both 3(1) and 3(2)).<br />
# RWGK See also: comment regarding shift_range below.<br />
<br />
from cctbx import sgtbx<br />
#from cctbx.misc.python_utils import list_plus<br />
<br />
import numpy as N<br />
import string, re<br />
<br />
def list_plus(lhs, rhs):<br />
return [l + r for l, r in zip(lhs, rhs)]<br />
<br />
def list_minus(lhs, rhs):<br />
return [l - r for l, r in zip(lhs, rhs)]<br />
<br />
def list_multiplies(lhs, rhs):<br />
return [l * r for l, r in zip(lhs, rhs)]<br />
<br />
def list_divides(lhs, rhs):<br />
return [l / r for l, r in zip(lhs, rhs)]<br />
<br />
def list_modulus(lhs, rhs):<br />
return [l % r for l, r in zip(lhs, rhs)]<br />
<br />
def list_dot_product(lhs, rhs=0):<br />
if (rhs == 0): rhs = lhs<br />
result = 0<br />
for l, r in zip(lhs, rhs): result += l * r<br />
return result<br />
<br />
def str_ev(EV):<br />
return "[%d,%d,%d]" % EV<br />
<br />
###def fract_2_dec(fraction):<br />
### list = fraction.split('/')<br />
### if len(list) == 2 and list[1] != 0:<br />
### decimal = string.atof(list[0])/string.atof(list[1])<br />
### else:<br />
### decimal = string.atof(fraction)<br />
### return decimal<br />
<br />
def rlc_RTMxAnalysis(M):<br />
r_info = sgtbx.rot_mx_info(M.r())<br />
t_info = sgtbx.translation_part_info(M)<br />
t_intrinsic = t_info.intrinsic_part().mod_positive().as_double()<br />
t_shift = t_info.origin_shift().mod_positive().as_double()<br />
<br />
#End = list_plus(Start + map(None,r_info.ev()))<br />
####debug<br />
### trans = 0<br />
### length = 0<br />
####debug<br />
<br />
#if (r_info.type() == 1):<br />
if (r_info.type() < 2):<br />
#(rt, start, end) = ('1',(0,0,0),(0,0,0))<br />
return None<br />
#elif (r_info.type() == -1):<br />
# (rt, start, end) = (str(r_info.type()),t_shift,())<br />
elif (abs(r_info.type()) == 2):<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
elif (r_info.type() == 3):<br />
if (r_info.sense() >= 0) :<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),(0,0,0),t_intrinsic))))<br />
# trans = N.sqrt(t_intrinsic[0]**2 + t_intrinsic[1]**2 + t_intrinsic[2]**2)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
# fudge to make sure that PyMOL actually draws the axis (move it slightly off [1,-1,1]) !!!<br />
r[0] = r[0]*1.000001<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
#(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
(start, end) = (t_shift,tuple(list_plus(t_shift,r)))<br />
length = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),start, end))))<br />
<br />
# r_info.sense() for 3^1 and 3^2 seems always to be "1" ???<br />
# if r_info.sense() < 0:<br />
# subscript = str(1-r_info.sense())<br />
# else:<br />
# subscript = str(r_info.sense())<br />
<br />
# use ratio of trans to length to get the correct axis symbol:<br />
# fudged the value to get the right numbers. (using length/2., rather than length/3.)<br />
if trans < length*0.5 :<br />
subscript = '1'<br />
else:<br />
subscript = '2'<br />
<br />
rt = str(r_info.type())+ "^" + subscript <br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
### print "Type, sense, Start, End, length, trans", rt, r_info.sense(), start, end, length, trans<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length)<br />
# print "(rt, start, end)", (rt,start,end)<br />
else:<br />
return None<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
elif (r_info.sense() > 0):<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
subscript = str(int(trans*r_info.type()+.5)) # add 0.5 to fix rounding errors<br />
(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
else:<br />
return None<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length),<br />
# print "(rt, start, end)", (rt,start,end)<br />
return (rt, start, end)<br />
<br />
def get_all_axes(space_group_symbol=None, space_group_info=None, extension=0):<br />
assert space_group_symbol is None or space_group_info is None<br />
shift_range = 1 # RWGK Works for the 230 reference settings; it is not<br />
# RWGK clear to me (rwgk) what value is needed in general.<br />
if (space_group_symbol is not None):<br />
space_group_info = sgtbx.space_group_info(symbol=space_group_symbol)<br />
#space_group_info.show_summary()<br />
<br />
axes_dict = {}<br />
for smx in space_group_info.group():<br />
r = smx.r()<br />
t = smx.t()<br />
shift = [0,0,0]<br />
for shift[0] in range(-shift_range,shift_range+1):<br />
for shift[1] in range(-shift_range,shift_range+1):<br />
for shift[2] in range(-shift_range,shift_range+1):<br />
ts = t.plus(sgtbx.tr_vec(shift, 1)).new_denominator(t.den())<br />
m = sgtbx.rt_mx(r, ts)<br />
#print m<br />
rtmxanal = rlc_RTMxAnalysis(m)<br />
#print r, t, shift, ts, m<br />
if rtmxanal:<br />
#print rtmxanal<br />
axes_dict[rtmxanal] = 0<br />
axes_list = axes_dict.keys()<br />
axes_list.sort()<br />
<br />
# reject nonenantiomorphic space groups<br />
if len(axes_list) > 0 and not re.compile("[A-z]").search(space_group_symbol[1:]):<br />
try:<br />
sgtbx.space_group_info(space_group_symbol).show_summary(), <br />
#print len(axes_list), space_group_symbol<br />
except:<br />
print space_group, space_group_symbol<br />
print<br />
sys.exit(1)<br />
axes = []<br />
for a in axes_list:<br />
if len(a) == 3 and len(a[1]) == 3 and len(a[2]) == 3:<br />
tmp_dict = {}<br />
print "%4s %7.4f %7.4f %7.4f %7.4f %7.4f %7.4f " % (a[0],a[1][0],a[1][1],a[1][2],a[2][0],a[2][1],a[2][2])<br />
tmp_dict['symb'] = a[0]<br />
start_array = N.asarray(a[1])<br />
end_array = N.asarray(a[2])<br />
start_vec = start_array - (end_array - start_array)*extension<br />
end_vec = end_array + (end_array - start_array)*extension<br />
tmp_dict['start'] = start_vec<br />
tmp_dict['end'] = end_vec<br />
#rlc# tmp_dict['start'] = a[1]<br />
#rlc# tmp_dict['end'] = a[2]<br />
axes.append(tmp_dict)<br />
else:<br />
print a<br />
else:<br />
return None<br />
<br />
return axes<br />
<br />
if (__name__ == "__main__"):<br />
import sys<br />
if (len(sys.argv) == 1):<br />
for i in range(230):<br />
get_all_axes(i + 1)<br />
else:<br />
for symbol in sys.argv[1:]:<br />
get_all_axes(symbol)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5606
SuperSym
2009-09-11T22:38:23Z
<p>Srballard: /* Using SuperSym */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] and displayed below.<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Installing SuperSym==<br />
<br />
To install SuperSym, first copy the text of source files to corresponding .py files or download them from SourceForge. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules. This will make all of SuperSym's functions available through a drop-down menu in the PyMOL GUI<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu, ignore SuperSymMenu.py and use the run command on the other files in PyMOL as you would for any other script.<br />
<br />
==Using SuperSym==<br />
<br />
The SuperSym dropdown menu on the PyMOL GUI provides the following options:<br />
*Default Symmetry Partner Set<br />
*Draw Unit Cell<br />
*Build Symmetry Partners ><br />
**Cell [0,0,0] (default)<br />
**Cell [x,y,z] (custom)<br />
**2x2x2 Block<br />
**3x3x3 Block<br />
*Coloring ><br />
**Default Rainbow<br />
**Select color for each operation<br />
**Select one color for custom set of operations<br />
*Graphics ><br />
**Lines<br />
**Ribbon<br />
**Sphere Surface (best for printing)<br />
**Surface (high load render)<br />
*Symmetry Axes ><br />
**Build Axes<br />
*Move symmetry partners<br />
*About<br />
*Help<br />
<br />
==Source Files==<br />
<br />
File: SuperSym.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import sys<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
import draw_cell as draw_cell<br />
import draw_symops_cctbx as sym_axes<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)], parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 3: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell.draw_cell(object, 3.0)<br />
else:<br />
draw_cell.draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
sym_axes.draw_symops(object, 2.0)<br />
else:<br />
sym_axes.draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
for i in opList:<br />
try:<br />
stored.tmpOp = raw_ops[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
atoms = cmd.count_atoms(copy)<br />
cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
xMean = (stored.xSum / atoms)<br />
yMean = (stored.ySum / atoms)<br />
zMean = (stored.zSum / atoms)<br />
xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
cell_shift(copy,dX,dY,dZ, 0)<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def shift_and_copy(object, dX, dY, dZ):<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
copy = oldPre + newX + newY + newZ<br />
if cmd.count_atoms(copy) != 0:<br />
print "Symmetry partner already exists in destination position!"<br />
quit()<br />
cmd.copy(newName, object)<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, newName, "x,y,z = cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
# this function is borrowed from findSurfaceResidues script on PyMOL wiki<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
</source><br />
File: SuperSymMenu.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkFileDialog<br />
from pymol import cmd, selector<br />
from SuperSym import *<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addmenu('SuperSym','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
</source><br />
File: draw_cell.py<br />
<source lang="python"><br />
#original code written by Robert Campbell<br />
#modified by Stuart Ballard<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
from pymol.vfont import plain<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
cmd.extend("draw_cell",draw_cell)<br />
</source><br />
File: draw_symops_cctbx.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
from cctbx import uctbx, sgtbx<br />
#import string, math<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
<br />
from all_axes_new import get_all_axes<br />
<br />
import numpy as N<br />
#import numarray as N<br />
<br />
print "Finished importing for draw_symops_cctbx.py"<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
cmd.extend("draw_symops",draw_symops)<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
</source><br />
File: all_axes_new.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# List all axes in the unit cell.<br />
<br />
# usage:<br />
# python all_axes.py - show axes for the 230 reference settings.<br />
# python all_axes.py P2 - show axes for (e.g.) space group P2<br />
<br />
# RWGK = Ralf W. Grosse-Kunstleve<br />
# RWGK Some further refinement is required:<br />
# RWGK - List only the axes of highest order (e.g. only 4, not 4 and 2).<br />
# RWGK - List only the axes with the smallest intrinsic component<br />
# RWGK (e.g. list only 3(1), not both 3(1) and 3(2)).<br />
# RWGK See also: comment regarding shift_range below.<br />
<br />
from cctbx import sgtbx<br />
#from cctbx.misc.python_utils import list_plus<br />
<br />
import numpy as N<br />
import string, re<br />
<br />
def list_plus(lhs, rhs):<br />
return [l + r for l, r in zip(lhs, rhs)]<br />
<br />
def list_minus(lhs, rhs):<br />
return [l - r for l, r in zip(lhs, rhs)]<br />
<br />
def list_multiplies(lhs, rhs):<br />
return [l * r for l, r in zip(lhs, rhs)]<br />
<br />
def list_divides(lhs, rhs):<br />
return [l / r for l, r in zip(lhs, rhs)]<br />
<br />
def list_modulus(lhs, rhs):<br />
return [l % r for l, r in zip(lhs, rhs)]<br />
<br />
def list_dot_product(lhs, rhs=0):<br />
if (rhs == 0): rhs = lhs<br />
result = 0<br />
for l, r in zip(lhs, rhs): result += l * r<br />
return result<br />
<br />
def str_ev(EV):<br />
return "[%d,%d,%d]" % EV<br />
<br />
###def fract_2_dec(fraction):<br />
### list = fraction.split('/')<br />
### if len(list) == 2 and list[1] != 0:<br />
### decimal = string.atof(list[0])/string.atof(list[1])<br />
### else:<br />
### decimal = string.atof(fraction)<br />
### return decimal<br />
<br />
def rlc_RTMxAnalysis(M):<br />
r_info = sgtbx.rot_mx_info(M.r())<br />
t_info = sgtbx.translation_part_info(M)<br />
t_intrinsic = t_info.intrinsic_part().mod_positive().as_double()<br />
t_shift = t_info.origin_shift().mod_positive().as_double()<br />
<br />
#End = list_plus(Start + map(None,r_info.ev()))<br />
####debug<br />
### trans = 0<br />
### length = 0<br />
####debug<br />
<br />
#if (r_info.type() == 1):<br />
if (r_info.type() < 2):<br />
#(rt, start, end) = ('1',(0,0,0),(0,0,0))<br />
return None<br />
#elif (r_info.type() == -1):<br />
# (rt, start, end) = (str(r_info.type()),t_shift,())<br />
elif (abs(r_info.type()) == 2):<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
elif (r_info.type() == 3):<br />
if (r_info.sense() >= 0) :<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),(0,0,0),t_intrinsic))))<br />
# trans = N.sqrt(t_intrinsic[0]**2 + t_intrinsic[1]**2 + t_intrinsic[2]**2)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
# fudge to make sure that PyMOL actually draws the axis (move it slightly off [1,-1,1]) !!!<br />
r[0] = r[0]*1.000001<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
#(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
(start, end) = (t_shift,tuple(list_plus(t_shift,r)))<br />
length = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),start, end))))<br />
<br />
# r_info.sense() for 3^1 and 3^2 seems always to be "1" ???<br />
# if r_info.sense() < 0:<br />
# subscript = str(1-r_info.sense())<br />
# else:<br />
# subscript = str(r_info.sense())<br />
<br />
# use ratio of trans to length to get the correct axis symbol:<br />
# fudged the value to get the right numbers. (using length/2., rather than length/3.)<br />
if trans < length*0.5 :<br />
subscript = '1'<br />
else:<br />
subscript = '2'<br />
<br />
rt = str(r_info.type())+ "^" + subscript <br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
### print "Type, sense, Start, End, length, trans", rt, r_info.sense(), start, end, length, trans<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length)<br />
# print "(rt, start, end)", (rt,start,end)<br />
else:<br />
return None<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
elif (r_info.sense() > 0):<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
subscript = str(int(trans*r_info.type()+.5)) # add 0.5 to fix rounding errors<br />
(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
else:<br />
return None<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length),<br />
# print "(rt, start, end)", (rt,start,end)<br />
return (rt, start, end)<br />
<br />
def get_all_axes(space_group_symbol=None, space_group_info=None, extension=0):<br />
assert space_group_symbol is None or space_group_info is None<br />
shift_range = 1 # RWGK Works for the 230 reference settings; it is not<br />
# RWGK clear to me (rwgk) what value is needed in general.<br />
if (space_group_symbol is not None):<br />
space_group_info = sgtbx.space_group_info(symbol=space_group_symbol)<br />
#space_group_info.show_summary()<br />
<br />
axes_dict = {}<br />
for smx in space_group_info.group():<br />
r = smx.r()<br />
t = smx.t()<br />
shift = [0,0,0]<br />
for shift[0] in range(-shift_range,shift_range+1):<br />
for shift[1] in range(-shift_range,shift_range+1):<br />
for shift[2] in range(-shift_range,shift_range+1):<br />
ts = t.plus(sgtbx.tr_vec(shift, 1)).new_denominator(t.den())<br />
m = sgtbx.rt_mx(r, ts)<br />
#print m<br />
rtmxanal = rlc_RTMxAnalysis(m)<br />
#print r, t, shift, ts, m<br />
if rtmxanal:<br />
#print rtmxanal<br />
axes_dict[rtmxanal] = 0<br />
axes_list = axes_dict.keys()<br />
axes_list.sort()<br />
<br />
# reject nonenantiomorphic space groups<br />
if len(axes_list) > 0 and not re.compile("[A-z]").search(space_group_symbol[1:]):<br />
try:<br />
sgtbx.space_group_info(space_group_symbol).show_summary(), <br />
#print len(axes_list), space_group_symbol<br />
except:<br />
print space_group, space_group_symbol<br />
print<br />
sys.exit(1)<br />
axes = []<br />
for a in axes_list:<br />
if len(a) == 3 and len(a[1]) == 3 and len(a[2]) == 3:<br />
tmp_dict = {}<br />
print "%4s %7.4f %7.4f %7.4f %7.4f %7.4f %7.4f " % (a[0],a[1][0],a[1][1],a[1][2],a[2][0],a[2][1],a[2][2])<br />
tmp_dict['symb'] = a[0]<br />
start_array = N.asarray(a[1])<br />
end_array = N.asarray(a[2])<br />
start_vec = start_array - (end_array - start_array)*extension<br />
end_vec = end_array + (end_array - start_array)*extension<br />
tmp_dict['start'] = start_vec<br />
tmp_dict['end'] = end_vec<br />
#rlc# tmp_dict['start'] = a[1]<br />
#rlc# tmp_dict['end'] = a[2]<br />
axes.append(tmp_dict)<br />
else:<br />
print a<br />
else:<br />
return None<br />
<br />
return axes<br />
<br />
if (__name__ == "__main__"):<br />
import sys<br />
if (len(sys.argv) == 1):<br />
for i in range(230):<br />
get_all_axes(i + 1)<br />
else:<br />
for symbol in sys.argv[1:]:<br />
get_all_axes(symbol)<br />
</source><br />
<br />
[[Category:Plugins]]<br />
[[Category:Script_Library]]<br />
[[Category:Math_Scripts]]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5604
SuperSym
2009-09-01T23:33:18Z
<p>Srballard: </p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [https://sourceforge.net/projects/supersym/ https://sourceforge.net/projects/supersym/] and displayed below.<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Using SuperSym==<br />
<br />
To use SuperSym, copy the text of source files to corresponding .py files. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu in the PyMOL GUI, ignore SuperSymMenu.py and run the other files in PyMOL as you would for any other script.<br />
<br />
==Source Files==<br />
<br />
File: SuperSym.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import sys<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
import draw_cell as draw_cell<br />
import draw_symops_cctbx as sym_axes<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)], parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 3: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell.draw_cell(object, 3.0)<br />
else:<br />
draw_cell.draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
sym_axes.draw_symops(object, 2.0)<br />
else:<br />
sym_axes.draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
for i in opList:<br />
try:<br />
stored.tmpOp = raw_ops[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
atoms = cmd.count_atoms(copy)<br />
cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
xMean = (stored.xSum / atoms)<br />
yMean = (stored.ySum / atoms)<br />
zMean = (stored.zSum / atoms)<br />
xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
cell_shift(copy,dX,dY,dZ, 0)<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def shift_and_copy(object, dX, dY, dZ):<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
copy = oldPre + newX + newY + newZ<br />
if cmd.count_atoms(copy) != 0:<br />
print "Symmetry partner already exists in destination position!"<br />
quit()<br />
cmd.copy(newName, object)<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, newName, "x,y,z = cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
# this function is borrowed from findSurfaceResidues script on PyMOL wiki<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
</source><br />
File: SuperSymMenu.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkFileDialog<br />
from pymol import cmd, selector<br />
from SuperSym import *<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addmenu('SuperSym','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
</source><br />
File: draw_cell.py<br />
<source lang="python"><br />
#original code written by Robert Campbell<br />
#modified by Stuart Ballard<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
from pymol.vfont import plain<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
cmd.extend("draw_cell",draw_cell)<br />
</source><br />
File: draw_symops_cctbx.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
from cctbx import uctbx, sgtbx<br />
#import string, math<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
<br />
from all_axes_new import get_all_axes<br />
<br />
import numpy as N<br />
#import numarray as N<br />
<br />
print "Finished importing for draw_symops_cctbx.py"<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
cmd.extend("draw_symops",draw_symops)<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
</source><br />
File: all_axes_new.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# List all axes in the unit cell.<br />
<br />
# usage:<br />
# python all_axes.py - show axes for the 230 reference settings.<br />
# python all_axes.py P2 - show axes for (e.g.) space group P2<br />
<br />
# RWGK = Ralf W. Grosse-Kunstleve<br />
# RWGK Some further refinement is required:<br />
# RWGK - List only the axes of highest order (e.g. only 4, not 4 and 2).<br />
# RWGK - List only the axes with the smallest intrinsic component<br />
# RWGK (e.g. list only 3(1), not both 3(1) and 3(2)).<br />
# RWGK See also: comment regarding shift_range below.<br />
<br />
from cctbx import sgtbx<br />
#from cctbx.misc.python_utils import list_plus<br />
<br />
import numpy as N<br />
import string, re<br />
<br />
def list_plus(lhs, rhs):<br />
return [l + r for l, r in zip(lhs, rhs)]<br />
<br />
def list_minus(lhs, rhs):<br />
return [l - r for l, r in zip(lhs, rhs)]<br />
<br />
def list_multiplies(lhs, rhs):<br />
return [l * r for l, r in zip(lhs, rhs)]<br />
<br />
def list_divides(lhs, rhs):<br />
return [l / r for l, r in zip(lhs, rhs)]<br />
<br />
def list_modulus(lhs, rhs):<br />
return [l % r for l, r in zip(lhs, rhs)]<br />
<br />
def list_dot_product(lhs, rhs=0):<br />
if (rhs == 0): rhs = lhs<br />
result = 0<br />
for l, r in zip(lhs, rhs): result += l * r<br />
return result<br />
<br />
def str_ev(EV):<br />
return "[%d,%d,%d]" % EV<br />
<br />
###def fract_2_dec(fraction):<br />
### list = fraction.split('/')<br />
### if len(list) == 2 and list[1] != 0:<br />
### decimal = string.atof(list[0])/string.atof(list[1])<br />
### else:<br />
### decimal = string.atof(fraction)<br />
### return decimal<br />
<br />
def rlc_RTMxAnalysis(M):<br />
r_info = sgtbx.rot_mx_info(M.r())<br />
t_info = sgtbx.translation_part_info(M)<br />
t_intrinsic = t_info.intrinsic_part().mod_positive().as_double()<br />
t_shift = t_info.origin_shift().mod_positive().as_double()<br />
<br />
#End = list_plus(Start + map(None,r_info.ev()))<br />
####debug<br />
### trans = 0<br />
### length = 0<br />
####debug<br />
<br />
#if (r_info.type() == 1):<br />
if (r_info.type() < 2):<br />
#(rt, start, end) = ('1',(0,0,0),(0,0,0))<br />
return None<br />
#elif (r_info.type() == -1):<br />
# (rt, start, end) = (str(r_info.type()),t_shift,())<br />
elif (abs(r_info.type()) == 2):<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
elif (r_info.type() == 3):<br />
if (r_info.sense() >= 0) :<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),(0,0,0),t_intrinsic))))<br />
# trans = N.sqrt(t_intrinsic[0]**2 + t_intrinsic[1]**2 + t_intrinsic[2]**2)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
# fudge to make sure that PyMOL actually draws the axis (move it slightly off [1,-1,1]) !!!<br />
r[0] = r[0]*1.000001<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
#(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
(start, end) = (t_shift,tuple(list_plus(t_shift,r)))<br />
length = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),start, end))))<br />
<br />
# r_info.sense() for 3^1 and 3^2 seems always to be "1" ???<br />
# if r_info.sense() < 0:<br />
# subscript = str(1-r_info.sense())<br />
# else:<br />
# subscript = str(r_info.sense())<br />
<br />
# use ratio of trans to length to get the correct axis symbol:<br />
# fudged the value to get the right numbers. (using length/2., rather than length/3.)<br />
if trans < length*0.5 :<br />
subscript = '1'<br />
else:<br />
subscript = '2'<br />
<br />
rt = str(r_info.type())+ "^" + subscript <br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
### print "Type, sense, Start, End, length, trans", rt, r_info.sense(), start, end, length, trans<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length)<br />
# print "(rt, start, end)", (rt,start,end)<br />
else:<br />
return None<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
elif (r_info.sense() > 0):<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
subscript = str(int(trans*r_info.type()+.5)) # add 0.5 to fix rounding errors<br />
(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
else:<br />
return None<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length),<br />
# print "(rt, start, end)", (rt,start,end)<br />
return (rt, start, end)<br />
<br />
def get_all_axes(space_group_symbol=None, space_group_info=None, extension=0):<br />
assert space_group_symbol is None or space_group_info is None<br />
shift_range = 1 # RWGK Works for the 230 reference settings; it is not<br />
# RWGK clear to me (rwgk) what value is needed in general.<br />
if (space_group_symbol is not None):<br />
space_group_info = sgtbx.space_group_info(symbol=space_group_symbol)<br />
#space_group_info.show_summary()<br />
<br />
axes_dict = {}<br />
for smx in space_group_info.group():<br />
r = smx.r()<br />
t = smx.t()<br />
shift = [0,0,0]<br />
for shift[0] in range(-shift_range,shift_range+1):<br />
for shift[1] in range(-shift_range,shift_range+1):<br />
for shift[2] in range(-shift_range,shift_range+1):<br />
ts = t.plus(sgtbx.tr_vec(shift, 1)).new_denominator(t.den())<br />
m = sgtbx.rt_mx(r, ts)<br />
#print m<br />
rtmxanal = rlc_RTMxAnalysis(m)<br />
#print r, t, shift, ts, m<br />
if rtmxanal:<br />
#print rtmxanal<br />
axes_dict[rtmxanal] = 0<br />
axes_list = axes_dict.keys()<br />
axes_list.sort()<br />
<br />
# reject nonenantiomorphic space groups<br />
if len(axes_list) > 0 and not re.compile("[A-z]").search(space_group_symbol[1:]):<br />
try:<br />
sgtbx.space_group_info(space_group_symbol).show_summary(), <br />
#print len(axes_list), space_group_symbol<br />
except:<br />
print space_group, space_group_symbol<br />
print<br />
sys.exit(1)<br />
axes = []<br />
for a in axes_list:<br />
if len(a) == 3 and len(a[1]) == 3 and len(a[2]) == 3:<br />
tmp_dict = {}<br />
print "%4s %7.4f %7.4f %7.4f %7.4f %7.4f %7.4f " % (a[0],a[1][0],a[1][1],a[1][2],a[2][0],a[2][1],a[2][2])<br />
tmp_dict['symb'] = a[0]<br />
start_array = N.asarray(a[1])<br />
end_array = N.asarray(a[2])<br />
start_vec = start_array - (end_array - start_array)*extension<br />
end_vec = end_array + (end_array - start_array)*extension<br />
tmp_dict['start'] = start_vec<br />
tmp_dict['end'] = end_vec<br />
#rlc# tmp_dict['start'] = a[1]<br />
#rlc# tmp_dict['end'] = a[2]<br />
axes.append(tmp_dict)<br />
else:<br />
print a<br />
else:<br />
return None<br />
<br />
return axes<br />
<br />
if (__name__ == "__main__"):<br />
import sys<br />
if (len(sys.argv) == 1):<br />
for i in range(230):<br />
get_all_axes(i + 1)<br />
else:<br />
for symbol in sys.argv[1:]:<br />
get_all_axes(symbol)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5603
SuperSym
2009-09-01T21:53:35Z
<p>Srballard: /* Dependencies and Acknowledgments */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is below.<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell and Ralf W. Grosse-Kunstleve, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. Some of this code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Using SuperSym==<br />
<br />
To use SuperSym, copy the text of source files to corresponding .py files. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu in the PyMOL GUI, ignore SuperSymMenu.py and run the other files in PyMOL as you would for any other script.<br />
<br />
==Source Files==<br />
<br />
File: SuperSym.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import sys<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
import draw_cell as draw_cell<br />
import draw_symops_cctbx as sym_axes<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)], parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 3: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell.draw_cell(object, 3.0)<br />
else:<br />
draw_cell.draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
sym_axes.draw_symops(object, 2.0)<br />
else:<br />
sym_axes.draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
for i in opList:<br />
try:<br />
stored.tmpOp = raw_ops[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
atoms = cmd.count_atoms(copy)<br />
cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
xMean = (stored.xSum / atoms)<br />
yMean = (stored.ySum / atoms)<br />
zMean = (stored.zSum / atoms)<br />
xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
cell_shift(copy,dX,dY,dZ, 0)<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def shift_and_copy(object, dX, dY, dZ):<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
copy = oldPre + newX + newY + newZ<br />
if cmd.count_atoms(copy) != 0:<br />
print "Symmetry partner already exists in destination position!"<br />
quit()<br />
cmd.copy(newName, object)<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, newName, "x,y,z = cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
# this function is borrowed from findSurfaceResidues script on PyMOL wiki<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
</source><br />
File: SuperSymMenu.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkFileDialog<br />
from pymol import cmd, selector<br />
from SuperSym import *<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addmenu('SuperSym','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
</source><br />
File: draw_cell.py<br />
<source lang="python"><br />
#original code written by Robert Campbell<br />
#modified by Stuart Ballard<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
from pymol.vfont import plain<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
cmd.extend("draw_cell",draw_cell)<br />
</source><br />
File: draw_symops_cctbx.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
from cctbx import uctbx, sgtbx<br />
#import string, math<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
<br />
from all_axes_new import get_all_axes<br />
<br />
import numpy as N<br />
#import numarray as N<br />
<br />
print "Finished importing for draw_symops_cctbx.py"<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
cmd.extend("draw_symops",draw_symops)<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
</source><br />
File: all_axes_new.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# List all axes in the unit cell.<br />
<br />
# usage:<br />
# python all_axes.py - show axes for the 230 reference settings.<br />
# python all_axes.py P2 - show axes for (e.g.) space group P2<br />
<br />
# RWGK = Ralf W. Grosse-Kunstleve<br />
# RWGK Some further refinement is required:<br />
# RWGK - List only the axes of highest order (e.g. only 4, not 4 and 2).<br />
# RWGK - List only the axes with the smallest intrinsic component<br />
# RWGK (e.g. list only 3(1), not both 3(1) and 3(2)).<br />
# RWGK See also: comment regarding shift_range below.<br />
<br />
from cctbx import sgtbx<br />
#from cctbx.misc.python_utils import list_plus<br />
<br />
import numpy as N<br />
import string, re<br />
<br />
def list_plus(lhs, rhs):<br />
return [l + r for l, r in zip(lhs, rhs)]<br />
<br />
def list_minus(lhs, rhs):<br />
return [l - r for l, r in zip(lhs, rhs)]<br />
<br />
def list_multiplies(lhs, rhs):<br />
return [l * r for l, r in zip(lhs, rhs)]<br />
<br />
def list_divides(lhs, rhs):<br />
return [l / r for l, r in zip(lhs, rhs)]<br />
<br />
def list_modulus(lhs, rhs):<br />
return [l % r for l, r in zip(lhs, rhs)]<br />
<br />
def list_dot_product(lhs, rhs=0):<br />
if (rhs == 0): rhs = lhs<br />
result = 0<br />
for l, r in zip(lhs, rhs): result += l * r<br />
return result<br />
<br />
def str_ev(EV):<br />
return "[%d,%d,%d]" % EV<br />
<br />
###def fract_2_dec(fraction):<br />
### list = fraction.split('/')<br />
### if len(list) == 2 and list[1] != 0:<br />
### decimal = string.atof(list[0])/string.atof(list[1])<br />
### else:<br />
### decimal = string.atof(fraction)<br />
### return decimal<br />
<br />
def rlc_RTMxAnalysis(M):<br />
r_info = sgtbx.rot_mx_info(M.r())<br />
t_info = sgtbx.translation_part_info(M)<br />
t_intrinsic = t_info.intrinsic_part().mod_positive().as_double()<br />
t_shift = t_info.origin_shift().mod_positive().as_double()<br />
<br />
#End = list_plus(Start + map(None,r_info.ev()))<br />
####debug<br />
### trans = 0<br />
### length = 0<br />
####debug<br />
<br />
#if (r_info.type() == 1):<br />
if (r_info.type() < 2):<br />
#(rt, start, end) = ('1',(0,0,0),(0,0,0))<br />
return None<br />
#elif (r_info.type() == -1):<br />
# (rt, start, end) = (str(r_info.type()),t_shift,())<br />
elif (abs(r_info.type()) == 2):<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
elif (r_info.type() == 3):<br />
if (r_info.sense() >= 0) :<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),(0,0,0),t_intrinsic))))<br />
# trans = N.sqrt(t_intrinsic[0]**2 + t_intrinsic[1]**2 + t_intrinsic[2]**2)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
# fudge to make sure that PyMOL actually draws the axis (move it slightly off [1,-1,1]) !!!<br />
r[0] = r[0]*1.000001<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
#(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
(start, end) = (t_shift,tuple(list_plus(t_shift,r)))<br />
length = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),start, end))))<br />
<br />
# r_info.sense() for 3^1 and 3^2 seems always to be "1" ???<br />
# if r_info.sense() < 0:<br />
# subscript = str(1-r_info.sense())<br />
# else:<br />
# subscript = str(r_info.sense())<br />
<br />
# use ratio of trans to length to get the correct axis symbol:<br />
# fudged the value to get the right numbers. (using length/2., rather than length/3.)<br />
if trans < length*0.5 :<br />
subscript = '1'<br />
else:<br />
subscript = '2'<br />
<br />
rt = str(r_info.type())+ "^" + subscript <br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
### print "Type, sense, Start, End, length, trans", rt, r_info.sense(), start, end, length, trans<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length)<br />
# print "(rt, start, end)", (rt,start,end)<br />
else:<br />
return None<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
elif (r_info.sense() > 0):<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
subscript = str(int(trans*r_info.type()+.5)) # add 0.5 to fix rounding errors<br />
(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
else:<br />
return None<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length),<br />
# print "(rt, start, end)", (rt,start,end)<br />
return (rt, start, end)<br />
<br />
def get_all_axes(space_group_symbol=None, space_group_info=None, extension=0):<br />
assert space_group_symbol is None or space_group_info is None<br />
shift_range = 1 # RWGK Works for the 230 reference settings; it is not<br />
# RWGK clear to me (rwgk) what value is needed in general.<br />
if (space_group_symbol is not None):<br />
space_group_info = sgtbx.space_group_info(symbol=space_group_symbol)<br />
#space_group_info.show_summary()<br />
<br />
axes_dict = {}<br />
for smx in space_group_info.group():<br />
r = smx.r()<br />
t = smx.t()<br />
shift = [0,0,0]<br />
for shift[0] in range(-shift_range,shift_range+1):<br />
for shift[1] in range(-shift_range,shift_range+1):<br />
for shift[2] in range(-shift_range,shift_range+1):<br />
ts = t.plus(sgtbx.tr_vec(shift, 1)).new_denominator(t.den())<br />
m = sgtbx.rt_mx(r, ts)<br />
#print m<br />
rtmxanal = rlc_RTMxAnalysis(m)<br />
#print r, t, shift, ts, m<br />
if rtmxanal:<br />
#print rtmxanal<br />
axes_dict[rtmxanal] = 0<br />
axes_list = axes_dict.keys()<br />
axes_list.sort()<br />
<br />
# reject nonenantiomorphic space groups<br />
if len(axes_list) > 0 and not re.compile("[A-z]").search(space_group_symbol[1:]):<br />
try:<br />
sgtbx.space_group_info(space_group_symbol).show_summary(), <br />
#print len(axes_list), space_group_symbol<br />
except:<br />
print space_group, space_group_symbol<br />
print<br />
sys.exit(1)<br />
axes = []<br />
for a in axes_list:<br />
if len(a) == 3 and len(a[1]) == 3 and len(a[2]) == 3:<br />
tmp_dict = {}<br />
print "%4s %7.4f %7.4f %7.4f %7.4f %7.4f %7.4f " % (a[0],a[1][0],a[1][1],a[1][2],a[2][0],a[2][1],a[2][2])<br />
tmp_dict['symb'] = a[0]<br />
start_array = N.asarray(a[1])<br />
end_array = N.asarray(a[2])<br />
start_vec = start_array - (end_array - start_array)*extension<br />
end_vec = end_array + (end_array - start_array)*extension<br />
tmp_dict['start'] = start_vec<br />
tmp_dict['end'] = end_vec<br />
#rlc# tmp_dict['start'] = a[1]<br />
#rlc# tmp_dict['end'] = a[2]<br />
axes.append(tmp_dict)<br />
else:<br />
print a<br />
else:<br />
return None<br />
<br />
return axes<br />
<br />
if (__name__ == "__main__"):<br />
import sys<br />
if (len(sys.argv) == 1):<br />
for i in range(230):<br />
get_all_axes(i + 1)<br />
else:<br />
for symbol in sys.argv[1:]:<br />
get_all_axes(symbol)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5602
SuperSym
2009-09-01T21:52:58Z
<p>Srballard: /* Source Files */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is below.<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. This code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Using SuperSym==<br />
<br />
To use SuperSym, copy the text of source files to corresponding .py files. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu in the PyMOL GUI, ignore SuperSymMenu.py and run the other files in PyMOL as you would for any other script.<br />
<br />
==Source Files==<br />
<br />
File: SuperSym.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import sys<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
import draw_cell as draw_cell<br />
import draw_symops_cctbx as sym_axes<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)], parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 3: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell.draw_cell(object, 3.0)<br />
else:<br />
draw_cell.draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
sym_axes.draw_symops(object, 2.0)<br />
else:<br />
sym_axes.draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
for i in opList:<br />
try:<br />
stored.tmpOp = raw_ops[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
atoms = cmd.count_atoms(copy)<br />
cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
xMean = (stored.xSum / atoms)<br />
yMean = (stored.ySum / atoms)<br />
zMean = (stored.zSum / atoms)<br />
xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
cell_shift(copy,dX,dY,dZ, 0)<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def shift_and_copy(object, dX, dY, dZ):<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
copy = oldPre + newX + newY + newZ<br />
if cmd.count_atoms(copy) != 0:<br />
print "Symmetry partner already exists in destination position!"<br />
quit()<br />
cmd.copy(newName, object)<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, newName, "x,y,z = cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
# this function is borrowed from findSurfaceResidues script on PyMOL wiki<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
</source><br />
File: SuperSymMenu.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkFileDialog<br />
from pymol import cmd, selector<br />
from SuperSym import *<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addmenu('SuperSym','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
</source><br />
File: draw_cell.py<br />
<source lang="python"><br />
#original code written by Robert Campbell<br />
#modified by Stuart Ballard<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
from pymol.vfont import plain<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
cmd.extend("draw_cell",draw_cell)<br />
</source><br />
File: draw_symops_cctbx.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
from cctbx import uctbx, sgtbx<br />
#import string, math<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
<br />
from all_axes_new import get_all_axes<br />
<br />
import numpy as N<br />
#import numarray as N<br />
<br />
print "Finished importing for draw_symops_cctbx.py"<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
cmd.extend("draw_symops",draw_symops)<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
</source><br />
File: all_axes_new.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# List all axes in the unit cell.<br />
<br />
# usage:<br />
# python all_axes.py - show axes for the 230 reference settings.<br />
# python all_axes.py P2 - show axes for (e.g.) space group P2<br />
<br />
# RWGK = Ralf W. Grosse-Kunstleve<br />
# RWGK Some further refinement is required:<br />
# RWGK - List only the axes of highest order (e.g. only 4, not 4 and 2).<br />
# RWGK - List only the axes with the smallest intrinsic component<br />
# RWGK (e.g. list only 3(1), not both 3(1) and 3(2)).<br />
# RWGK See also: comment regarding shift_range below.<br />
<br />
from cctbx import sgtbx<br />
#from cctbx.misc.python_utils import list_plus<br />
<br />
import numpy as N<br />
import string, re<br />
<br />
def list_plus(lhs, rhs):<br />
return [l + r for l, r in zip(lhs, rhs)]<br />
<br />
def list_minus(lhs, rhs):<br />
return [l - r for l, r in zip(lhs, rhs)]<br />
<br />
def list_multiplies(lhs, rhs):<br />
return [l * r for l, r in zip(lhs, rhs)]<br />
<br />
def list_divides(lhs, rhs):<br />
return [l / r for l, r in zip(lhs, rhs)]<br />
<br />
def list_modulus(lhs, rhs):<br />
return [l % r for l, r in zip(lhs, rhs)]<br />
<br />
def list_dot_product(lhs, rhs=0):<br />
if (rhs == 0): rhs = lhs<br />
result = 0<br />
for l, r in zip(lhs, rhs): result += l * r<br />
return result<br />
<br />
def str_ev(EV):<br />
return "[%d,%d,%d]" % EV<br />
<br />
###def fract_2_dec(fraction):<br />
### list = fraction.split('/')<br />
### if len(list) == 2 and list[1] != 0:<br />
### decimal = string.atof(list[0])/string.atof(list[1])<br />
### else:<br />
### decimal = string.atof(fraction)<br />
### return decimal<br />
<br />
def rlc_RTMxAnalysis(M):<br />
r_info = sgtbx.rot_mx_info(M.r())<br />
t_info = sgtbx.translation_part_info(M)<br />
t_intrinsic = t_info.intrinsic_part().mod_positive().as_double()<br />
t_shift = t_info.origin_shift().mod_positive().as_double()<br />
<br />
#End = list_plus(Start + map(None,r_info.ev()))<br />
####debug<br />
### trans = 0<br />
### length = 0<br />
####debug<br />
<br />
#if (r_info.type() == 1):<br />
if (r_info.type() < 2):<br />
#(rt, start, end) = ('1',(0,0,0),(0,0,0))<br />
return None<br />
#elif (r_info.type() == -1):<br />
# (rt, start, end) = (str(r_info.type()),t_shift,())<br />
elif (abs(r_info.type()) == 2):<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type())+"^1",t_shift,tuple(list_plus(t_shift,r_info.ev())))<br />
elif (r_info.type() == 3):<br />
if (r_info.sense() >= 0) :<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),(0,0,0),t_intrinsic))))<br />
# trans = N.sqrt(t_intrinsic[0]**2 + t_intrinsic[1]**2 + t_intrinsic[2]**2)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
# fudge to make sure that PyMOL actually draws the axis (move it slightly off [1,-1,1]) !!!<br />
r[0] = r[0]*1.000001<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
#(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
(start, end) = (t_shift,tuple(list_plus(t_shift,r)))<br />
length = N.sqrt(reduce(lambda x,y:x+y,(map(lambda x,y:(y-x)*(y-x),start, end))))<br />
<br />
# r_info.sense() for 3^1 and 3^2 seems always to be "1" ???<br />
# if r_info.sense() < 0:<br />
# subscript = str(1-r_info.sense())<br />
# else:<br />
# subscript = str(r_info.sense())<br />
<br />
# use ratio of trans to length to get the correct axis symbol:<br />
# fudged the value to get the right numbers. (using length/2., rather than length/3.)<br />
if trans < length*0.5 :<br />
subscript = '1'<br />
else:<br />
subscript = '2'<br />
<br />
rt = str(r_info.type())+ "^" + subscript <br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
### print "Type, sense, Start, End, length, trans", rt, r_info.sense(), start, end, length, trans<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length)<br />
# print "(rt, start, end)", (rt,start,end)<br />
else:<br />
return None<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
elif (r_info.sense() > 0):<br />
# ignore opposite sense of rotation axes since they superimpose<br />
trans = reduce(lambda x,y:x+y,t_intrinsic)<br />
if trans == 0:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
(rt, start, end) = (str(r_info.type()),t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()),t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
else:<br />
maxr = max([abs(x) for x in r_info.ev()])<br />
r = [float(x)/maxr for x in r_info.ev()]<br />
subscript = str(int(trans*r_info.type()+.5)) # add 0.5 to fix rounding errors<br />
(rt, start, end) = (str(r_info.type())+ "^" + subscript ,t_shift,tuple(list_plus(t_shift,r)))<br />
#(rt, start, end) = (str(r_info.type()) + "^" + subscript,t_shift, tuple(list_plus(t_shift,r_info.ev())))<br />
#return (r_info.type(),r_info.ev(), t_intrinsic, t_shift)<br />
else:<br />
return None<br />
# print "type: %s, sense: %s, trans: %s, length: %s," % (r_info.type(), r_info.sense(), trans, length),<br />
# print "(rt, start, end)", (rt,start,end)<br />
return (rt, start, end)<br />
<br />
def get_all_axes(space_group_symbol=None, space_group_info=None, extension=0):<br />
assert space_group_symbol is None or space_group_info is None<br />
shift_range = 1 # RWGK Works for the 230 reference settings; it is not<br />
# RWGK clear to me (rwgk) what value is needed in general.<br />
if (space_group_symbol is not None):<br />
space_group_info = sgtbx.space_group_info(symbol=space_group_symbol)<br />
#space_group_info.show_summary()<br />
<br />
axes_dict = {}<br />
for smx in space_group_info.group():<br />
r = smx.r()<br />
t = smx.t()<br />
shift = [0,0,0]<br />
for shift[0] in range(-shift_range,shift_range+1):<br />
for shift[1] in range(-shift_range,shift_range+1):<br />
for shift[2] in range(-shift_range,shift_range+1):<br />
ts = t.plus(sgtbx.tr_vec(shift, 1)).new_denominator(t.den())<br />
m = sgtbx.rt_mx(r, ts)<br />
#print m<br />
rtmxanal = rlc_RTMxAnalysis(m)<br />
#print r, t, shift, ts, m<br />
if rtmxanal:<br />
#print rtmxanal<br />
axes_dict[rtmxanal] = 0<br />
axes_list = axes_dict.keys()<br />
axes_list.sort()<br />
<br />
# reject nonenantiomorphic space groups<br />
if len(axes_list) > 0 and not re.compile("[A-z]").search(space_group_symbol[1:]):<br />
try:<br />
sgtbx.space_group_info(space_group_symbol).show_summary(), <br />
#print len(axes_list), space_group_symbol<br />
except:<br />
print space_group, space_group_symbol<br />
print<br />
sys.exit(1)<br />
axes = []<br />
for a in axes_list:<br />
if len(a) == 3 and len(a[1]) == 3 and len(a[2]) == 3:<br />
tmp_dict = {}<br />
print "%4s %7.4f %7.4f %7.4f %7.4f %7.4f %7.4f " % (a[0],a[1][0],a[1][1],a[1][2],a[2][0],a[2][1],a[2][2])<br />
tmp_dict['symb'] = a[0]<br />
start_array = N.asarray(a[1])<br />
end_array = N.asarray(a[2])<br />
start_vec = start_array - (end_array - start_array)*extension<br />
end_vec = end_array + (end_array - start_array)*extension<br />
tmp_dict['start'] = start_vec<br />
tmp_dict['end'] = end_vec<br />
#rlc# tmp_dict['start'] = a[1]<br />
#rlc# tmp_dict['end'] = a[2]<br />
axes.append(tmp_dict)<br />
else:<br />
print a<br />
else:<br />
return None<br />
<br />
return axes<br />
<br />
if (__name__ == "__main__"):<br />
import sys<br />
if (len(sys.argv) == 1):<br />
for i in range(230):<br />
get_all_axes(i + 1)<br />
else:<br />
for symbol in sys.argv[1:]:<br />
get_all_axes(symbol)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5601
SuperSym
2009-08-31T22:09:34Z
<p>Srballard: /* Dependencies and Acknowledgments */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is below.<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell, available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. This code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Using SuperSym==<br />
<br />
To use SuperSym, copy the text of source files to corresponding .py files. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu in the PyMOL GUI, ignore SuperSymMenu.py and run the other files in PyMOL as you would for any other script.<br />
<br />
==Source Files==<br />
<br />
File: SuperSym.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import sys<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
import draw_cell as draw_cell<br />
import draw_symops_cctbx as sym_axes<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)], parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 3: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell.draw_cell(object, 3.0)<br />
else:<br />
draw_cell.draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
sym_axes.draw_symops(object, 2.0)<br />
else:<br />
sym_axes.draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
for i in opList:<br />
try:<br />
stored.tmpOp = raw_ops[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
atoms = cmd.count_atoms(copy)<br />
cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
xMean = (stored.xSum / atoms)<br />
yMean = (stored.ySum / atoms)<br />
zMean = (stored.zSum / atoms)<br />
xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
cell_shift(copy,dX,dY,dZ, 0)<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def shift_and_copy(object, dX, dY, dZ):<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
copy = oldPre + newX + newY + newZ<br />
if cmd.count_atoms(copy) != 0:<br />
print "Symmetry partner already exists in destination position!"<br />
quit()<br />
cmd.copy(newName, object)<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, newName, "x,y,z = cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
# this function is borrowed from findSurfaceResidues script on PyMOL wiki<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
</source><br />
File: SuperSymMenu.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkFileDialog<br />
from pymol import cmd, selector<br />
from SuperSym import *<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addmenu('SuperSym','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
</source><br />
File: draw_cell.py<br />
<source lang="python"><br />
#original code written by Robert Campbell<br />
#modified by Stuart Ballard<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
from pymol.vfont import plain<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
cmd.extend("draw_cell",draw_cell)<br />
</source><br />
File: draw_symops_cctbx.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
from cctbx import uctbx, sgtbx<br />
#import string, math<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
<br />
from all_axes_new import get_all_axes<br />
<br />
import numpy as N<br />
#import numarray as N<br />
<br />
print "Finished importing for draw_symops_cctbx.py"<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
cmd.extend("draw_symops",draw_symops)<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5600
SuperSym
2009-08-31T22:09:04Z
<p>Srballard: </p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is below.<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts created by Robert Campbell available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. This code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Using SuperSym==<br />
<br />
To use SuperSym, copy the text of source files to corresponding .py files. Place SuperSymMenu.py in pymol/modules/pmg_tk/startup, and all other files in pymol/modules.<br />
<br />
To use functions of SuperSym directly, without creating a drop-down menu in the PyMOL GUI, ignore SuperSymMenu.py and run the other files in PyMOL as you would for any other script.<br />
<br />
==Source Files==<br />
<br />
File: SuperSym.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import sys<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
import draw_cell as draw_cell<br />
import draw_symops_cctbx as sym_axes<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)], parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 3: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell.draw_cell(object, 3.0)<br />
else:<br />
draw_cell.draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
sym_axes.draw_symops(object, 2.0)<br />
else:<br />
sym_axes.draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
for i in opList:<br />
try:<br />
stored.tmpOp = raw_ops[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
atoms = cmd.count_atoms(copy)<br />
cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
xMean = (stored.xSum / atoms)<br />
yMean = (stored.ySum / atoms)<br />
zMean = (stored.zSum / atoms)<br />
xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
cell_shift(copy,dX,dY,dZ, 0)<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def shift_and_copy(object, dX, dY, dZ):<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
copy = oldPre + newX + newY + newZ<br />
if cmd.count_atoms(copy) != 0:<br />
print "Symmetry partner already exists in destination position!"<br />
quit()<br />
cmd.copy(newName, object)<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, newName, "x,y,z = cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
# this function is borrowed from findSurfaceResidues script on PyMOL wiki<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
</source><br />
File: SuperSymMenu.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkFileDialog<br />
from pymol import cmd, selector<br />
from SuperSym import *<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addmenu('SuperSym','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
</source><br />
File: draw_cell.py<br />
<source lang="python"><br />
#original code written by Robert Campbell<br />
#modified by Stuart Ballard<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
from pymol.vfont import plain<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
cmd.extend("draw_cell",draw_cell)<br />
</source><br />
File: draw_symops_cctbx.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
from cctbx import uctbx, sgtbx<br />
#import string, math<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
<br />
from all_axes_new import get_all_axes<br />
<br />
import numpy as N<br />
#import numarray as N<br />
<br />
print "Finished importing for draw_symops_cctbx.py"<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
cmd.extend("draw_symops",draw_symops)<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5599
SuperSym
2009-08-31T22:01:11Z
<p>Srballard: /* Dependencies and Acknowledgments */</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is below.<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. This code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Source Files==<br />
<br />
File: SuperSym.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import sys<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
import draw_cell as draw_cell<br />
import draw_symops_cctbx as sym_axes<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)], parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 3: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell.draw_cell(object, 3.0)<br />
else:<br />
draw_cell.draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
sym_axes.draw_symops(object, 2.0)<br />
else:<br />
sym_axes.draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
for i in opList:<br />
try:<br />
stored.tmpOp = raw_ops[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
atoms = cmd.count_atoms(copy)<br />
cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
xMean = (stored.xSum / atoms)<br />
yMean = (stored.ySum / atoms)<br />
zMean = (stored.zSum / atoms)<br />
xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
cell_shift(copy,dX,dY,dZ, 0)<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def shift_and_copy(object, dX, dY, dZ):<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
copy = oldPre + newX + newY + newZ<br />
if cmd.count_atoms(copy) != 0:<br />
print "Symmetry partner already exists in destination position!"<br />
quit()<br />
cmd.copy(newName, object)<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, newName, "x,y,z = cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
# this function is borrowed from findSurfaceResidues script on PyMOL wiki<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
</source><br />
File: SuperSymMenu.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkFileDialog<br />
from pymol import cmd, selector<br />
from SuperSym import *<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addmenu('SuperSym','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
</source><br />
File: draw_cell.py<br />
<source lang="python"><br />
#original code written by Robert Campbell<br />
#modified by Stuart Ballard<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
from pymol.vfont import plain<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
cmd.extend("draw_cell",draw_cell)<br />
</source><br />
File: draw_symops_cctbx.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
from cctbx import uctbx, sgtbx<br />
#import string, math<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
<br />
from all_axes_new import get_all_axes<br />
<br />
import numpy as N<br />
#import numarray as N<br />
<br />
print "Finished importing for draw_symops_cctbx.py"<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
cmd.extend("draw_symops",draw_symops)<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5598
SuperSym
2009-08-31T22:00:46Z
<p>Srballard: </p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is below.<br />
<br />
==Dependencies and Acknowledgments==<br />
<br />
Pre-v1.0 of PyMOL may not display objects created by this plugin properly. Use at your own risk.<br />
<br />
This plugin requires cctbx and numeric python.<br />
<br />
Code for unit cell and symmetry axis building is borrowed from scripts available at [http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/ http://pldserver1.biochem.queensu.ca/~rlc/work/pymol/]. This code has been modified for use in SuperSym.<br />
<br />
[[FindSurfaceResidues]] is utilized for some of SuperSym's graphics generation, with some modifications.<br />
<br />
==Source Files==<br />
<br />
File: SuperSym.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkSimpleDialog<br />
import tkMessageBox<br />
import tkColorChooser<br />
import sys<br />
from pymol import stored, cmd, selector<br />
import math<br />
from cctbx import sgtbx, uctbx<br />
import numpy as N<br />
from numpy.linalg import *<br />
import draw_cell as draw_cell<br />
import draw_symops_cctbx as sym_axes<br />
<br />
'''<br />
symDialog: Dialog generator and command issuer for generating symmetry partners<br />
<br />
This function is called by SuperSymMenu when any symmetry partner generating option is<br />
selected. It creates dialog windows and receives user input for symmetry generation parameters.<br />
<br />
@app -- identifies the GUI interface to build dialog boxes onto.<br />
@mode -- determines specific treatment of symmetry building command<br />
'''<br />
def symDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter desired prefix for these partners:', parent=app.root)<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate partners from:', parent=app.root)<br />
if (mode == 0): #make default symmetry set in cell [0,0,0]<br />
symset(prefix, object)<br />
if (mode == 1): #make symmetry set in custom cell<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x, y, z)<br />
if mode == 2: #make 2x2x2 block of symmetry sets<br />
for i in range(2):<br />
for j in range(2):<br />
for k in range(2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 3: #make 3x3x3 block of symmetry sets<br />
for i in range(-1,2):<br />
for j in range(-1,2):<br />
for k in range(-1,2):<br />
symset(prefix, object, i, j, k)<br />
if mode == 4: #select individual partners by operation and cell<br />
ops = get_operations(object)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9)", parent = app.root) <br />
opListStrings = opIndeces.split(",")<br />
opList = []<br />
for op in opListStrings:<br />
opList.append(int(op))<br />
cell = tkSimpleDialog.askstring('Cell',<br />
'Enter lattice cell coordinates separated by commas (ex:x,y,z):', parent = app.root)<br />
x,y,z = cell.split(',')<br />
x,y,z = int(x),int(y),int(z)<br />
symset(prefix, object, x,y,z, opList)<br />
<br />
'''<br />
colorDialog: Dialog generator for coloring commands<br />
<br />
This function colors sets of symmetry partners defined by the user in the<br />
dialog which it generates.<br />
<br />
@app -- identifies root menu calling this function<br />
@mode -- determines coloring scheme to execute<br />
'''<br />
def colorDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter the prefix of symmetry partners to color', parent = app.root)<br />
if mode == 0: #standard rainbow by symmetry operation<br />
colors = ["red", "orange", "yellow", "green", "blue", "purple",<br />
"salmon", "grey", "pink", "teal", "brown", "br0", "aquamarine", <br />
"deepolive", "dirtyviolet", "slate", "br4", "darksalmon", "br7",<br />
"chocolate", "firebrick", "brightorange"]<br />
for i in range(10):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + "0" + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
for i in range(10,20):<br />
try: #required because PyMOL inappropriately throws an exception<br />
#when the cmd.color() function colors no objects<br />
cmd.color(colors[i], prefix + str(i) + "*")<br />
except:<br />
pass #allows us to move on to next symmetry operator<br />
if mode == 1: #specify for each symmetry operation<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == "all":<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
for i in opList:<br />
tempColor = tkColorChooser.askcolor(title = "Color for " + opStringList[int(i)], parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
if mode == 2: #monochrome for a set of operations<br />
cmd.iterate_state(1, prefix + "*", "stored.tmpObject = model")<br />
ops = get_operations(stored.tmpObject)<br />
opString = ""<br />
for i in range(len(ops)):<br />
opString = opString + str(i) + " : " + ops[i] + "\n"<br />
opIndeces = tkSimpleDialog.askstring("Symmetry Operations", opString +<br />
"Enter numbers of desired operations separated by commas (ex:0,2,9) or all", parent = app.root) <br />
if opIndeces == 'all':<br />
opList = []<br />
for i in range(len(ops)):<br />
opList.append(i)<br />
else:<br />
opList = opIndeces.split(",")<br />
opStringList = opString.split("\n")<br />
tempColor = tkColorChooser.askcolor(parent = app.root)[0]<br />
rgb = []<br />
for value in tempColor:<br />
value = float(value)<br />
value = value/255<br />
rgb.append(value)<br />
cmd.set_color("tempColor", rgb)<br />
for i in opList:<br />
try:<br />
if int(i) < 10:<br />
cmd.color("tempColor", prefix + "0" + str(i) + "*")<br />
if int(i) > 9:<br />
cmd.color("tempColor", prefix + str(i) + "*")<br />
except:<br />
pass<br />
'''<br />
graphicsDialog: Dialog generator for graphics commands<br />
<br />
This function sets visual representations for sets of symmetry partners.<br />
<br />
@app -- identifies root menu<br />
@mode -- determines type of representation to show<br />
'''<br />
def graphicsDialog(app, mode):<br />
prefix = tkSimpleDialog.askstring('Prefix',<br />
'Enter prefix of symmetry partners to display', parent = app.root)<br />
cmd.hide("everything", prefix + "*")<br />
if mode == 0: # show lines<br />
cmd.show("lines", prefix + "*")<br />
if mode == 1: # show ribbon<br />
cmd.show("ribbon", prefix + "*")<br />
if mode == 2: # sphere surface<br />
objSel = prefix + "*"<br />
findSurfaceResidues(objSel, 3.5, "surface")<br />
cmd.set("sphere_scale", 1.8)<br />
cmd.show("spheres", "surface")<br />
if mode == 3: # regular surface<br />
cmd.show("surface", prefix + "*")<br />
<br />
'''<br />
cellDialog: dialog proxy for draw_cell<br />
<br />
This function generates a unit cell representation<br />
FUTURE IMPLEMENTATIONS: select which lattice coordinates to generate unit cell for<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate cell for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
draw_cell.draw_cell(object, 3.0)<br />
else:<br />
draw_cell.draw_cell(object)<br />
<br />
'''<br />
axesDialog: dialog proxy for draw_symops_cctbx<br />
<br />
This function generates one set of symmetry axes for a given object<br />
FUTURE IMPLEMENTATIONS: select individual axes to generate, attach to model for 3D printing,<br />
generate axes for multiple unit cells<br />
<br />
@app -- identifies root menu<br />
'''<br />
def axesDialog(app):<br />
object = tkSimpleDialog.askstring('Object',<br />
'Enter object to generate symmetry axes for:', parent = app.root)<br />
if tkMessageBox.askyesno('3D Printing', 'Going to print this model?', parent = app.root):<br />
sym_axes.draw_symops(object, 2.0)<br />
else:<br />
sym_axes.draw_symops(object)<br />
<br />
'''<br />
cellShiftInfo: displays info for using cell_shift hotkeys<br />
<br />
@app -- identifies root menu<br />
'''<br />
def cellShiftInfo(app):<br />
tkMessageBox.showinfo('Cell Shifting',<br />
"To shift a symmetry partner, simply click to select any part of it (select only one partner at a time). \n\n" +<br />
"Next, hold ALT and press the numpad key corresponding to the axis direction you\'d like to move. \n\n" +<br />
"Key assignments:\n" +<br />
"A (x) axis: down--4, up--6 \n" +<br />
"B (y) axis: down--2, up--8 \n" +<br />
"C (z) axis: down--1, up--5", parent = app.root)<br />
tkMessageBox.showwarning('Caution', 'Only attempt to shift symmetry partners created by SuperSym.'+<br />
'Attempting to shift any other object will result in errors.')<br />
<br />
def aboutInfo(app):<br />
tkMessageBox.showinfo('About',<br />
'SuperSym v1.0\nDeveloped by Stuart Ballard (srballard@wisc.edu)\nDepartment of Biochemistry\n'+<br />
'University of Wisconsin-Madison', parent = app.root)<br />
def helpInfo(app):<br />
tkMessageBox.showinfo('Help',<br />
'For documentation see http://pymolwiki.org/index.php/SuperSym', parent = app.root)<br />
<br />
'''<br />
symset: generates up to one full set of symmetry partners for a given object in a given lattice position<br />
<br />
1. Obtain all essential symmetry information from CCTBX. This includes the space group, unit cell parameters,<br />
and fractional coordinates corresponding to symmetry operations.<br />
2. Generate transformation matrices to translate coordinates from orthogonal to fractional, and back.<br />
3. <br />
'''<br />
def symset(prefix = "sym", object = -1, x=0,y=0,z=0, opList = []):<br />
if object == -1:<br />
object = cmd.get_names()[0]<br />
cell = [float(x),float(y),float(z)]<br />
view = cmd.get_view()<br />
cmd.show("lines", object)<br />
sgInfo = cmd.get_symmetry(object)<br />
raw_ops = []<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
if (len(opList) == 0):<br />
for i in range(len(raw_ops)):<br />
opList.append(i)<br />
a,b,c,alpha,beta,gamma = sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
for i in opList:<br />
try:<br />
stored.tmpOp = raw_ops[i]<br />
except:<br />
print "Bad symmetry partner numbers. Try again."<br />
quit()<br />
if i > 9:<br />
copy = prefix + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
else:<br />
copy = prefix + "0" + str(i) + "_" + str(x) + "_" + str(y) + "_" + str(z)<br />
cmd.copy(copy, object)<br />
#COPIES COORDINATES OF EACH ATOM TO CORRESPONDING ONE IN GIVEN SYMMETRY PARTNER<br />
cmd.alter_state(1, copy, "x,y,z = cmd.sym_partner([x,y,z], stored.tmpOp)")<br />
#MOVES SYMMETRY PARTNER TO PROPER LATTICE COORDINATES AND CORRECTS FOR NATIVE LATTICE POSITION ERROR<br />
stored.xSum,stored.ySum,stored.zSum = 0.0,0.0,0.0<br />
atoms = cmd.count_atoms(copy)<br />
cmd.iterate_state(1, copy, "stored.xSum = stored.xSum + x; stored.ySum = stored.ySum + y; stored.zSum = stored.zSum + z")<br />
xMean = (stored.xSum / atoms)<br />
yMean = (stored.ySum / atoms)<br />
zMean = (stored.zSum / atoms)<br />
xError, yError, zError = N.dot(N.array([xMean,yMean,zMean]), stored.ortToFrac)<br />
dX,dY,dZ = -math.floor(xError) + cell[0], -math.floor(yError) + cell[1], -math.floor(zError) + cell[2]<br />
cell_shift(copy,dX,dY,dZ, 0)<br />
cmd.hide("everything", object)<br />
cmd.set_view(view)<br />
<br />
def sym_partner(coords, op):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
op = op.replace("x", "(" + str(fracCoords[0]) + ")")<br />
op = op.replace("y", "(" + str(fracCoords[1]) + ")")<br />
op = op.replace("z", "(" + str(fracCoords[2]) + ")")<br />
op = op.split(",")<br />
for i in range(3):<br />
index = op[i].find("/")<br />
if index != -1:<br />
if len(op[i]) == index + 2:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1]))<br />
else:<br />
op[i] = op[i][0:index - 1] + str(float(op[i][index - 1]) / float(op[i][index + 1])) + op[i][index + 2:]<br />
op[i] = eval(op[i])<br />
return N.dot(N.array(op), stored.fracToOrt)<br />
<br />
def cell_shift_proxyX1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 1,0,0)<br />
def cell_shift_proxyX2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, -1,0,0)<br />
def cell_shift_proxyY1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,1,0)<br />
def cell_shift_proxyY2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,-1,0)<br />
def cell_shift_proxyZ1():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,1)<br />
def cell_shift_proxyZ2():<br />
cmd.iterate_state(1, "sele", "stored.tmpObject = model")<br />
cell_shift(stored.tmpObject, 0,0,-1)<br />
<br />
def cell_shift(object, dX, dY, dZ, rename = 1):<br />
if rename:<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
newName = oldPre + newX + newY + newZ<br />
#if cmd.get_names().find(newName) != -1:<br />
# print "Symmetry partner already exists in destination position!"<br />
# quit()<br />
cmd.set_name(object, newName)<br />
object = newName<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, object, "x,y,z = cmd.cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def shift_and_copy(object, dX, dY, dZ):<br />
oldName = object.split("_")<br />
oldPre = oldName[0]<br />
oldX = int(oldName[1])<br />
oldY = int(oldName[2])<br />
oldZ = int(oldName[3])<br />
newX = "_" + str(int(dX) + oldX)<br />
newY = "_" + str(int(dY) + oldY)<br />
newZ = "_" + str(int(dZ) + oldZ)<br />
copy = oldPre + newX + newY + newZ<br />
if cmd.count_atoms(copy) != 0:<br />
print "Symmetry partner already exists in destination position!"<br />
quit()<br />
cmd.copy(newName, object)<br />
stored.shift = [float(dX),float(dY),float(dZ)]<br />
stored.sgInfo = cmd.get_symmetry(object)<br />
a,b,c,alpha,beta,gamma = stored.sgInfo[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
stored.fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
stored.fracToOrt = stored.fracToOrt.transpose()<br />
stored.ortToFrac = inv(stored.fracToOrt)<br />
cmd.alter_state(1, newName, "x,y,z = cell_shift_helper([x,y,z],stored.shift)")<br />
<br />
<br />
def cell_shift_helper(coords, shift):<br />
fracCoords = N.dot(N.array(coords), stored.ortToFrac)<br />
for i in range(3):<br />
fracCoords[i] = fracCoords[i] + shift[i]<br />
coords = N.dot(N.array(fracCoords), stored.fracToOrt)<br />
return coords[0], coords[1], coords[2]<br />
<br />
def get_operations(object):<br />
raw_ops = []<br />
sgInfo = cmd.get_symmetry(object)<br />
for s in sgtbx.space_group_info(sgInfo[6]).group():<br />
raw_ops.append(str(s))<br />
return raw_ops <br />
<br />
def get_orthogonalization_matrix(object, quiet = 0):<br />
a,b,c,alpha,beta,gamma = cmd.get_symmetry(object)[0:6]<br />
ca = math.cos(math.radians(alpha))<br />
cb = math.cos(math.radians(beta))<br />
cg = math.cos(math.radians(gamma))<br />
sb = math.sin(math.radians(beta))<br />
sg = math.sin(math.radians(gamma))<br />
fracToOrt = N.array([[a, b * cg, c * cb], <br />
[0.0, b * sg, c * (ca - cb * cg) / sg], <br />
[0.0, 0.0, c * sb * math.sqrt(1.0 - ((cb * cg - ca) / (sb * sg))**2)]])<br />
if not quiet:<br />
print fracToOrt<br />
print inv(fracToOrt)<br />
return fracToOrt<br />
<br />
# -*- coding: utf-8 -*-<br />
# this function is borrowed from findSurfaceResidues script on PyMOL wiki<br />
def findSurfaceResidues(objSel="(all)", cutoff=2.5, selName = 0):<br />
"""<br />
findSurfaceResidues<br />
finds those residues on the surface of a protein<br />
that have at least 'cutoff' exposed A**2 surface area.<br />
<br />
PARAMS<br />
objSel (string)<br />
the object or selection in which to find<br />
exposed residues<br />
DEFAULT: (all)<br />
<br />
cutoff (float)<br />
your cutoff of what is exposed or not. <br />
DEFAULT: 2.5 Ang**2<br />
<br />
asSel (boolean)<br />
make a selection out of the residues found<br />
<br />
RETURNS<br />
(list: (chain, resv ) )<br />
A Python list of residue numbers corresponding<br />
to those residues w/more exposure than the cutoff.<br />
<br />
"""<br />
tmpObj="__tmp"<br />
cmd.create( tmpObj, objSel + " and polymer");<br />
cmd.set("dot_solvent");<br />
cmd.get_area(selection=tmpObj, load_b=1)<br />
<br />
# threshold on what one considers an "exposed" atom (in A**2):<br />
cmd.remove( tmpObj + " and b < " + str(cutoff) )<br />
<br />
stored.tmp_dict = {}<br />
cmd.iterate(tmpObj, "stored.tmp_dict[(chain,resv)]=1")<br />
exposed = stored.tmp_dict.keys()<br />
exposed.sort()<br />
<br />
cmd.select(selName, objSel + " in " + tmpObj )<br />
cmd.delete(tmpObj)<br />
<br />
return exposed<br />
</source><br />
File: SuperSymMenu.py<br />
<source lang="python"><br />
from Tkinter import *<br />
import tkFileDialog<br />
from pymol import cmd, selector<br />
from SuperSym import *<br />
<br />
def __init__(self):<br />
#MAIN<br />
self.menuBar.addmenu('SuperSym','SuperSym')<br />
#DEFAULT SET BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Default Symmetry Partner Set',<br />
label = 'Default Symmetry Partner Set', <br />
command = lambda s = self: symDialog(s, 0))<br />
#UNIT CELL BUILD<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Draw Unit Cell',<br />
label = 'Draw Unit Cell', <br />
command = lambda s = self: cellDialog(s))<br />
#SYM SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Build Symmetry Partners')<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [0,0,0] (default)', <br />
label = 'Cell [0,0,0] (default)', <br />
command = lambda s = self: symDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'Cell [x,y,z] (custom)',<br />
label = 'Cell [x,y,z] (custom)', <br />
command = lambda s = self: symDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '2x2x2 Block',<br />
label = '2x2x2 Block', <br />
command = lambda s = self: symDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', '3x3x3 Block',<br />
label = '3x3x3 Block', <br />
command = lambda s = self: symDialog(s, 3))<br />
<br />
self.menuBar.addmenuitem('Build Symmetry Partners', 'command', 'By Partner',<br />
label = 'By Partner', <br />
command = lambda s = self: symDialog(s, 4))<br />
#COLOR SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Coloring')<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Default Rainbow',<br />
label = 'Default Rainbow', <br />
command = lambda s = self: colorDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select color for each operation',<br />
label = 'Select color for each operation', <br />
command = lambda s = self: colorDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Coloring', 'command', 'Select one color for custom set of operations',<br />
label = 'Select one color for custom set of operations', <br />
command = lambda s = self: colorDialog(s, 2))<br />
#GRAPHICS SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Graphics')<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Lines',<br />
label = 'Lines', <br />
command = lambda s = self: graphicsDialog(s, 0))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Ribbon',<br />
label = 'Ribbon', <br />
command = lambda s = self: graphicsDialog(s, 1))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Sphere Surface (best for printing)',<br />
label = 'Sphere Surface (best for printing)', <br />
command = lambda s = self: graphicsDialog(s, 2))<br />
<br />
self.menuBar.addmenuitem('Graphics', 'command', 'Surface (high load render)',<br />
label = 'Surface (high load render)', <br />
command = lambda s = self: graphicsDialog(s, 3))<br />
#SYM AXES SUBMENU<br />
self.menuBar.addcascademenu('SuperSym', 'Symmetry Axes')<br />
<br />
self.menuBar.addmenuitem('Symmetry Axes', 'command', 'Build Axes',<br />
label = 'Build Axes', <br />
command = lambda s = self: axesDialog(s))<br />
#ADD OTHER SYMMETRY AXES OPTION HERE<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Move symmetry partners',<br />
label = 'Move symmetry partners',<br />
command = lambda s = self: cellShiftInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'About',<br />
label = 'About',<br />
command = lambda s = self: aboutInfo(s))<br />
self.menuBar.addmenuitem('SuperSym', 'command', 'Help',<br />
label = 'Help',<br />
command = lambda s = self: helpInfo(s))<br />
cmd.cell_shift = cell_shift<br />
cmd.get_operations = get_operations<br />
cmd.get_matrix = get_orthogonalization_matrix<br />
cmd.symset = symset<br />
cmd.sym_partner = sym_partner<br />
cmd.cell_shift_helper = cell_shift_helper<br />
cmd.set_key("ALT-6", cell_shift_proxyX1)<br />
cmd.set_key("ALT-4", cell_shift_proxyX2) <br />
cmd.set_key("ALT-8", cell_shift_proxyY1) <br />
cmd.set_key("ALT-2", cell_shift_proxyY2) <br />
cmd.set_key("ALT-5", cell_shift_proxyZ1) <br />
cmd.set_key("ALT-1", cell_shift_proxyZ2)<br />
</source><br />
File: draw_cell.py<br />
<source lang="python"><br />
#original code written by Robert Campbell<br />
#modified by Stuart Ballard<br />
from cctbx import uctbx, sgtbx<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
from pymol.vfont import plain<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_cell(obj,radius=1.0,mode=0):<br />
"""<br />
From pymol issue the "run draw_cell.py" command to load the script,<br />
then issue the "draw_cell(object,<optional radius>)" command <br />
to actually run it and create the cgo object showing the unit cell<br />
border for the space group specified by molecular object 'object'.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_cell.py<br />
draw_cell 1avv 0.5 (or draw_cell('1avv',.5))<br />
<br />
see also help(draw_cell_param) to draw the cell border for <br />
user-defined cell dimensions (i.e. not loaded from a pdb file)<br />
<br />
See also "help(draw_cell_param) to draw the cell border by<br />
specifying the unit cell parameters directly (i.e. not loaded from<br />
a pdb file).<br />
"""<br />
radius=float(radius)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_cell_param(cell_info[0:6],radius,mode)<br />
<br />
def draw_cell_param(cell_param_list,radius=1.0,mode=0):<br />
"""<br />
If you wish to draw the unit cell border for any cell without the<br />
need to load a pdb file, then do this:<br />
<br />
e.g. run draw_cell.py<br />
draw_cell_param((45.2,45.2,70.8,90.,90.,120.),0.5)<br />
<br />
to generate the cell border for this trigonal space group "p 31 2 1"<br />
with a radius of 0.5A. Labels for the origin, and A, B and C axes<br />
will appear as well. The perimeter of the cell is colored with the<br />
RGB components corresponding to the A,B,C components.<br />
"""<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
vert_000 = map(set_to_zero,U.orthogonalize((0.,0.,0)))<br />
vert_100 = map(set_to_zero,U.orthogonalize((1.,0.,0)))<br />
vert_010 = map(set_to_zero,U.orthogonalize((0.,1.,0)))<br />
vert_001 = map(set_to_zero,U.orthogonalize((0.,0.,1)))<br />
vert_110 = map(set_to_zero,U.orthogonalize((1.,1.,0)))<br />
vert_011 = map(set_to_zero,U.orthogonalize((0.,1.,1)))<br />
vert_101 = map(set_to_zero,U.orthogonalize((1.,0.,1)))<br />
vert_111 = map(set_to_zero,U.orthogonalize((1.,1.,1)))<br />
<br />
# vert_000 = map(None,U.orthogonalize((0.,0.,0)))<br />
# vert_100 = map(None,U.orthogonalize((1.,0.,0)))<br />
# vert_010 = map(None,U.orthogonalize((0.,1.,0)))<br />
# vert_001 = map(None,U.orthogonalize((0.,0.,1)))<br />
# vert_110 = map(None,U.orthogonalize((1.,1.,0)))<br />
# vert_011 = map(None,U.orthogonalize((0.,1.,1)))<br />
# vert_101 = map(None,U.orthogonalize((1.,0.,1)))<br />
# vert_111 = map(None,U.orthogonalize((1.,1.,1)))<br />
<br />
#print vert_000<br />
<br />
#CYLINDER = ['CYLINDER']<br />
#radius = [0.2]<br />
#print radius<br />
cell = [] <br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_100 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_010 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_000 + vert_001 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_100 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_110 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_010 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_101 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_001 + vert_011 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_110 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_101 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(CYLINDER)<br />
cell = cell + vert_011 + vert_111 + [radius] + [1,1,1] + [1,1,1]<br />
cell.append(SPHERE)<br />
cell = cell + vert_000 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_001 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_010 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_011 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_100 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_101 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_110 + [radius]<br />
cell.append(SPHERE)<br />
cell = cell + vert_111 + [radius]<br />
<br />
cmd.load_cgo(cell,"cell")<br />
#return cell<br />
<br />
if mode == 1:<br />
text = [COLOR, 1.0, 0.0, 1.0,]<br />
<br />
#wire_text(text,plain,[-5.,-5.,-1],'Origin',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
#wire_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]])<br />
<br />
cyl_text(text,plain,[-5.,-5.,-1],'Origin',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,1.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((1.05,0.0,0.0))),'A',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[1.0,0.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,1.05,0.0))),'B',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,1.0,0.0])<br />
cyl_text(text,plain,map(None,U.orthogonalize((0.0,0.0,1.05))),'C',0.20,axes=[[3.0,0.0,0.0],[0.0,3.0,0.0],[0.0,0.0,3.0]],color=[0.0,0.0,1.0])<br />
<br />
cmd.load_cgo(text,'text')<br />
<br />
cmd.extend("draw_cell",draw_cell)<br />
</source><br />
File: draw_symops_cctbx.py<br />
<source lang="python"><br />
#! /usr/bin/env python<br />
# Copyright (c) 2004 Robert L. Campbell<br />
<br />
from cctbx import uctbx, sgtbx<br />
#import string, math<br />
from pymol.cgo import *<br />
from pymol import cmd<br />
<br />
from all_axes_new import get_all_axes<br />
<br />
import numpy as N<br />
#import numarray as N<br />
<br />
print "Finished importing for draw_symops_cctbx.py"<br />
<br />
def set_to_zero(a):<br />
if abs(a) < 1e-10:<br />
a=0<br />
return a<br />
<br />
def draw_symbol(start,end,symb,color,radius=0.2):<br />
degtorad = N.pi/180.<br />
costhirty = N.cos(30.0*degtorad)<br />
sinthirty = N.sin(30.0*degtorad)<br />
symb_obj = []<br />
<br />
if symb == '2' or symb == '2^1':<br />
pass<br />
<br />
elif symb == '3' or symb == '3^1' or symb == '3^2':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, 0, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius*sinthirty, -radius*costhirty, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '4' or symb == '4^1' or symb == '4^2' or symb == '4^3':<br />
symb_obj = [ BEGIN, TRIANGLES, COLOR ] + color<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([start]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(VERTEX)<br />
symb_obj = symb_obj + (N.array([end]) + N.array([-radius, -radius, 0]))[0].tolist()<br />
symb_obj.append(END)<br />
<br />
elif symb == '6' or symb == '6^1' or symb == '6^2' or symb == '6^3' or symb == '6^4' or symb == '6^5':<br />
# hexagons still need to be created :)<br />
pass<br />
<br />
return symb_obj<br />
<br />
def draw_symops(obj,radius=0.2,extension=0):<br />
"""<br />
From pymol issue the "run draw_symops_cctbx.py" command to load the script,<br />
then issue the "draw_symops(object,<optional radius>,<optional extension>)" command <br />
to actually run it and create the cgo object.<br />
<br />
e.g. load 1avv.pdb<br />
run draw_symops_cctbx.py<br />
draw_symops 1avv, 0.5, .2 <br />
or draw_symops('1avv',.5,.2)<br />
or draw_symops 1avv, radius=.5, extension=.2<br />
<br />
The different axis types appear as different objects on the PyMOL menu so they can be turned<br />
on and off individually.<br />
<br />
See also help(draw_symops_param) to draw operators by specifying the space group <br />
and cell dimensions directly (i.e. not loaded from a pdb file)<br />
<br />
The 'extension' parameter is a fractional increase in the length of each symmetry<br />
operator axis drawn. i.e. a value of 0 is the default and a value of .2 increases<br />
the length by 20% at each end<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
cell_info=cmd.get_symmetry(obj)<br />
draw_symops_param(cell_info[0:6],cell_info[6],radius,extension)<br />
<br />
def draw_symops_param(cell_param_list,sg,radius=0.2,extension=0):<br />
"""<br />
If you wish to draw the symmetry operators for any cell without the need to load a<br />
pdb file, then do this:<br />
<br />
e.g. run draw_symops_cctbx.py<br />
draw_symops_param((45.2,45.2,70.8,90.,90.,120.),'p3121',0.5,0.1)<br />
<br />
to generate the symmetry operators for this trigonal space group "p 31 2 1"<br />
of radius .5 with 10% added as an extension at each end.<br />
"""<br />
radius=float(radius)<br />
extension=float(extension)<br />
<br />
U=uctbx.unit_cell((cell_param_list))<br />
<br />
#rotation axes<br />
# "2" "yellow",<br />
# "3" "orange",<br />
# "4" "mauve",<br />
# "6" "purple",<br />
<br />
#screw axes (all sub_1 axes are green)<br />
# "21" "green",<br />
# "31" "green",<br />
# "32" "lime",<br />
# "41" "green",<br />
# "42" "cyan",<br />
# "43" "iceblue",<br />
# "61" "green",<br />
# "62" "silver",<br />
# "63" "cyan",<br />
# "64" "iceblue",<br />
# "65" "blue",<br />
<br />
color = {<br />
"2" : [1.0, 1.0, 0.0],<br />
"3" : [1.0, 0.5, 0.0],<br />
"4" : [1.0, 0.5, 1.0],<br />
"6" : [1.0, 0.0, 1.0],<br />
"2^1" : [0.0, 1.0, 0.0],<br />
"3^1" : [0.0, 1.0, 0.0],<br />
"3^2" : [0.5, 1.0, 0.5],<br />
"4^1" : [0.0, 1.0, 0.0],<br />
"4^2" : [0.0, 1.0, 1.0],<br />
"4^3" : [0.5, 0.5, 1.0],<br />
"6^1" : [0.0, 1.0, 0.0],<br />
"6^2" : [0.8, 0.8, 0.8],<br />
"6^3" : [0.0, 1.0, 1.0],<br />
"6^4" : [0.5, 0.5, 1.0],<br />
"6^5" : [0.0, 0.0, 1.0],<br />
}<br />
<br />
sg = sg.upper()<br />
symop_axes = get_all_axes(sg,extension=extension)<br />
<br />
#CYLINDER = 'CYLINDER'<br />
ax_obj = {}<br />
#vert_obj = []<br />
<br />
#debug_out = open('debug.log','w')<br />
<br />
if symop_axes:<br />
for i in range(len(symop_axes)):<br />
#print symop_axes[i]<br />
start = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['start'])))<br />
end = map(set_to_zero,U.orthogonalize(map(None,symop_axes[i]['end'])))<br />
###############################################################################<br />
# Tried rounding off start and end values in order to understand why axes go <br />
# missing in the drawing, but seem to be present in the cgo. Doesn't help!<br />
# e.g. for space group 'p23' one of the 3-fold rotations is missing (0,0,0 -> x,-x,x)<br />
# changing one cell axis to something ever so slightly different recovers the axis<br />
# e.g. set cell to be (30.00001,30.,30.,90.,90.,90) and it works!<br />
# start = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['start']))<br />
# end = map(lambda x: round(x,3),U.orthogonalize(symop_axes[i]['end']))<br />
###############################################################################<br />
color_ax = color[symop_axes[i]['symb']]<br />
symb_ax = symop_axes[i]['symb']<br />
<br />
#print "axis: ",symb_ax, start, end<br />
if ax_obj.has_key(symb_ax):<br />
ax_obj[symb_ax].append(CYLINDER)<br />
else:<br />
ax_obj[symb_ax] = [CYLINDER]<br />
<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + start + end + [radius]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + color[symb_ax] + color[symb_ax]<br />
ax_obj[symb_ax] = ax_obj[symb_ax] + draw_symbol(start,end,symb_ax,color[symb_ax],radius*6.)<br />
<br />
# #######################################################################################<br />
# # Debugging output to try to understand why some axes go missing in the drawing.<br />
# # They don't appear to be missing from the cgo object, though!<br />
# for xxx in ax_obj[symb_ax]:<br />
# if xxx == 9.0:<br />
# #print "\n\n",xxx<br />
# xxx = "\n\n" + str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# else:<br />
# #print xxx<br />
# #xxx = "\n" + str(xxx) + " "<br />
# xxx = str(xxx) + " "<br />
# debug_out.write(xxx)<br />
# #print ax_obj[symb_ax]<br />
# debug_out.write("\n\n")<br />
# big_string = str(ax_obj)<br />
# debug_out.write(big_string)<br />
# # End of debugging output<br />
# #######################################################################################<br />
<br />
else:<br />
print "\nNo symmetry axes found for this space group: %s\n" % sg<br />
<br />
for key in ax_obj.keys():<br />
name=sg + "_" + key<br />
cmd.load_cgo(ax_obj[key],name)<br />
#debug_out.write("\n\n" + key + "\n" + str(ax_obj[key]))<br />
#return ax_obj<br />
<br />
cmd.extend("draw_symops",draw_symops)<br />
#cmd.extend("draw_symops_param",draw_symops_param)<br />
</source></div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5597
SuperSym
2009-08-31T21:22:50Z
<p>Srballard: </p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [http://sourceforge.net/projects/supersym http://sourceforge.net/projects/supersym]</div>
Srballard
https://wiki.pymol.org/index.php?title=SuperSym&diff=5596
SuperSym
2009-08-31T21:22:01Z
<p>Srballard: Created page with 'SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.…'</p>
<hr />
<div>SuperSym is a PyMOL plugin providing a large number of tools for visualization of space groups; unit cells; and symmetry axes, operators, and partners. Source code for version 1.0 is available from [http://sourceforge.net/projects/supersym]</div>
Srballard
https://wiki.pymol.org/index.php?title=User_talk:Srballard&diff=10774
User talk:Srballard
2009-08-27T17:35:41Z
<p>Srballard: </p>
<hr />
<div>Stuart's scratchpad:<br />
#Strut builder scripts<br />
#3D printing concerns<br />
#VRML export information<br />
#Arbitrary graphics--CGOs<br />
#SuperSym Crystallography Tools</div>
Srballard
https://wiki.pymol.org/index.php?title=User_talk:Srballard&diff=10773
User talk:Srballard
2009-08-07T18:20:23Z
<p>Srballard: </p>
<hr />
<div>Stuart's scratchpad:<br />
#Strut builder scripts<br />
#3D printing concerns<br />
#VRML export information<br />
#Arbitrary graphics--CGOs<br />
#EasyCryst Crystallography Tools</div>
Srballard
https://wiki.pymol.org/index.php?title=Delete&diff=7702
Delete
2009-07-08T18:41:57Z
<p>Srballard: </p>
<hr />
<div>===DESCRIPTION===<br />
'''delete''' removes objects or selections matching an expression ''name'', which can include wildcards.<br />
<br />
===USAGE===<br />
<source lang="python"><br />
delete name <br />
delete all # deletes all objects</source><br />
<br />
name = name of object or selection <br />
<br />
===PYMOL API===<br />
<source lang="python"><br />
cmd.delete(string name = object-or-selection-name )<br />
</source><br />
<br />
===SEE ALSO===<br />
[[Remove|Remove]]<br />
<br />
[[Category:Commands|Delete]]<br />
[[Category:Input Output Module|Delete]]</div>
Srballard
https://wiki.pymol.org/index.php?title=Delete&diff=7701
Delete
2009-07-08T18:41:27Z
<p>Srballard: </p>
<hr />
<div>===DESCRIPTION===<br />
'''delete''' removes objects or selections matching the expression name, which can include wildcards.<br />
<br />
===USAGE===<br />
<source lang="python"><br />
delete name <br />
delete all # deletes all objects</source><br />
<br />
name = name of object or selection <br />
<br />
===PYMOL API===<br />
<source lang="python"><br />
cmd.delete(string name = object-or-selection-name )<br />
</source><br />
<br />
===SEE ALSO===<br />
[[Remove|Remove]]<br />
<br />
[[Category:Commands|Delete]]<br />
[[Category:Input Output Module|Delete]]</div>
Srballard
https://wiki.pymol.org/index.php?title=User_talk:Srballard&diff=10772
User talk:Srballard
2009-07-08T17:39:02Z
<p>Srballard: </p>
<hr />
<div>Stuart's scratchpad:<br />
#Strut builder scripts<br />
#3D printing concerns<br />
#VRML export information<br />
#Arbitrary graphics--CGOs</div>
Srballard
https://wiki.pymol.org/index.php?title=User_talk:Srballard&diff=10771
User talk:Srballard
2009-07-08T17:35:25Z
<p>Srballard: </p>
<hr />
<div><nowiki>Stuart's scratchpad:<br />
Strut builder scripts<br />
3D printing concerns<br />
VRML export information<br />
Arbitrary graphics--CGOs</nowiki></div>
Srballard
https://wiki.pymol.org/index.php?title=User_talk:Srballard&diff=10770
User talk:Srballard
2009-07-08T17:34:47Z
<p>Srballard: </p>
<hr />
<div>Stuart's scratchpad:<br />
Strut builder scripts /n<br />
3D printing concerns \n<br />
VRML export information \n<br />
Arbitrary graphics--CGOs \n</div>
Srballard
https://wiki.pymol.org/index.php?title=User_talk:Srballard&diff=10769
User talk:Srballard
2009-07-08T17:34:37Z
<p>Srballard: </p>
<hr />
<div>Stuart's scratchpad:<br />
Strut builder scripts \n<br />
3D printing concerns \n<br />
VRML export information \n<br />
Arbitrary graphics--CGOs \n</div>
Srballard
https://wiki.pymol.org/index.php?title=User_talk:Srballard&diff=10768
User talk:Srballard
2009-07-08T17:34:10Z
<p>Srballard: Created page with 'Stuart's scratchpad: Strut builder scripts 3D printing concerns VRML export information Arbitrary graphics--CGOs'</p>
<hr />
<div>Stuart's scratchpad:<br />
Strut builder scripts<br />
3D printing concerns<br />
VRML export information<br />
Arbitrary graphics--CGOs</div>
Srballard
https://wiki.pymol.org/index.php?title=Selection_Algebra&diff=8775
Selection Algebra
2009-06-30T21:36:37Z
<p>Srballard: /* Selection Operator/Modifier Table */ Added "bycell" selection syntax</p>
<hr />
<div>==Selection Algebra==<br />
===Intro===<br />
Selections can be made more precise or inclusive by combining them with logical operators, including the boolean '''and''', '''or''', and '''not'''. The boolean '''and''' selects only those items that have both (or all) of the named properties, and the boolean '''or''' selects items that have either (or any) of them. Venn diagrams show that '''and ''' selects the areas of overlap, while '''or''' selects both areas. <br />
<br />
See [http://pymol.sourceforge.net/newman/user/S0220venn.jpg simple logic Venn diagram].<br />
<br />
===Selection Operator/Modifier Table===<br />
Selection operators and modifiers are listed below. The dummy variables ''s1'' and ''s2'' stand for selection-expressions such as "chain a" or "hydro."<br />
<br />
<TABLE BORDER="1"><br />
<TR><TH ALIGN="CENTER" WIDTH="100">Operator</TH><TH>Short form</TH><br />
<TH>Effect</TH><br />
</TR><br />
<TR><TD ALIGN="CENTER">not<I>s</I>1</TD><br />
<TD ALIGN="CENTER">!<I>s</I>1</TD><br />
<TD>Selects atoms that are not included in <I>s</I>1<br />
<pre>PyMOL> select sidechains, ! bb</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER"><I> s</I>1 and<I> s</I>2</TD><br />
<TD ALIGN="CENTER"><I> s</I>1 &amp;<I> s</I>2</TD><br />
<TD>Selects atoms included in both<I> s</I>1 and<I> s</I>2<br />
<pre>PyMOL> select far_bb, bb &amp;farfrm_ten</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER"><I> s</I>1 or<I> s</I>2</TD><br />
<TD ALIGN="CENTER"><I> s</I>1 |<I> s</I>2</TD><TD>Selects atoms included in either<I> s</I>1 or<I> s</I>2<br />
<pre>PyMOL> select all_prot, bb | sidechain</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER"><I> s</I>1 in<I> s</I>2</TD><br />
<TD ALIGN="CENTER"><I> s</I>1 in<I> s</I>2</TD><TD>Selects atoms in<I> s</I>1 whose<br />
identifiers name, resi, resn, chain and segi <strong><u>all</u></strong> match atoms in<I> s</I>2<br />
<pre>PyMOL> select same_atms, pept in prot</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER"><I> s</I>1 like<I> s</I>2</TD><TD ALIGN="CENTER"><I> s</I>1 l.<I> s</I>2</TD><TD>Selects atoms in<I> s</I>1 whose identifiers name and resi match atoms in<I> s</I>2<br />
<pre>PyMOL> select similar_atms, pept like prot</pre><br />
<br />
</TD></TR><br />
<TR><TD ALIGN="CENTER"><I> s</I>1 gap<I> X</I></TD><br />
<TD ALIGN="CENTER"><I> s</I>1 gap<I> X</I></TD><TD>Selects all atoms whose van der Waals radii are separated from the van der Waals radii of<I> s</I>1 by a minimum of<I> X</I> Angstroms.<br />
<pre>PyMOL> select farfrm_ten, resi 10 gap 5</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER"><I> s</I>1 around<I> X</I></TD><br />
<TD ALIGN="CENTER"><I> s</I>1 a.<I> X</I></TD><TD>Selects atoms with centers within<I> X</I> Angstroms of the center of any atom in<I> s</I>1<br />
<pre>PyMOL> select near_ten, resi 10 around 5</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER"><I> s</I>1 expand<I> X</I><br />
</TD><TD ALIGN="CENTER"><I> s</I>1 e.<I> X</I></TD><TD>Expands<I> s</I>1 by all atoms within<I> X</I> Angstroms of the center of any atom in<I> s</I>1<br />
<pre>PyMOL> select near_ten_x, near10 expand 3</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER">&nbsp;<I> s</I>1 within X of<I> s</I>2&nbsp;</TD><br />
<TD ALIGN="CENTER"><I> s</I>1 w. X of<I> s</I>2&nbsp;</TD><TD>Selects atoms in<I> s</I>1 that are within X Angstroms of the<I> s</I>2<br />
<pre>PyMOL> select bbnearten, bb w. 4 of resi 10</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER">byres<I> s</I>1</TD><br />
<TD ALIGN="CENTER">br.<I> s</I>1</TD><TD>Expands selection to complete residues<br />
<pre>PyMOL> select complete_res, br. bbnear10</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER">bymolecule<I> s</I>1</TD><br />
<TD ALIGN="CENTER">bm.<I> s</I>1</TD><TD>Expands selection to complete molecules<br />
<pre>PyMOL> select complete_res, bm. bbnear10</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER">byfragment<I> s</I>1</TD><br />
<TD ALIGN="CENTER">bf.<I> s</I>1</TD><TD>Expands selection to complete fragments<br />
<pre>PyMOL> select complete_res, bf. bbnear10</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER">bysegment<I> s</I>1</TD><br />
<TD ALIGN="CENTER">bs.<I> s</I>1</TD><TD>Expands selection to complete segments<br />
<pre>PyMOL> select complete_res, bs. bbnear10</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER">byobject<I> s</I>1</TD><br />
<TD ALIGN="CENTER">bo.<I> s</I>1</TD><TD>Expands selection to complete objects><br />
<pre>PyMOL> select near_obj, bo. near_res</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER">bycell<I> s</I>1</TD><br />
<TD ALIGN="CENTER">???<I> s</I>1</TD><TD>Expands selection to unit cell><br />
<pre>PyMOL> select complete_cell, bycell orig_res</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER">neighbor<I> s</I>1</TD><br />
<TD ALIGN="CENTER">nbr.<I> s</I>1</TD><TD>Selects atoms directly bonded to<I> s</I>1<br />
<pre>PyMOL> select vicinos, neighbor resi 10</pre><br />
</TD></TR><br />
<TR><TD ALIGN="CENTER"><I> s</I>1 extend<I> X</I><br />
</TD><TD ALIGN="CENTER"><I> s</I>1 ?<I> X</I></TD><TD>Extends<I> s</I>1 by<I> X</I> bonds connected to atom in<I> s</I>1<br />
<pre>PyMOL> select connect_x, near10 extend 3</pre><br />
</TD></TR><br />
</TABLE><br />
<br />
===Examples===<br />
Logical selections can be combined. For example, you might select atoms that are part of chain a, but not residue number 125:<br />
<source lang="python"><br />
# selects atoms that are part of chain a, but not residue number 125.<br />
PyMOL> select chain a and (not resi 125)<br />
<br />
# The following two selections are equivalent, <br />
PyMOL> select (name cb or name cg1 or name cg2) and chain A<br />
<br />
# select c-beta's, c-gamma-1's and c-gamma-2's <br />
# that are in chain A.<br />
PyMOL> select name cb+cg1+cg2 and chain A <br />
</source><br />
<br />
Like the results of groups of arithmetic operations, the results of groups of logical operations depend on which operation is performed first. They have an order of precedence. To ensure that the operations are performed in the order you have in mind, use parentheses:<br />
<br />
<source lang="python">byres ((chain a or (chain b and (not resi 125))) around 5)</source><br />
<br />
PyMOL will expand its logical selection out from the innermost parentheses.<br />
<br />
<br />
[[Category:Selector Quick Reference]]<br />
[[Category:Selecting|Selection Algebra]]</div>
Srballard
https://wiki.pymol.org/index.php?title=Count_Atoms&diff=7651
Count Atoms
2009-06-02T19:22:07Z
<p>Srballard: /* PYMOL API */</p>
<hr />
<div>===DESCRIPTION===<br />
'''count_atoms''' returns a count of atoms in a selection.<br />
<br />
===USAGE===<br />
<source lang="python"><br />
count_atoms (selection)<br />
</source><br />
<br />
===PYMOL API===<br />
<source lang="python"><br />
cmd.count_atoms(string selection) <br />
</source><br />
<br />
[[Category:Commands|count_atoms]]</div>
Srballard