Example #1
0
    def horseshoe_segment(self, side_length, semicircle_length, spacing,
                          start_index):
        '''
        Make a horseshoe segment with two sides each with side_length nucleotides
        parallel the y axis, curved top has semicircle_length nucleotides, spacing of
        nucleotides is spacing.  Starting nucleotide index is start_index.
        '''
        from chimerax.geometry import translation, rotation
        c = {}
        # Horseshoe side going up in y.
        ns = side_length
        b = start_index
        ls = spacing
        for i in range(ns):
            c[b + i] = translation((0, i * ls, 0)) * rotation((0, 0, 1), 90)
        from math import pi, cos, sin
        nc = semicircle_length
        r = 0.5 * ls / sin(0.5 * pi / (nc - 1))
        for i in range(nc):
            a = i * pi / (nc - 1)
            a_deg = a * 180 / pi
            ca, sa = cos(a), sin(a)
            # Horeshoe curve
            c[b + ns + i] = translation(
                (r * (1 - ca), r * sa + ns * ls, 0)) * rotation(
                    (0, 0, 1), 90 - a_deg)
        # Horseshoe side going down in y.
        for i in range(ns):
            c[b + ns + nc + i] = translation(
                (2 * r, (ns - 1 - i) * ls, 0)) * rotation((0, 0, 1), -90)

        return Segment(c, 2 * r, spacing)
Example #2
0
def ring_arrow(major_radius, minor_radius, circle_segments, ring_segments,
               head_length, head_radius):
    import numpy
    #Find the starting angle from the length of the arrow head
    from math import asin, pi, degrees
    starting_angle = 2 * asin(head_length / (2 * major_radius))
    vr, nr, tr = split_torus_geometry(major_radius, minor_radius,
                                      circle_segments, ring_segments,
                                      starting_angle * 0.8, 3 * pi / 2)
    vh, nh, th = cone_geometry(head_radius, head_length, circle_segments)
    from chimerax.geometry import rotation
    # Rotate the cone
    move_dir = numpy.array(((major_radius, 0, -head_length), ), numpy.double)
    r1 = rotation((1, 0, 0), -90)
    r1.transform_points(vh, in_place=True)
    r1.transform_points(move_dir, in_place=True)
    r2 = rotation((0, 0, 1), degrees(starting_angle))
    r2.transform_points(vh, in_place=True)
    r2.transform_points(move_dir, in_place=True)
    # ... and move it into position
    vh += move_dir

    from numpy import concatenate
    v = concatenate((vr, vh))
    n = concatenate((nr, nh))
    t = concatenate((tr, th + len(vr)))

    return v, n, t
Example #3
0
 def _wobble_position(self, f):
     amax = 0.5 * self._full_angle
     from math import pi, sin
     a = sin(2 * pi * f) * amax
     wa = sin(4 * pi * f) * amax * self._wobble_aspect
     from chimerax.geometry import rotation
     r = rotation(self._axis, a, self._center)
     rw = rotation(self._wobble_axis, wa, self._center)
     return rw * r
Example #4
0
 def _set_pointer_shape(self, cross_diameter=1.0, stick_diameter=0.1):
     from chimerax.surface import cylinder_geometry, combine_geometry_vnt
     cva, cna, cta = cylinder_geometry(radius=0.5 * stick_diameter,
                                       height=cross_diameter)
     from chimerax.geometry import rotation
     rx90, ry90 = rotation((1, 0, 0), 90), rotation((0, 1, 0), 90)
     vax, nax = ry90 * cva, ry90.transform_vectors(cna)
     vay, nay = rx90 * cva, rx90.transform_vectors(cna)
     geom = [(vax, nax, cta), (vay, nay, cta)]
     if self._emulate == 'vr':
         geom.append((cva, cna, cta))  # z-axis
     va, na, ta = combine_geometry_vnt(geom)
     self.set_geometry(va, na, ta)
Example #5
0
def correct_o_position(res, psi):
    n, ca, c, o = [res.find_atom(name) for name in ['N', 'CA', 'C', 'O']]
    from chimerax.geometry import rotation, dihedral
    d = dihedral(*[a.coord for a in (n, ca, c, o)])
    r = rotation(c.coord - ca.coord, psi + 180 - d, center=c.coord)
    from chimerax.atomic import Atoms
    Atoms([o]).transform(r)
Example #6
0
def angle_pos(atom_pos, bond_pos, bond_length, degrees, coplanar=None):
    if coplanar is not None and len(coplanar) > 0:
        # may have one or two coplanar positions specified,
        # if two, compute both resultant positions and average
        # (the up vector has to be negated for the second one)
        xforms = []
        if len(coplanar) > 2:
            raise ValueError("More than 2 coplanar positions specified!")
        for cpos in coplanar:
            up = cpos - atom_pos
            if xforms:
                up = tinyarray.negative(up)
            # lookAt puts ref point opposite that of zAlign, so
            # also rotate 180 degrees around y axis
            xform = rotation(
                (0.0, 1.0, 0.0), 180.0) * look_at(atom_pos, bond_pos, up)
            xforms.append(xform)

    else:
        xforms = [z_align(atom_pos, bond_pos)]
    points = []
    for xform in xforms:
        radians = pi * degrees / 180.0
        angle = tinyarray.array(
            [0.0, bond_length * sin(radians), bond_length * cos(radians)])
        points.append(xform.inverse() * angle)

    if len(points) > 1:
        midpoint = points[0] + (points[1] - points[0]) / 2.0
        v = midpoint - atom_pos
        v = v * bond_length / norm(v)
        return atom_pos + v

    return tinyarray.array(points[0])
Example #7
0
    def helix_segment(self, base_index, count, spacing, rise):
        '''
        Lay out a single turn helix on x axis.
        Radius is calculated to fit the specified number of nucleotides.
        '''
        # Choose radius so one helix turn has desired length.
        # Helix arc length = s, radius = r, rise = h: s**2 = r**2 + (h/(2*pi))**2
        length = spacing * count
        from math import sqrt, pi
        radius = sqrt((length / (2 * pi))**2 - (rise / (2 * pi))**2)

        # Compute screw motion to advance along helix
        angle = 2 * pi / count
        angle_deg = angle * 180 / pi
        from chimerax.geometry import translation, rotation, vector_rotation, Place
        step = translation((rise / count, 0, 0)) * rotation(
            (1, 0, 0), angle_deg, center=(0, radius, 0))

        # Compute first nucleotide so P-P lies on helix.
        orient = vector_rotation((1, 0, 0), step * (0, 0, 0))

        # Place nucleotides on helix.
        place = {}
        p = Place()
        for i in range(count):
            place[base_index + i] = p * orient
            p = step * p

        return Segment(place, rise, pad=0)
Example #8
0
  def _rotation_changed(self):

    v = self._map
    if v is None:
        return

    data = v.data

    if data.rotation == ((1,0,0),(0,1,0),(0,0,1)):
      axis, angle = (0,0,1), 0
    else:
      from chimerax.geometry import Place
      axis, angle = Place(axes = data.rotation).rotation_axis_and_angle()

    rax = self._rotation_axis.value
    from .volume_viewer import vector_value
    naxis = vector_value(rax, axis)
    if naxis is None:
      self._status('Invalid rotation axis.  Must be 3 numbers separated by spaces.')
      return
    if tuple(naxis) == (0,0,0):
      self._status('Rotation axis must be non-zero')
      return

    nangle = self._rotation_angle.value

    if tuple(naxis) != tuple(axis) or nangle != angle:
      from chimerax.geometry import rotation
      r = rotation(naxis, nangle)
      data.set_rotation(r.matrix[:,:3])
      # Have to change xyz origin for index origin to remain the same.
      self._origin_changed()
      self._redraw_regions(data)
      self._status('Set rotation axis %s, angle %.3g' % (rax, nangle))
def _transform_schematic(session, transform, center, from_rgba, to_rgba,
                         length, width, thickness):

    axis, rot_center, angle_deg, shift = transform.axis_center_angle_shift()

    # Align rot_center at same position along axis as center.
    from chimerax.geometry import inner_product
    rot_center += inner_product(center - rot_center, axis) * axis
    width_axis = center - rot_center
    varray, narray, tarray = _axis_square(axis, rot_center, width_axis, length,
                                          width, thickness)

    from chimerax.core.models import Model, Surface

    s1 = Surface('slab 1', session)
    s1.set_geometry(varray, narray, tarray)
    s1.color = from_rgba

    s2 = Surface('slab 2', session)
    from chimerax.geometry import rotation, translation
    rot2 = translation(shift * axis) * rotation(
        axis, angle_deg, center=rot_center)
    varray2 = rot2 * varray
    narray2 = rot2.transform_vectors(narray)
    s2.set_geometry(varray2, narray2, tarray)
    s2.color = to_rgba

    m = Model('transform schematic', session)
    m.add([s1, s2])

    return m
Example #10
0
 def clip_rotate(self, axis, angle):
     v = self.view
     scene_axis = v.camera.position.transform_vector(axis)
     from chimerax.geometry import rotation
     r = rotation(scene_axis, angle, v.center_of_rotation)
     for p in self._planes():
         p.normal = r.transform_vector(p.normal)
         p.plane_point = r * p.plane_point
Example #11
0
 def _extend_ends(self, centers, frac):
     n = len(centers)
     if self.curved:
         tc = self.center  # Torus center
         r0,r1 = centers[0] - tc, centers[-1] - tc # radial vectors from center of torus.
         from chimerax.geometry import angle, rotation
         a = frac * angle(r0,r1) / (n-1)
         c0 = tc + rotation(self.axis, -a) * r0
         c1 = tc + rotation(self.axis, a) * r1
     else:
         e = frac/(n-1) * (centers[-1] - centers[0])
         c0 = centers[0] - e
         c1 = centers[-1] + e
     n = len(centers)
     from numpy import concatenate
     ecenters = concatenate((c0.reshape(1,3), centers, c1.reshape(1,3)))
     return ecenters
Example #12
0
 def parse(text, session):
     from chimerax.core.commands import FloatsArg
     aa, text, rest = FloatsArg.parse(text, session)
     if len(aa) != 4:
         raise AnnotationError('Axis-angle must be 4 comma-separated floats, got %d from %s'
                               % (len(aa), text))
     from chimerax.geometry import rotation
     v = rotation(aa[:3], aa[3])
     return v, text, rest
Example #13
0
 def _exclamation_mark(self):
     v, n, t = exclamation_mark(radius=0.1, height=0.5, nc = 8)
     flip = rotation((1,0,0), 180)
     flip.transform_points(v, in_place=True)
     flip.transform_vectors(n, in_place=True)
     translation((0,1,0)).transform_points(v, in_place=True)
     d = Drawing('rotamer cb indicator')
     d.set_geometry(v, n, t)
     return d
Example #14
0
    def circle_layout(self, segs, params, gap):
        '''
        Layout on circle with a gap at the bottom, progressing
        clockwise from bottom left gap end point which is at the origin.
        This is used both for laying out a top level circle pattern
        and also for laying out the loops and stems attached in a
        circle to the end of a stem.
        '''

        # Compute circle radius that exactly fits the segments
        # with segment end points lying on the circle.
        seg_lengths = [seg.width for seg in segs] + [seg.pad
                                                     for seg in segs] + [gap]
        wc = value_counts(seg_lengths)
        radius = polygon_radius(list(wc.items()))

        # Translate from origin at bottom of circle to origin
        # at lower left gap end point.
        gap_angle_step = circle_angle(gap, radius)
        from math import pi, sin, cos
        a = 0.5 * gap_angle_step * pi / 180
        from chimerax.geometry import translation, rotation
        stf = translation((radius * sin(a), -radius + radius * cos(a), 0))

        # Layout segments on the circle
        coords = {}
        angle = 0.5 * gap_angle_step
        for seg in segs:
            angle_step = circle_angle(seg.width, radius)
            rtf = rotation((0, 0, 1), 180 - 0.5 * angle_step)
            if params.branch_tilt != 0:
                from random import random
                btf = rotation((1, 0, 0),
                               params.branch_tilt * (1 - 2 * random()))
                rtf = rtf * btf
            ptf = rotation((0, 0, 1), -angle, center=(0, radius, 0))
            ctf = stf * ptf * rtf
            for b, tf in seg.placements.items():
                coords[b] = ctf * tf
            # Next position along circle.
            gap_step = circle_angle(seg.pad, radius)
            angle += angle_step + gap_step

        return coords
Example #15
0
def point_symmetry(v, center, xyz, w, minimum_correlation=0.99, nmax=8):

    from chimerax import geometry

    # Look for icosahedral symmetry.
    csname = icosahedral_symmetry(v, center, xyz, w, minimum_correlation)
    if csname:
        syms = geometry.icosahedral_symmetry_matrices(csname, center)
        return ('Icosahedral %s' % csname), syms

    # Look for z-axis cyclic symmetry.
    n = cyclic_symmetry(nmax, v, (0, 0, 1), center, xyz, w,
                        minimum_correlation)
    if n is None:
        return None, None

    # Check for octahedral symmetry.
    if n == 4:
        c4x, cm = correlation(v, xyz, w, (1, 0, 0), 90, center)
        if c4x >= minimum_correlation:
            syms = geometry.octahedral_symmetry_matrices(center)
            return 'Octahedral', syms

    # Check for tetrahedral symmetry 3-fold on z, EMAN convention.
    if n == 3:
        from math import sqrt
        a3yz = (0, -2 * sqrt(2) / 3, -1.0 / 3)  # 3-fold in yz plane
        c3yz, cm = correlation(v, xyz, w, a3yz, 120, center)
        if c3yz >= minimum_correlation:
            syms = geometry.tetrahedral_symmetry_matrices('z3', center)
            return 'Tetrahedral z3', syms

    # Check for tetrahedral symmetry, 2-folds on x,y,z.
    c2x, cm = correlation(v, xyz, w, (1, 0, 0), 180, center)
    c2y, cm = correlation(v, xyz, w, (0, 1, 0), 180, center)
    if n == 2 and c2x >= minimum_correlation and c2y >= minimum_correlation:
        c3d, cm = correlation(v, xyz, w, (1, 1, 1), 120, center)
        if c3d >= minimum_correlation:
            syms = geometry.tetrahedral_symmetry_matrices('222', center)
            return 'Tetrahedral', syms

    # Check for dihedral symmetry, x axis flip.
    if c2x >= minimum_correlation:
        syms = geometry.dihedral_symmetry_matrices(n, center)
        return 'D%d' % n, syms

    # Check for dihedral symmetry, y axis flip.
    if c2y >= minimum_correlation:
        zrot = geometry.rotation((0, 0, 1), -90)
        syms = geometry.dihedral_symmetry_matrices(n).transform_coordinates(
            zrot)
        syms = geometry.recenter_symmetries(syms, center)
        return 'D%d, y flip' % n, syms

    syms = geometry.cyclic_symmetry_matrices(n, center)
    return ('C%d' % n), syms
Example #16
0
 def _rotate(self, axis, angle):
     # Convert axis from camera to scene coordinates
     saxis = self.camera_position.transform_vector(axis)
     angle *= self.speed
     if self._moving_atoms:
         from chimerax.geometry import rotation
         self._move_atoms(
             rotation(saxis, angle, center=self._atoms_center()))
     else:
         self.view.rotate(saxis, angle, self.models())
Example #17
0
    def rotate_nucleotides(self, segs, max_rotation):
        '''Rotate each nucleotide a random angle around P-P backbone.'''
        if max_rotation == 0:
            return

        from chimerax.geometry import rotation
        from random import random
        for seg in segs:
            for b, place in seg.placements.items():
                a = (2 * random() - 1) * max_rotation
                seg.placements[b] = place * rotation((1, 0, 0), a)
Example #18
0
def random_loop_orientations(coords, pmap, angle=90, center=(0, 0, 0)):
    '''
    Rotate nucleotides in loops about x-axis by random amount.
    '''
    from random import random
    from chimerax.geometry import rotation
    for b, tf in tuple(coords.items()):
        if not b in pmap:
            a = (2 * random() - 1) * angle
            rx = rotation((1, 0, 0), a, center)
            coords[b] = tf * rx
Example #19
0
def correlation(v, xyz, w, axis, angle, center, rise=None):

    from chimerax.geometry import rotation, translation
    tf = rotation(axis, angle, center)
    if not rise is None:
        shift = translation([x * rise for x in axis])
        tf = shift * tf
    xf = v.scene_position * tf
    wtf = v.interpolated_values(xyz, xf)
    from chimerax.map_fit.fitmap import overlap_and_correlation
    olap, cor, corm = overlap_and_correlation(w, wtf)
    return cor, corm
Example #20
0
 def update_position(self, *_):
     m = self.model
     fr = self.frame
     if fr >= self.frames:
         m.position = self.pos1
         from chimerax.core.triggerset import DEREGISTER
         return DEREGISTER
     else:
         f = fr / self.frames
         from chimerax.geometry import translation, rotation
         m.position = translation(f * (self.c1 - self.c0)) * rotation(
             self.axis, f * self.angle, self.c0) * self.pos0
         self.frame += 1
Example #21
0
def post_geometry(radius, height, caps=False):
    '''
    Returns a simple cylinder, rotated and translated so its base is on
    the origin and it points along (1,0,0)
    '''
    from chimerax.surface.shapes import cylinder_geometry
    from chimerax.geometry import rotation, translation
    v, n, t = cylinder_geometry(radius=radius, height=height, caps=caps, nc=6)
    tr = translation([0, 0, height / 2])
    tr.transform_points(v, in_place=True)
    r = rotation([0, 1, 0], 90)
    r.transform_points(v, in_place=True)
    r.transform_vectors(n, in_place=True)
    return v, n, t
Example #22
0
def box_path(points, width, twist=0):

    from numpy import dot, concatenate, array

    # Find normal to bisecting plane through each point.
    n = len(points)
    p = array(points)
    from chimerax.geometry import normalize_vector as nv
    tangents = array([
        nv(
            array(nv(p[min(i + 1, n - 1)] - p[i])) +
            array(nv(p[i] - p[max(i - 1, 0)]))) for i in range(n)
    ])

    # Trace edge of square cross-section from start to finish.
    edges = []
    y, z = p[2] - p[0], tangents[0]
    from chimerax.geometry import rotation, orthonormal_frame
    if twist != 0:
        y = rotation(z, twist) * y
    f = orthonormal_frame(z, y)
    xa, ya = f.axes()[:2]
    corners = ((1, 1), (-1, 1), (-1, -1), (1, -1))
    for x, y in corners:
        ep = [points[0] + (x * 0.5 * width) * xa + (y * 0.5 * width) * ya]
        for i in range(n - 1):
            e0, p0, p1, t = ep[i], p[i], p[i + 1], tangents[i + 1]
            ep.append(e0 + (dot(p1 - e0, t) / dot(p1 - p0, t)) * (p1 - p0))
        edges.append(ep)

    # Calculate triangles for each face of a surface model.
    # Make sharp edges.
    va = concatenate(edges + edges + edges + edges)
    ta = []
    nc = len(corners)
    for s in range(n - 1):
        for c in range(nc):
            c1 = (c + 1) % nc + nc
            t = s + (s % 2) * 2 * nc * n
            ta.append((c * n + t, c1 * n + 1 + t, c * n + 1 + t))
            ta.append((c * n + t, c1 * n + t, c1 * n + 1 + t))

    # Add end caps.
    ta.extend([(nc * n + 0, nc * n + (2 + c) * n, nc * n + (1 + c) * n)
               for c in range(nc - 2)])
    ta.extend([(n - 1, (1 + c) * n + n - 1, (2 + c) * n + n - 1)
               for c in range(nc - 2)])
    ta = array(ta)

    return va, ta
Example #23
0
    def straight_layout(self, segs, params):
        '''Layout on x-axis starting at the origin, proceeding in positive x direction.'''

        coords = {}
        s = 0
        from chimerax.geometry import translation, rotation
        for i, seg in enumerate(segs):
            rtf = rotation((1, 0, 0), params.branch_twist * i)
            stf = translation((s, 0, 0))
            ptf = stf * rtf
            for b, tf in seg.placements.items():
                coords[b] = ptf * tf
            # Next position along line
            s += seg.width + seg.pad

        return coords
Example #24
0
 def set_angle(self, angle):
     if angle == self._angle:
         return
     delta = angle - self._angle
     self._angle = angle
     moving, fixed = self.moving_side.coord, self.bond.other_atom(
         self.moving_side).coord
     from chimerax.geometry import z_align, rotation
     za = z_align(moving, fixed)
     update = za.inverse() * rotation((0, 0, -1), delta) * za
     side_atoms = self.bond.side_atoms(self.moving_side)
     coords = side_atoms.coords
     # avoid a copy...
     update.transform_points(coords, in_place=True)
     side_atoms.coords = coords
     self.rotation._rotater_update(self, delta)
Example #25
0
 def _rota_indicator(self):
     v1, n1, t1 = exclamation_mark(radius=0.1, height=0.5, nc = 8)
     v2, n2, t2 = spiral(major_radius=0.3, minor_radius = 0.05, height=0.4,
                         turn_segments=6, circle_segments=3)
     translation((0,0,-0.15)).transform_points(v2, in_place=True)
     v = numpy.concatenate((v1, v2))
     n = numpy.concatenate((n1, n2))
     t = numpy.concatenate((t1, t2+len(v1)))
     r = rotation((1,0,0),180)
     r.transform_points(v, in_place=True)
     r.transform_vectors(n, in_place=True)
     translation((0,0.5,0.25)).transform_points(v, in_place=True)
     d = Drawing('rotamer indicator')
     d.skip_bounds = True
     d.pickable = False
     d.set_geometry(v, n, t)
     return d
Example #26
0
 def rotate(self, axis, angle, drawings=None):
     '''
     Move camera to simulate a rotation of drawings about current
     rotation center.  Axis is in scene coordinates and angle is
     in degrees.
     '''
     if drawings:
         from chimerax.geometry import bounds
         b = bounds.union_bounds(d.bounds() for d in drawings)
         if b is None:
             return
         center = b.center()
     else:
         center = self.center_of_rotation
     from chimerax.geometry import rotation
     r = rotation(axis, angle, center)
     self.move(r, drawings)
Example #27
0
    def _rotate_slab(self, axis, angle, center=None):
        v = self._map
        vaxis = v.scene_position.inverse().transform_vector(axis)
        ro = v.rendering_options
        saxis, soffset = ro.tilted_slab_axis, ro.tilted_slab_offset
        thickness = ro.tilted_slab_spacing * (ro.tilted_slab_plane_count - 1)
        if center is None:
            rcenter = self._center
        else:
            rcenter = v.scene_position.inverse() * center
        from chimerax.geometry import rotation, inner_product
        axis = rotation(vaxis, angle).transform_vector(saxis)
        #        offset = inner_product(axis, rcenter) - 0.5*thickness
        offset = soffset + inner_product(axis - saxis, rcenter)
        offset = keep_tilted_slab_in_box(v, offset, axis=axis)
        for m in [v] + self._matching_maps:
            m.set_parameters(tilted_slab_axis=axis, tilted_slab_offset=offset)

        # Make sure new plane is shown before another mouse event shows another plane.
        self.session.update_loop.update_graphics_now()
Example #28
0
 def rotate_command(self, tokens):
     if len(tokens) not in (3, 5):
         raise ValueError("Expected 'angle axis' after %s" % tokens[0])
     if len(tokens) == 3:
         angle = self.parse_float(tokens[1])
         if tokens[2] == 'x':
             axis = (1., 0., 0.)
         elif tokens[2] == 'y':
             axis = (1., 0., 0.)
         elif tokens[2] == 'z':
             axis = (1., 0., 0.)
         else:
             raise UserError("Expected 'x', 'y', or 'z' axis in %s" %
                             tokens[0])
     else:
         data = [self.parse_float(x) for x in tokens[1:5]]
         angle = data[0]
         axis = array(data[1:4])
     xform = rotation(axis, angle)
     self.transforms.append(self.transforms[-1] * xform)
     self.pure.append(self.pure[-1])
def sym_axis_drawing_standard(fold_symmetry, axyz0, axyz1, base_radius=0.3):
    import numpy
    radius = base_radius * (1 + 0.1 * fold_symmetry)
    n = len(axyz0)
    radii = numpy.ones(n, numpy.float32) * radius
    from chimerax.geometry import Places, cylinder_rotations, rotation
    rot44 = numpy.empty([n, 4, 4], numpy.float32)
    cylinder_rotations(axyz0, axyz1, radii, rot44)
    rot44[:, 3, :3] = 0.5 * (axyz0 + axyz1)

    vertices = []
    normals = []
    triangles = []
    colors = []
    angle = 360 / fold_symmetry
    v, n, t = cylindrical_wedge_geometry(angle=angle, nc=3)
    colors_base = numpy.ones((len(v), 4), numpy.uint8)
    # colors_1 = numpy.array([_symmetry_colors[fold_symmetry]]*len(v), numpy.uint8)
    # colors_2 = numpy.ones(colors_1.shape, numpy.uint8) * 255
    for i in range(fold_symmetry):
        colors_base[:, :] = _symmetry_colors[fold_symmetry][i]
        r = rotation((0, 0, 1), angle * i)
        vertices.append(r * v)
        normals.append(r.apply_without_translation(n))
        triangles.append(t + len(v) * i)
        colors.append(colors_base.copy())
    vertices = numpy.concatenate(vertices)
    normals = numpy.concatenate(normals)
    triangles = numpy.concatenate(triangles)
    colors = numpy.concatenate(colors)

    from chimerax.graphics import Drawing
    d = Drawing('{}-fold symmetry axis'.format(fold_symmetry))
    d.set_geometry(vertices, normals, triangles)
    d.set_vertex_colors(colors)

    d.positions = Places(opengl_array=rot44)

    # d.position = Place(axes=place.axes(), origin = constant_point + (f0+f1/2)*axis_direction)
    return d
Example #30
0
    def curve_layout(self, segs, params, curve):
        '''
        Layout along a curve which is a class instance such as HelixCurve
        or SphereSpiral defining position(t), velocity(t), normal(t) methods.
        Layout starts at t = 0 and goes toward increasing t values until
        all segments are layed out.
        '''

        seg_lengths = [(seg.width, seg.pad) for seg in segs]
        placements = segments_on_curve(curve, seg_lengths)

        coords = {}
        from random import random
        from chimerax.geometry import rotation
        random_tilt = params.branch_tilt
        for seg, place in zip(segs, placements):
            tf = place
            if random_tilt != 0:
                tf = tf * rotation((1, 0, 0), random_tilt * (1 - 2 * random()))
            for b, stf in seg.placements.items():
                coords[b] = tf * stf

        return coords