File: representation.py

package info (click to toggle)
python-ihm 2.7-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 3,368 kB
  • sloc: python: 30,422; ansic: 5,990; sh: 24; makefile: 20
file content (181 lines) | stat: -rw-r--r-- 7,074 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
"""Classes for handling representation of the system during modeling.
"""


def _starting_model_report(seg):
    if seg.starting_model:
        if hasattr(seg.starting_model, '_id'):
            return " (from starting model %s)" % seg.starting_model._id
        else:
            return " (from starting model)"
    else:
        return ""


class Segment:
    """Base class for part of a :class:`Representation`.
       See :class:`AtomicSegment`, :class:`ResidueSegment`,
       :class:`MultiResidueSegment`, and :class:`FeatureSegment`.
    """
    def _get_report(self):
        """Return a textual description of the object, used by
           :meth:`ihm.System.report`"""
        return str(self)


class AtomicSegment(Segment):
    """Part of the system modeled atomistically, stored in
       a :class:`Representation`.

       :param asym_unit: The asymmetric unit (or part of one) that
              this segment represents.
       :type asym_unit: :class:`~ihm.AsymUnit` or :class:`~ihm.AsymUnitRange`
       :param bool rigid: Whether internal coordinates of the segment were
              fixed during modeling.
       :param starting_model: initial coordinates used for the segment
              (or None).
       :type starting_model: :class:`~ihm.startmodel.StartingModel`
       :param str description: Additional text describing this segment.
    """

    primitive = 'atomistic'
    count = None
    granularity = 'by-atom'

    def _get_report(self):
        asym = self.asym_unit
        return ("%s %d-%d as %s atoms%s"
                % (asym.details, asym.seq_id_range[0], asym.seq_id_range[1],
                   "rigid" if self.rigid else "flexible",
                   _starting_model_report(self)))

    def __init__(self, asym_unit, rigid, starting_model=None,
                 description=None):
        self.asym_unit = asym_unit
        self.starting_model, self.rigid = starting_model, rigid
        self.description = description


class ResidueSegment(Segment):
    """Part of the system modeled as a set of residues, stored in
       a :class:`Representation`.

       :param asym_unit: The asymmetric unit (or part of one) that
              this segment represents.
       :type asym_unit: :class:`~ihm.AsymUnit` or :class:`~ihm.AsymUnitRange`
       :param bool rigid: Whether internal coordinates of the segment were
              fixed during modeling.
       :param str primitive: The type of object used to represent this segment
              (sphere/gaussian/other).
       :param starting_model: initial coordinates used for the segment
              (or None).
       :type starting_model: :class:`~ihm.startmodel.StartingModel`
       :param str description: Additional text describing this segment.
    """

    count = None
    granularity = 'by-residue'

    def _get_report(self):
        asym = self.asym_unit
        return ("%s %d-%d as %s residues%s"
                % (asym.details, asym.seq_id_range[0], asym.seq_id_range[1],
                   "rigid" if self.rigid else "flexible",
                   _starting_model_report(self)))

    def __init__(self, asym_unit, rigid, primitive, starting_model=None,
                 description=None):
        self.asym_unit = asym_unit
        self.primitive = primitive
        self.starting_model, self.rigid = starting_model, rigid
        self.description = description


class MultiResidueSegment(Segment):
    """Part of the system modeled as a single object representing a
       range of residues, stored in a :class:`Representation`.

       :param asym_unit: The asymmetric unit (or part of one) that
              this segment represents.
       :type asym_unit: :class:`~ihm.AsymUnit` or :class:`~ihm.AsymUnitRange`
       :param bool rigid: Whether internal coordinates of the segment were
              fixed during modeling.
       :param str primitive: The type of object used to represent this segment
              (sphere/gaussian/other).
       :param starting_model: initial coordinates used for the segment
              (or None).
       :type starting_model: :class:`~ihm.startmodel.StartingModel`
       :param str description: Additional text describing this segment.
    """

    count = None
    granularity = 'multi-residue'

    def __init__(self, asym_unit, rigid, primitive, starting_model=None,
                 description=None):
        self.asym_unit = asym_unit
        self.primitive = primitive
        self.starting_model, self.rigid = starting_model, rigid
        self.description = description


class FeatureSegment(Segment):
    """Part of the system modeled as a number of geometric features,
       stored in a :class:`Representation`.

       :param asym_unit: The asymmetric unit (or part of one) that
              this segment represents.
       :type asym_unit: :class:`~ihm.AsymUnit` or :class:`~ihm.AsymUnitRange`
       :param bool rigid: Whether internal coordinates of the segment were
              fixed during modeling.
       :param str primitive: The type of object used to represent this segment
              (sphere/gaussian/other).
       :param int count: The number of objects used to represent this segment.
       :param starting_model: initial coordinates used for the segment
              (or None).
       :type starting_model: :class:`~ihm.startmodel.StartingModel`
       :param str description: Additional text describing this segment.
    """

    granularity = 'by-feature'

    def _get_report(self):
        asym = self.asym_unit
        return ("%s %d-%d as %d %s feature%s (%s)%s"
                % (asym.details, asym.seq_id_range[0], asym.seq_id_range[1],
                   self.count, "rigid" if self.rigid else "flexible",
                   "" if self.count == 1 else "s", self.primitive,
                   _starting_model_report(self)))

    def __init__(self, asym_unit, rigid, primitive, count, starting_model=None,
                 description=None):
        self.asym_unit = asym_unit
        self.primitive, self.count = primitive, count
        self.starting_model, self.rigid = starting_model, rigid
        self.description = description


class Representation(list):
    """Part of the system modeled as a set of geometric objects, such as
       spheres or atoms. This is implemented as a simple list of
       :class:`Segment` objects.

       :param sequence elements: Initial set of segments.
       :param str name: A short descriptive name.
       :param str details: A longer description of the representation.

       Typically a Representation is assigned to a
       :class:`~ihm.model.Model`. See also
       :attr:`ihm.System.orphan_representations`.

       Multiple representations of the same system are possible (multi-scale).
    """

    # For backwards compatibility with earlier versions of this class which
    # didn't specify name/details
    name = details = None

    # todo: use set rather than list?
    def __init__(self, elements=(), name=None, details=None):
        super().__init__(elements)
        self.name, self.details = name, details