Exemplo n.º 1
0
 def test_circle_1(self):
     circle = SvCircle(Matrix(), 1.0)
     circle.u_bounds = (0, pi / 6)
     nurbs = circle.to_nurbs()
     cpts = nurbs.get_control_points()
     expected_cpts = np.array([[1.0, 0.0, 0.0], [1.0, 0.26794919, 0.0],
                               [0.8660254, 0.5, 0.0]])
     self.assert_numpy_arrays_equal(cpts, expected_cpts, precision=6)
Exemplo n.º 2
0
 def test_circle_2(self):
     circle = SvCircle(Matrix(), 1.0)
     t_max = pi + 0.3
     circle.u_bounds = (0, t_max)
     nurbs = circle.to_nurbs()
     ts = np.array([0, pi / 2, pi, t_max])
     points = nurbs.evaluate_array(ts)
     expected_points = circle.evaluate_array(ts)
     self.assert_numpy_arrays_equal(points, expected_points, precision=6)
Exemplo n.º 3
0
    def get_circular_arc(self):
        center = np.array(self.center)
        normal = np.array(self.normal)
        p1 = np.array(self.p1)

        circle = SvCircle(center = center,
                    normal = -normal,
                    vectorx = p1 - center)
        circle.u_bounds = (0.0, self.angle)
        #circle.u_bounds = (-self.angle, 0.0)
        return circle
Exemplo n.º 4
0
 def test_arc_2(self):
     pt1 = (-5, 0, 0)
     pt2 = (-4, 3, 0)
     pt3 = (-3, 4, 0)
     eq = circle_by_three_points(pt1, pt2, pt3)
     matrix = eq.get_matrix()
     arc = SvCircle(matrix, eq.radius)
     arc.u_bounds = (0.0, eq.arc_angle)
     nurbs = arc.to_nurbs()
     u_min, u_max = nurbs.get_u_bounds()
     self.assertEquals(u_min, 0, "U_min")
     self.assertEquals(u_max, eq.arc_angle, "U_max")
     startpoint = nurbs.evaluate(u_min)
     self.assert_sverchok_data_equal(startpoint.tolist(), pt1, precision=8)
     endpoint = nurbs.evaluate(u_max)
     self.assert_sverchok_data_equal(endpoint.tolist(), pt3, precision=8)
Exemplo n.º 5
0
def nurbs_revolution_surface(curve,
                             origin,
                             axis,
                             v_min=0,
                             v_max=2 * pi,
                             global_origin=True):
    my_control_points = curve.get_control_points()
    my_weights = curve.get_weights()
    control_points = []
    weights = []

    any_circle = SvCircle(Matrix(), 1)
    any_circle.u_bounds = (v_min, v_max)
    any_circle = any_circle.to_nurbs()
    # all circles with given (v_min, v_max)
    # actually always have the same knotvector
    # and the same number of control points
    n = len(any_circle.get_control_points())
    circle_knotvector = any_circle.get_knotvector()
    circle_weights = any_circle.get_weights()

    # TODO: vectorize with numpy? Or better let it so for better readability?
    for my_control_point, my_weight in zip(my_control_points, my_weights):
        eq = CircleEquation3D.from_axis_point(origin, axis, my_control_point)
        if abs(eq.radius) < 1e-8:
            parallel_points = np.empty((n, 3))
            parallel_points[:] = np.array(eq.center)  #[np.newaxis].T
        else:
            circle = SvCircle.from_equation(eq)
            circle.u_bounds = (v_min, v_max)
            nurbs_circle = circle.to_nurbs()
            parallel_points = nurbs_circle.get_control_points()
        parallel_weights = circle_weights * my_weight
        control_points.append(parallel_points)
        weights.append(parallel_weights)
    control_points = np.array(control_points)
    if global_origin:
        control_points = control_points - origin

    weights = np.array(weights)
    degree_u = curve.get_degree()
    degree_v = 2  # circle

    return SvNurbsSurface.build(curve.get_nurbs_implementation(), degree_u,
                                degree_v, curve.get_knotvector(),
                                circle_knotvector, control_points, weights)
Exemplo n.º 6
0
 def test_arc_3(self):
     pt1 = np.array((-4, 2, 0))
     pt2 = np.array((0, 2.5, 0))
     pt3 = np.array((4, 2, 0))
     eq = circle_by_three_points(pt1, pt2, pt3)
     #matrix = eq.get_matrix()
     arc = SvCircle(center=np.array(eq.center),
                    vectorx=np.array(pt1 - eq.center),
                    normal=eq.normal)
     arc.u_bounds = (0.0, eq.arc_angle)
     nurbs = arc.to_nurbs()
     u_min, u_max = nurbs.get_u_bounds()
     self.assertEquals(u_min, 0, "U_min")
     self.assertEquals(u_max, eq.arc_angle, "U_max")
     startpoint = nurbs.evaluate(u_min)
     self.assert_sverchok_data_equal(startpoint.tolist(), pt1, precision=6)
     endpoint = nurbs.evaluate(u_max)
     self.assert_sverchok_data_equal(endpoint.tolist(), pt3, precision=6)
Exemplo n.º 7
0
    def calc(point_a, point_b, tangent_a, tangent_b, p, planar_tolerance=1e-6):
        xx = point_b - point_a
        xx /= np.linalg.norm(xx)
        tangent_normal = np.cross(tangent_a, tangent_b)
        volume = np.dot(xx, tangent_normal)
        if abs(volume) > planar_tolerance:
            raise Exception(
                f"Provided tangents are not coplanar, volume={volume}")

        zz_a = np.cross(tangent_a, xx)
        zz_b = np.cross(tangent_b, xx)
        zz = (zz_a + zz_b)
        zz /= np.linalg.norm(zz)
        yy = np.cross(zz, xx)

        c = np.linalg.norm(point_b - point_a) * 0.5

        tangent_a /= np.linalg.norm(tangent_a)
        tangent_b /= np.linalg.norm(tangent_b)

        to_center_a = np.cross(zz, tangent_a)
        to_center_b = -np.cross(zz, tangent_b)

        matrix_inv = np.stack((xx, yy, zz))
        matrix = np.linalg.inv(matrix_inv)

        # TODO: sin(arccos(...)) = ...
        alpha = acos(np.dot(tangent_a, xx))
        beta = acos(np.dot(tangent_b, xx))
        if np.dot(tangent_a, yy) > 0:
            alpha = -alpha
        if np.dot(tangent_b, yy) > 0:
            beta = -beta
        #print("A", alpha, "B", beta)

        omega = (alpha + beta) * 0.5
        r1 = c / (sin(alpha) + sin(omega) / p)
        r2 = c / (sin(beta) + p * sin(omega))
        #print("R1", r1, "R2", r2)
        theta1 = 2 * arg(cexp(-1j * alpha) + cexp(-1j * omega) / p)
        theta2 = 2 * arg(cexp(1j * beta) + p * cexp(1j * omega))
        #print("T1", theta1, "T2", theta2)

        vectorx_a = r1 * to_center_a
        center1 = point_a + vectorx_a
        center2 = point_b + r2 * to_center_b

        arc1 = SvCircle(  #radius = r1,
            center=center1,
            normal=-zz,
            vectorx=point_a - center1)
        if theta1 > 0:
            arc1.u_bounds = (0.0, theta1)
        else:
            theta1 = -theta1
            arc1.u_bounds = (0.0, theta1)
            arc1.set_normal(-arc1.normal)

        junction = arc1.evaluate(theta1)
        #print("J", junction)

        arc2 = SvCircle(  #radius = r2,
            center=center2,
            normal=-zz,
            vectorx=junction - center2)
        if theta2 > 0:
            arc2.u_bounds = (0.0, theta2)
        else:
            theta2 = -theta2
            arc2.u_bounds = (0.0, theta2)
            arc2.set_normal(-arc2.normal)

        curve = SvBiArc(arc1, arc2)
        curve.p = p
        curve.junction = junction

        return curve