Пример #1
0
def arc_between_two_points(coordinate_system, point1, point2, radius=1, right=True):
    global_point1 = coordinate_system.to_parent(point1)
    global_point2 = coordinate_system.to_parent(point2)
    direction = point2 - point1
    distance = np.sqrt(np.dot(direction, direction))
    arc_coordinate_system = Cartesian(basis=np.copy(coordinate_system.basis), origin=np.copy(global_point1),
                                      name='Arc coordinate_system')

    r_theta_phi = transforms.cartesian_to_spherical(direction)
    arc_coordinate_system.rotate_axis_angle([0, 0, 1], r_theta_phi[2])
    arc_coordinate_system.rotate_axis_angle([0, 1, 0], r_theta_phi[1] + np.pi/2)
    x_offset = -distance / 2
    y_offset = np.sqrt(radius**2 - x_offset**2)
    if right:
        y_offset *= -1
    arc_coordinate_system.origin = arc_coordinate_system.to_parent([x_offset, y_offset, 0])
    local_point1 = arc_coordinate_system.to_local(global_point1)
    local_point2 = arc_coordinate_system.to_local(global_point2)
    start = transforms.cartesian_to_spherical(local_point1)[2]
    stop = transforms.cartesian_to_spherical(local_point2)[2]
    if not right:
        start = 2 * np.pi - start
        stop = 2 * np.pi - stop
    path = Arc(coordinate_system=arc_coordinate_system, a=radius, b=radius, start=start, stop=stop, right=right)
    return path
Пример #2
0
def helix_between_two_points(coordinate_system, point1, point2, radius=1, loops=1, right=True):
    direction = point2 - point1
    distance = np.sqrt(np.dot(direction, direction))
    origin = coordinate_system.to_parent(point1)
    helix_coordinate_system = Cartesian(basis=np.copy(coordinate_system.basis), origin=np.copy(origin),
                                        name='Helix coordinate system')
    r_theta_phi = transforms.cartesian_to_spherical(direction)
    helix_coordinate_system.rotate_axis_angle([0, 0, 1], r_theta_phi[2])
    helix_coordinate_system.rotate_axis_angle([0, 1, 0], r_theta_phi[1])
    pitch = distance / int(loops)
    name = 'Right Helix' if right else 'Left Helix'
    path = Helix(name=name, coordinate_system=helix_coordinate_system,
                 radius=radius, pitch=pitch, start=0, stop=np.pi * 2 * int(loops), right=right)
    return path
Пример #3
0
 def test_rotation_axis_angle(self):
     other_coordinate_system = Cartesian()
     order = 3
     axis = [1, 1, 2]
     steps = 10**order  # per turn
     step = 2 * np.pi / steps
     for k in range(steps):
         other_coordinate_system.rotate_axis_angle(axis, step)
     self.assertEqual(self.coordinate_system, other_coordinate_system)
     np.testing.assert_allclose(self.coordinate_system.basis,
                                other_coordinate_system.basis, atol=np.finfo(float).eps*steps)
     axis = [1, 0, 0]
     self.coordinate_system.rotate_axis_angle(axis, np.pi)
     np.testing.assert_allclose(self.coordinate_system.basis,
                                np.array([[1, 0, 0], [0, -1, 0], [0, 0, -1]]), atol=np.finfo(float).eps)
     self.coordinate_system.rotate_axis_angle(axis, np.pi)
     np.testing.assert_allclose(self.coordinate_system.basis,
                                np.array([[1, 0, 0], [0, 1, 0], [0, 0, 1]]), atol=2*np.finfo(float).eps)
Пример #4
0
 def __init__(self, name, coordinate_system=None):
     if coordinate_system is None:
         self.coordinate_system = Cartesian()
     elif isinstance(coordinate_system, Cartesian):
         self.coordinate_system = coordinate_system
     else:
         raise ValueError('coordinates system must be instance of Cartesian class')
     self.name = str(name)
     self.parent = None
     self.elements = {}
     self.points = None
Пример #5
0
 def test_to_parent_to_local(self):
     origin = (np.random.random(3) - 0.5) * 100
     other_coordinate_system = Cartesian(origin=origin)
     axis = (np.random.random(3) - 0.5) * 100
     angle = (np.random.random() - 0.5) * 100
     other_coordinate_system.rotate_axis_angle(axis, angle)
     point_global = (np.random.random(3) - 0.5) * 100
     point_local = other_coordinate_system.to_local(point_global)
     point_global2 = other_coordinate_system.to_parent(point_local)
     np.testing.assert_allclose(point_global2, point_global, atol=np.finfo(float).eps)
     point_local = (np.random.random(3) - 0.5) * 100
     point_global = other_coordinate_system.to_parent(point_local)
     point_local_2 = other_coordinate_system.to_local(point_global)
     np.testing.assert_allclose(point_local_2, point_local, atol=np.finfo(float).eps)
Пример #6
0
    from matplotlib import pyplot as plt
    use_mpl = True
except ImportError:
    use_mpl = True
from Space.Coordinates import Cartesian


def error(cs_1, cs_2):
    delta = cs_1.basis - cs_2.basis
    return np.sqrt(np.sum(delta ** 2))

# Create cartesian coordinate system

# if you don't pass arguments the basis coincide with 'Absolute' (mayavi) coordinate system
cs_1 = Cartesian(origin=np.array([0, 0, 0]), euler_angles_convention='Bunge')
cs_2 = Cartesian(origin=np.array([0, 0, 0]), euler_angles_convention='Bunge')

print(cs_1)

turns = 10
axis = np.array([1, 1, 1])
steps = 1  # per turn
max_steps_order = 4
errors = []

for order in range(max_steps_order + 1):
    steps = 10**order # per turn
    print("Processing %g steps per turn" % steps)
    step = 2 * np.pi / steps
    print("  Angle increment is %g rad (%g deg)" % (step, np.rad2deg(step)))
    laps_errors = []
Пример #7
0
class Space(object):

    def __init__(self, name, coordinate_system=None):
        if coordinate_system is None:
            self.coordinate_system = Cartesian()
        elif isinstance(coordinate_system, Cartesian):
            self.coordinate_system = coordinate_system
        else:
            raise ValueError('coordinates system must be instance of Cartesian class')
        self.name = str(name)
        self.parent = None
        self.elements = {}
        self.points = None

    def __str__(self):
        description = 'Space: %s\n' % self.name
        description += str(self.coordinate_system)
        return description

    def to_global_coordinate_system(self, xyz):
        """
        convert local points coordinates xyz to global coordinate system coordinates
        :param xyz: array of points shaped Nx3
        :return: array of points in global coordinates system
        """
        parent_xyz = self.coordinate_system.to_parent(xyz)
        if self.parent is None:
            return parent_xyz
        else:
            return self.parent.to_global_coordinate_system(parent_xyz)

    def basis_in_global_coordinate_system(self):
        """
        returns local coordinate system basis in global coordinate system as Cartesian class object
        :return: local Cartesian coordinate system in global coordinate system
        """
        origin = np.copy(self.coordinate_system.origin)
        basis = np.copy(self.coordinate_system.basis)
        if self.parent is not None:
            basis = self.parent.to_global_coordinate_system(basis + origin)
            origin = self.parent.to_global_coordinate_system(origin)
            basis = basis - origin
        name = self.coordinate_system.name
        labels = self.coordinate_system.labels
        coordinate_system = Cartesian(basis=basis, origin=origin, name=name, labels=labels)
        return coordinate_system

    def to_local_coordinate_system(self, xyz):
        """
        convert global points coordinates xyz to local coordinate system coordinates
        :param xyz: array of points shaped Nx3
        :return: array of points in local coordinates system
        """
        basis_global = self.basis_in_global_coordinate_system()
        return basis_global.to_local(xyz)

    def add_element(self, element):
        if isinstance(element, Space):
            if element == self:
                raise ValueError('Space can not be its own subspace')
            else:
                if element.parent is None:
                    element_name = element.name
                    name_counter = 1
                    name_format = ' %d'
                    while element_name in self.elements.keys():
                        element_name = element.name + name_format % name_counter
                        name_counter += 1
                    element.name = element_name
                    self.elements[element.name] = element
                    element.parent = self
                elif element.parent == self:
                    print('Space ' + element.name + 'is already a subspace of ' + self.name)
                else:
                    raise ValueError(element.name + ' is subspace of another space: ' + element.parent.name +
                                     '. Please delete first.')
        else:
            raise ValueError('Only another space could be included as a subspace')

    def remove_element(self, element):
        if isinstance(element, Space):
            if element.parent == self:
                for key in self.elements.keys():
                    if self.elements[key] == element:
                        del self.elements[key]
                element.parent = None
            else:
                print(element.name + ' is not a subspace of ' + self.name)
        else:
            raise ValueError('Only another space could be detached')

    def detach_from_parent(self):
        if self.parent is not None:
            self.parent.remove_element(self)

    def print_tree(self, level=0):
        print('-' * level + ' ' * (level > 0) + self.name)
        for key in self.elements.keys():
            self.elements[key].print_tree(level=level+1)
from __future__ import division, print_function
import numpy as np
from mayavi import mlab

from Space.Coordinates import Cartesian
from Space.Curve.Parametric import Helix
from Space.Pathfinder import line_between_two_points, helix_between_two_points, arc_between_two_points
import Space_visualization as Visual

coordinate_system = Cartesian()
coordinate_system.rotate_axis_angle(np.ones(3), np.deg2rad(45))

fig = mlab.figure('CS demo', bgcolor=(0, 0, 0))
Visual.draw_coordinate_system_axes(fig, coordinate_system)

right_helix = Helix(name='Right Helix', coordinate_system=coordinate_system,
                    radius=2, pitch=0.5, start=0, stop=np.pi * 4, right=True)
left_helix = Helix(name='Left Helix', coordinate_system=coordinate_system,
                   radius=2, pitch=0.5, start=0, stop=np.pi * 2, right=False)

print('Helix length:', left_helix.length())

right_helix_view = Visual.CurveView(fig=fig, curve=right_helix)
right_helix_view.draw()

left_helix_view = Visual.CurveView(fig=fig, curve=left_helix)
left_helix_view.draw()

point1 = np.array([1, 1, 0])
point2 = np.array([2, 2, 0])
points = np.vstack((coordinate_system.to_parent(point1), coordinate_system.to_parent(point2)))
Пример #9
0
 def setUp(self):
     self.coordinate_system = Cartesian()
Пример #10
0
class TestCoordinates(unittest.TestCase):

    def setUp(self):
        self.coordinate_system = Cartesian()

    def test_equality(self):
        other_coordinate_system = Cartesian()
        self.assertEqual(self.coordinate_system, other_coordinate_system)
        other_coordinate_system.origin = [1, 0, 0]
        self.assertNotEqual(self.coordinate_system, other_coordinate_system)

    def test_rotation_axis_angle(self):
        other_coordinate_system = Cartesian()
        order = 3
        axis = [1, 1, 2]
        steps = 10**order  # per turn
        step = 2 * np.pi / steps
        for k in range(steps):
            other_coordinate_system.rotate_axis_angle(axis, step)
        self.assertEqual(self.coordinate_system, other_coordinate_system)
        np.testing.assert_allclose(self.coordinate_system.basis,
                                   other_coordinate_system.basis, atol=np.finfo(float).eps*steps)
        axis = [1, 0, 0]
        self.coordinate_system.rotate_axis_angle(axis, np.pi)
        np.testing.assert_allclose(self.coordinate_system.basis,
                                   np.array([[1, 0, 0], [0, -1, 0], [0, 0, -1]]), atol=np.finfo(float).eps)
        self.coordinate_system.rotate_axis_angle(axis, np.pi)
        np.testing.assert_allclose(self.coordinate_system.basis,
                                   np.array([[1, 0, 0], [0, 1, 0], [0, 0, 1]]), atol=2*np.finfo(float).eps)

    def test_euler_angles(self):
        self.coordinate_system.euler_angles_convention = 'Bunge'
        axis = [1, 0, 0]
        self.coordinate_system.rotate_axis_angle(axis, np.pi)
        np.testing.assert_allclose(self.coordinate_system.euler_angles,
                                   np.array([0, np.pi, 0]), atol=np.finfo(float).eps)
        self.coordinate_system.rotate_axis_angle(axis, np.pi)
        np.testing.assert_allclose(self.coordinate_system.euler_angles,
                                   np.array([0, 0, 0]), atol=np.finfo(float).eps * 2)
        self.coordinate_system.rotate_axis_angle(axis, np.pi / 2)
        #np.testing.assert_allclose(self.coordinate_system.euler_angles,
        #                           np.array([0, np.pi / 2, 0]), atol=np.finfo(float).eps * 2)
        self.coordinate_system.rotate_axis_angle(axis, np.pi / 2)
        np.testing.assert_allclose(self.coordinate_system.euler_angles,
                                   np.array([0, np.pi, 0]), atol=np.finfo(float).eps)
        self.coordinate_system.rotate_axis_angle(axis, np.pi / 2)
        #np.testing.assert_allclose(self.coordinate_system.euler_angles,
        #                           np.array([np.pi, np.pi / 2, np.pi]), atol=np.finfo(float).eps)
        self.coordinate_system.rotate_axis_angle(axis, np.pi / 2)
        np.testing.assert_allclose(self.coordinate_system.euler_angles,
                                   np.array([0, 0, 0]), atol=np.finfo(float).eps * 4)

    def test_to_parent_to_local(self):
        origin = (np.random.random(3) - 0.5) * 100
        other_coordinate_system = Cartesian(origin=origin)
        axis = (np.random.random(3) - 0.5) * 100
        angle = (np.random.random() - 0.5) * 100
        other_coordinate_system.rotate_axis_angle(axis, angle)
        point_global = (np.random.random(3) - 0.5) * 100
        point_local = other_coordinate_system.to_local(point_global)
        point_global2 = other_coordinate_system.to_parent(point_local)
        np.testing.assert_allclose(point_global2, point_global, atol=np.finfo(float).eps)
        point_local = (np.random.random(3) - 0.5) * 100
        point_global = other_coordinate_system.to_parent(point_local)
        point_local_2 = other_coordinate_system.to_local(point_global)
        np.testing.assert_allclose(point_local_2, point_local, atol=np.finfo(float).eps)
Пример #11
0
 def test_equality(self):
     other_coordinate_system = Cartesian()
     self.assertEqual(self.coordinate_system, other_coordinate_system)
     other_coordinate_system.origin = [1, 0, 0]
     self.assertNotEqual(self.coordinate_system, other_coordinate_system)
import numpy as np
from mayavi import mlab

from Space import Space
from Space.Figure.Sphere import *
from Space.Figure.Cylinder import CylindricalWedge, Cylinder
from Space.Figure.Cone import ConicalWedge
from Space.Figure.Torus import ToricWedge
from Space.Figure.Cube import Parallelepiped, ParallelepipedTriclinic, Cuboid, Cube
from Space.Curve.Parametric import Arc
from Space.Coordinates import Cartesian
import Space_visualization as Visual

fig = mlab.figure('CS demo', bgcolor=(0.5, 0.5, 0.5))  # Create the mayavi figure

joint_disc_cs = Cartesian()
joint_disc_cs.euler_angles = (0, np.pi/2, 0)

joint_disc = Cylinder(name='Moon', coordinate_system=joint_disc_cs,
                      r_inner=0.0, r_outer=1.5, z=[-1.0, 1.0])
rod = Cylinder(name='Moon', coordinate_system=Cartesian(origin=[0.0, 0.0, 0.0]),
               r_inner=0.3, r_outer=0.5, z=[0.0, 4])
box = ParallelepipedTriclinic(name='Parallelepiped', a=1, b=1, c=1, alpha=np.pi/4, beta=np.pi/4, gamma=np.pi/4)
#wedge = SphericalWedge(r_inner=5, r_outer=7, phi=2*np.pi*0.7, theta=[np.pi/4*0, np.pi/3])
wedge = ConicalWedge(phi=2*np.pi, theta=np.pi/4, z=np.array([0, 1.0]), z_offset=0.4, r_min=0.3)
#wedge = ToricWedge(r_torus=1.0, r_tube=[0.25, 1.5], phi=np.pi, theta=np.array([-np.pi, 0]))
print('V =', wedge.volume())
print('S = ', wedge.surface_area())
joint_vis = Visual.FigureView(fig, joint_disc, color=(0, 1, 0))
rod_vis = Visual.FigureView(fig, rod)
box_vis = Visual.FigureView(fig, box)
from Space.Coordinates import Cartesian
import Space_visualization as Visual

# Euler's angles are used in the proper notation Z (phi1) - X' (Phi) - Z" (phi2)
# phi1 and phi2 are defined to have modulo 2*pi radians [-pi; pi] or [0; 2*pi]
# Phi is defined to have modulo pi radians [-pi/2; pi/2] or [0; pi]

M = 10
N = 5

# Here we use degrees and numpy deg2rad for conversion

scale = min(360 / (2 * M), 180 / (2 * N)) # scale factor for mayavi scene

fig = mlab.figure('CS demo', bgcolor=(0, 0, 0))  # Create the mayavi figure

for phi1 in np.linspace(0, 360, M, endpoint=True):
    for Phi in np.linspace(0, 180, N, endpoint=True):
        for phi2 in np.linspace(0, 360, M, endpoint=True):
            euler_angles = np.deg2rad(np.array([phi1, Phi, phi2]))
            # Create cartesian coordinate system
            CS = Cartesian(origin=np.array([phi1, Phi, phi2]), labels=['i1', 'i2', 'i3'],)
                           #euler_angles_convention='Bunge')
            # Set CS orientation using Euler's angles
            CS.euler_angles = euler_angles
            # CS_box visualize CS as a cube colored according to Euler's angles
            Visual.draw_coordinate_system_box(fig, CS, scale=scale, draw_axes=False)
# mlab.outline(extent=[0, 360, 0, 180, 0, 360])  # uncomment to draw white outline

mlab.show()