def test_spin_relative_compound_coordinates(self, sixpoints): """Check compounds's relative coordinates don't change upon spinning""" np.random.seed(0) angles_before = np.asarray([ angle(a, b, c) for (a, b, c) in itt.combinations(sixpoints.xyz, 3) ]) sixpoints.spin(np.pi * 0.1234569789, np.random.rand(3)) angles_after = np.asarray([ angle(a, b, c) for (a, b, c) in itt.combinations(sixpoints.xyz, 3) ]) assert np.allclose(angles_before, angles_after, atol=1e-15)
def test_spin_relative_compound_coordinates(self, sixpoints): """Check compounds's relative coordinates don't change upon spinning""" np.random.seed(0) angles_before = np.asarray( [angle(a, b, c) for (a, b, c) in itt.combinations(sixpoints.xyz, 3)]) sixpoints.spin(np.pi*0.1234569789, np.random.rand(3)) angles_after = np.asarray( [angle(a, b, c) for (a, b, c) in itt.combinations(sixpoints.xyz, 3)]) assert np.allclose(angles_before, angles_after, atol=1e-15)
def __init__(self, anchor=None, orientation=None, separation=0): super(Port, self).__init__(name='Port', port_particle=True) self.anchor = anchor up = Compound(name='subport', port_particle=True) up.add( Particle(name='G', pos=[0.005, 0.0025, -0.0025], port_particle=True), 'middle') up.add( Particle(name='G', pos=[0.005, 0.0225, -0.0025], port_particle=True), 'top') up.add( Particle(name='G', pos=[-0.015, -0.0075, -0.0025], port_particle=True), 'left') up.add( Particle(name='G', pos=[0.005, -0.0175, 0.0075], port_particle=True), 'right') down = clone(up) down.rotate(np.pi, [0, 0, 1]) self.add(up, 'up') self.add(down, 'down') self.used = False if orientation is None: orientation = [0, 1, 0] default_direction = [0, 1, 0] if np.array_equal(np.asarray(default_direction), unit_vector(-np.asarray(orientation))): self.rotate(np.pi, [1, 0, 0]) elif np.array_equal(np.asarray(default_direction), unit_vector(np.asarray(orientation))): pass else: normal = np.cross(default_direction, orientation) self.rotate(angle(default_direction, orientation), normal) if anchor: self.translate_to(anchor.pos) self.translate(separation * unit_vector(orientation))
def calc_dihedral(point1, point2, point3, point4): """Calculate a dihedral angle. Here, two planes are defined by (point1, point2, point3) and (point2, point3, point4). The angle between them is returned. Parameters ---------- point1, point2, point3, point4 : array-like, shape=(3,), dtype=float Four points that define two planes Returns ------- float The dihedral angle between the two planes defined by the four points. """ points = np.array([point1, point2, point3, point4]) x = np.cross(points[1] - points[0], points[2] - points[1]) y = np.cross(points[2] - points[1], points[3] - points[2]) return angle(x, y)
def update_orientation(self, orientation): """ Change the direction between a port and its anchor particle orientation : array-like, shape=(3,), required Vector along which to orient the port """ if self.used: warn("This port is already being used and changing its orientation" " will have no effect on the direction between particles.") orientation = np.asarray(orientation).reshape(3, ) init_separation = self.separation normal = np.cross(self.direction, orientation) #Move to origin to perform rotation self.translate_to((0, 0, 0)) self.rotate(angle(self.direction, orientation), normal) self.labels['down'].rotate(np.pi, normal) self.labels['up'].rotate(np.pi, normal) #Move back to it's anchor particle self.update_separation(init_separation)
def calc_dihedral(point1, point2, point3, point4): """Calculates a dihedral angle Here, two planes are defined by (point1, point2, point3) and (point2, point3, point4). The angle between them is returned. Parameters ---------- point1, point2, point3, point4 : array-like, shape=(3,), dtype=float Four points that define two planes Returns ------- float The dihedral angle between the two planes defined by the four points. """ points = np.array([point1, point2, point3, point4]) x = np.cross(points[1] - points[0], points[2] - points[1]) y = np.cross(points[2] - points[1], points[3] - points[2]) return angle(x, y)
def __init__(self, anchor=None, orientation=None, separation=0): super(Port, self).__init__(name='Port', port_particle=True) self.anchor = anchor up = Compound(name='subport', port_particle=True) up.add(Particle(name='G', pos=[0.005, 0.0025, -0.0025], port_particle=True), 'middle') up.add(Particle(name='G', pos=[0.005, 0.0225, -0.0025], port_particle=True), 'top') up.add(Particle(name='G', pos=[-0.015, -0.0075, -0.0025], port_particle=True), 'left') up.add(Particle(name='G', pos=[0.005, -0.0175, 0.0075], port_particle=True), 'right') down = clone(up) down.rotate(np.pi, [0, 0, 1]) self.add(up, 'up') self.add(down, 'down') self.used = False if orientation is None: orientation = [0, 1, 0] default_direction = [0, 1, 0] if np.array_equal( np.asarray(default_direction), unit_vector(-np.asarray(orientation))): self.rotate(np.pi, [1, 0, 0]) elif np.array_equal( np.asarray(default_direction), unit_vector(np.asarray(orientation))): pass else: normal = np.cross(default_direction, orientation) self.rotate(angle(default_direction, orientation), normal) if anchor: self.translate_to(anchor.pos) self.translate(separation*unit_vector(orientation))
def __init__(self, anchor=None, orientation=None, separation=0): super(Port, self).__init__(name="Port", port_particle=True) self.anchor = anchor default_direction = np.array([0, 1, 0]) if orientation is None: orientation = [0, 1, 0] orientation = np.asarray(orientation) up = Compound(name="subport", port_particle=True) pos = [0.005, 0.0025, -0.0025] up.add(Particle(name="G", pos=pos, port_particle=True), "middle") pos = [0.005, 0.0225, -0.0025] up.add(Particle(name="G", pos=pos, port_particle=True), "top") pos = [-0.015, -0.0075, -0.0025] up.add(Particle(name="G", pos=pos, port_particle=True), "left") pos = [0.005, -0.0175, 0.0075] up.add(Particle(name="G", pos=pos, port_particle=True), "right") down = clone(up) self.add(up, "up") self.add(down, "down") self.used = False if np.allclose(default_direction, unit_vector(-orientation)): down.rotate(np.pi, [0, 0, 1]) self.rotate(np.pi, [0, 0, 1]) elif np.allclose(default_direction, unit_vector(orientation)): down.rotate(np.pi, [0, 0, 1]) else: normal = np.cross(default_direction, orientation) self.rotate(angle(default_direction, orientation), normal) down.rotate(np.pi, normal) if anchor: self.translate_to(anchor.pos) self.translate(separation * unit_vector(orientation))