Package lib :: Package structure :: Package internal :: Module displacements
[hide private]
[frames] | no frames]

Source Code for Module lib.structure.internal.displacements

  1  ############################################################################### 
  2  #                                                                             # 
  3  # Copyright (C) 2008-2014 Edward d'Auvergne                                   # 
  4  #                                                                             # 
  5  # This file is part of the program relax (http://www.nmr-relax.com).          # 
  6  #                                                                             # 
  7  # This program is free software: you can redistribute it and/or modify        # 
  8  # it under the terms of the GNU General Public License as published by        # 
  9  # the Free Software Foundation, either version 3 of the License, or           # 
 10  # (at your option) any later version.                                         # 
 11  #                                                                             # 
 12  # This program is distributed in the hope that it will be useful,             # 
 13  # but WITHOUT ANY WARRANTY; without even the implied warranty of              # 
 14  # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the               # 
 15  # GNU General Public License for more details.                                # 
 16  #                                                                             # 
 17  # You should have received a copy of the GNU General Public License           # 
 18  # along with this program.  If not, see <http://www.gnu.org/licenses/>.       # 
 19  #                                                                             # 
 20  ############################################################################### 
 21   
 22  # Module docstring. 
 23  """The objects representing displacement information in the internal structural object.""" 
 24   
 25  # relax module import. 
 26  from lib.structure.superimpose import kabsch 
 27  from lib.structure.internal.models import ModelContainer 
 28  from lib.xml import object_to_xml, xml_to_object 
 29   
 30   
31 -class Displacements:
32 """A special object for representing rotational and translational displacements between models.""" 33
34 - def __init__(self):
35 """Initialise the storage objects.""" 36 37 # The displacement structures. 38 self._translation_vector = {} 39 self._translation_distance = {} 40 self._rotation_matrix = {} 41 self._rotation_axis = {} 42 self._rotation_angle = {}
43 44
45 - def _calculate(self, model_from=None, model_to=None, coord_from=None, coord_to=None, centroid=None):
46 """Calculate the rotational and translational displacements using the given coordinate sets. 47 48 This uses the U{Kabsch algorithm<http://en.wikipedia.org/wiki/Kabsch_algorithm>}. 49 50 51 @keyword model_from: The model number of the starting structure. 52 @type model_from: int 53 @keyword model_to: The model number of the ending structure. 54 @type model_to: int 55 @keyword coord_from: The list of atomic coordinates for the starting structure. 56 @type coord_from: numpy rank-2, Nx3 array 57 @keyword coord_to: The list of atomic coordinates for the ending structure. 58 @type coord_to: numpy rank-2, Nx3 array 59 @keyword centroid: An alternative position of the centroid, used for studying pivoted systems. 60 @type centroid: list of float or numpy rank-1, 3D array 61 """ 62 63 # Initialise structures if necessary. 64 if not model_from in self._translation_vector: 65 self._translation_vector[model_from] = {} 66 if not model_from in self._translation_distance: 67 self._translation_distance[model_from] = {} 68 if not model_from in self._rotation_matrix: 69 self._rotation_matrix[model_from] = {} 70 if not model_from in self._rotation_axis: 71 self._rotation_axis[model_from] = {} 72 if not model_from in self._rotation_angle: 73 self._rotation_angle[model_from] = {} 74 75 # The Kabsch algorithm. 76 trans_vect, trans_dist, R, axis, angle, pivot = kabsch(name_from='model %s'%model_from, name_to='model %s'%model_to, coord_from=coord_from, coord_to=coord_to, centroid=centroid) 77 78 # Store the data. 79 self._translation_vector[model_from][model_to] = trans_vect 80 self._translation_distance[model_from][model_to] = trans_dist 81 self._rotation_matrix[model_from][model_to] = R 82 self._rotation_axis[model_from][model_to] = axis 83 self._rotation_angle[model_from][model_to] = angle
84 85
86 - def from_xml(self, str_node, dir=None, file_version=1):
87 """Recreate the structural object from the XML structural object node. 88 89 @param str_node: The structural object XML node. 90 @type str_node: xml.dom.minicompat.Element instance 91 @keyword dir: The name of the directory containing the results file. 92 @type dir: str 93 @keyword file_version: The relax XML version of the XML file. 94 @type file_version: int 95 """ 96 97 # Get the pairs of displacements. 98 pair_nodes = str_node.getElementsByTagName('pair') 99 100 # Loop over the pairs. 101 for pair_node in pair_nodes: 102 # Get the two models. 103 model_from = int(pair_node.getAttribute('model_from')) 104 model_to = int(pair_node.getAttribute('model_to')) 105 106 # Initialise structures if necessary. 107 if not model_from in self._translation_vector: 108 self._translation_vector[model_from] = {} 109 if not model_from in self._translation_distance: 110 self._translation_distance[model_from] = {} 111 if not model_from in self._rotation_matrix: 112 self._rotation_matrix[model_from] = {} 113 if not model_from in self._rotation_axis: 114 self._rotation_axis[model_from] = {} 115 if not model_from in self._rotation_angle: 116 self._rotation_angle[model_from] = {} 117 118 # A temporary container to place the Python objects into. 119 cont = ModelContainer() 120 121 # Recreate the Python objects. 122 xml_to_object(pair_node, cont, file_version=file_version) 123 124 # Repackage the data. 125 for name in ['translation_vector', 'translation_distance', 'rotation_matrix', 'rotation_axis', 'rotation_angle']: 126 # The objects. 127 obj = getattr(self, '_'+name) 128 obj_temp = getattr(cont, name) 129 130 # Store. 131 obj[model_from][model_to] = obj_temp
132 133
134 - def to_xml(self, doc, element):
135 """Create XML elements for each model. 136 137 @param doc: The XML document object. 138 @type doc: xml.dom.minidom.Document instance 139 @param element: The element to add the displacement XML elements to. 140 @type element: XML element object 141 """ 142 143 # Loop over the starting models. 144 start_models = sorted(self._translation_vector.keys()) 145 for model_from in start_models: 146 # Loop over the ending models. 147 end_models = sorted(self._translation_vector[model_from].keys()) 148 for model_to in end_models: 149 # Create an XML element for each pair. 150 pair_element = doc.createElement('pair') 151 element.appendChild(pair_element) 152 153 # Set the attributes. 154 pair_element.setAttribute('desc', 'The displacement from model %s to model %s' % (model_from, model_to)) 155 pair_element.setAttribute('model_from', str(model_from)) 156 pair_element.setAttribute('model_to', str(model_to)) 157 158 # The objects to store. 159 obj_names = [ 160 '_translation_vector', 161 '_translation_distance', 162 '_rotation_matrix', 163 '_rotation_axis', 164 '_rotation_angle' 165 ] 166 167 # Store the objects. 168 for i in range(len(obj_names)): 169 # Create a new element for this object, and add it to the main element. 170 sub_elem = doc.createElement(obj_names[i][1:]) 171 pair_element.appendChild(sub_elem) 172 173 # Get the sub-object. 174 subobj = getattr(self, obj_names[i])[model_from][model_to] 175 176 # Add the value to the sub element. 177 object_to_xml(doc, sub_elem, value=subobj)
178