Ejemplo n.º 1
0
    def deriv(self, u, v, k, l, rtype='Vector', domain='local'):
        """
        Compute the surface derivative.

        :param float u: Parametric point.
        :param float v: Parametric point.
        :param int k: Derivative to return in u-direction (0 <= k <= d).
        :param int l: Derivative to return in v-direction (0 <= l <= d).
        :param str rtype: Option to return a NumPy array or a Vector instance
            (rtype = 'Vector' or 'ndarray').
        :param str domain: Option to use local (0 <= u, v <= 1) or global
            (a <= u, v <= b) domain ('local', 'l', 'global', 'g').

        :return: Surface derivative.
        :rtype: :class:`.Vector` or ndarray
        """
        if self._cp is None:
            return None
        # Use NURBS rational curve derivative to compute Bezier derivative.
        # Convert to global since using a NURBS method.
        if is_local_domain(domain):
            u = self.local_to_global_param('u', u)
            v = self.local_to_global_param('v', v)
        d = k + l
        der = rat_surface_derivs(self._n, self._p, self._uk, self._m, self._q,
                                 self._vk, self._cpw, u, v, d)
        if is_array_type(rtype):
            return der[k, l]
        else:
            p0 = Point(der[0, 0])
            return Vector(der[k, l], p0)
Ejemplo n.º 2
0
    def deriv(self, u, k, d=None, rtype='Vector', domain='local'):
        """
        Compute the *k* -th derivative at point *u*.

        :param float u: Parametric point.
        :param int k: Derivative to return (0 <= k <= d).
        :param int d: Highest derivative to compute. If *d* = *None*, then only
            the *k* th derivative will be computed.
        :param str rtype: Option to return a NumPy array or a Vector instance
            (rtype = 'Vector' or 'ndarray').
        :param str domain: Option to use local (0 <= u <= 1) or global
            (a <= u <= b) domain ('local', 'l', 'global', 'g').

        :return: Curve *k* -th derivative.
        :rtype: :class:`.Vector` or ndarray
        """
        if self._cp is None:
            return None
        if d is None:
            d = k
        if is_local_domain(domain):
            u = self.local_to_global_param(u)
        der = rat_curve_derivs(self._n, self._p, self._uk,
                               self._cpw, u, d)
        if is_array_type(rtype):
            return der[k]
        else:
            p0 = Point(der[0])
            return Vector(der[k], p0)
Ejemplo n.º 3
0
    def eval(self, u, v, rtype='Point', domain='local'):
        """
        Evaluate surface at parametric points.

        :param float u: Parametric point in u-direction.
        :param float v: Parametric point in v-direction.
        :param str rtype: Option to return a NumPy array or Point instance
            (rtype = 'ndarray' or 'Point').
        :param str domain: Option to use local (0 <= u, v <= 1) or global
            (a <= u, v <= b) domain ('local', 'l', 'global', 'g').

        :return: Point on surface.
        :rtype: :class:`.Point` or ndarray
        """
        if is_array_like(u) and is_array_like(v):
            return self.eval_params(u, v, rtype, domain)

        if is_local_domain(domain):
            u = self.local_to_global_param('u', u)
            v = self.local_to_global_param('v', v)
        pnt = surface_point(self._n, self._p, self._uk,
                            self._m, self._q, self._vk,
                            self._cpw, u, v)
        if is_array_type(rtype):
            return pnt
        else:
            return Point(pnt)
Ejemplo n.º 4
0
    def eval_params(self, ulist, vlist, rtype='Point', domain='local'):
        """
        Evaluate the surface at multiple parameters.

        :param array_like ulist: Parameters in u-direction.
        :param array_like vlist: Parameters in v-direction.
        :param str rtype: Option to return a NumPy array or Point instance
            (rtype = 'ndarray' or 'Point').
        :param str domain: Option to use local (0 <= u, v <= 1) or global
            (a <= u, v <= b) domain ('local', 'l', 'global', 'g').

        :return: Points on surface.
        :rtype: List :class:`.Point` instances or ndarray
        """
        if not is_array_like(ulist) or not is_array_like(vlist):
            return self.eval(ulist, vlist, rtype, domain)

        if not is_local_domain(domain):
            ulist = [self.global_to_local_param('u', ui) for ui in ulist]
            vlist = [self.global_to_local_param('v', vi) for vi in vlist]
        pnts = bezier_surface_points(self._n, self._m, self._cpw, ulist, vlist)
        if is_array_type(rtype):
            return pnts
        else:
            return [Point(pi) for pi in pnts]
Ejemplo n.º 5
0
    def eval2d(self, u, rtype='Point', domain='local', tol=None, sref=None):
        """
        Evaluate the intersection curve in 2-D space for each surface.

        :param float u: Parametric point.
        :param str rtype: Option to return a NumPy array or Point2D instance
            (rtype = 'Point' or 'ndarray').
        :param str domain: Option to use local (0 <= u <= 1) or global
            (a <= u <= b) domain ('local', 'l', 'global', 'g').
        :param float tol: Tolerance for point refinement.
        :param surface_like sref: Option to provide one of the two surfaces
            used in the intersection curve. If present, the method will
            only return the 2-D parameters associated to that surface.

        :return: Point on curve. Will return *None* if *sref* is not in the
            intersection.
        :rtype: :class:`.Point2D` or ndarray
        """
        if is_local_domain(domain):
            u = self.local_to_global_param(u)

        # Evaluate 2-D curves.
        s1, s2 = self._s1, self._s2
        u1, v1 = self._crv2d_s1.eval(u, rtype='ndarray', domain='global')[:-1]
        u2, v2 = self._crv2d_s2.eval(u, rtype='ndarray', domain='global')[:-1]

        # Project 3-D point to surfaces to get initial parameters.
        # s1, s2 = self._s1, self._s2
        # p3d = self._crv3d.eval(u, domain='global')
        # u1, v1 = invert_point_on_surface(p3d, s1)
        # if self.is_spi:
        #     u2, v2 = invert_point_on_plane(p3d, s2)
        # else:
        #     u2, v2 = invert_point_on_surface(p3d, s2)

        # Refine parameters.
        if tol is None:
            tol = Settings.gtol / 100.
        if self.is_spi:
            u1, v1, u2, v2 = refine_spi_point(s1, s2, u1, v1, tol)[:-1]
        else:
            u1, v1, u2, v2 = refine_ssi_point(s1, s2, u1, v1, u2, v2, tol)[:-1]

        if is_array_type(rtype):
            if sref is s1:
                return array([u1, v1], dtype=float64)
            if sref is s2:
                return array([u2, v2], dtype=float64)
            return (array([u1, v1],
                          dtype=float64), array([u2, v2], dtype=float64))
        else:
            if sref is s1:
                return Point2D((u1, v1))
            if sref is s2:
                return Point2D((u2, v2))
            return Point2D((u1, v1)), Point2D((u2, v2))
Ejemplo n.º 6
0
    def eval(self, u, rtype='Point', *args, **kwargs):
        """
        Evaluate point on line.

        :param float u: Parameter (-inf < u < inf).
        :param str rtype: Option to return a NumPy array or :class:`.Point`
            instance (rtype = 'ndarray' or 'Point').

        :return: Point on line.
        :rtype: :class:`.Point` or ndarray
        """
        pnt = self._p0.xyz + u * self._v.ijk
        if is_array_type(rtype):
            return pnt
        else:
            return Point(pnt)
Ejemplo n.º 7
0
    def eval(self, u=0., v=0., w=0., rtype='Point', *args, **kwargs):
        """
        Evaluate point on the plane at (u, v).

        :param u:
        :param v:
        :param w:
        :param rtype:

        :return:
        """
        pnt = (self._p0.xyz + u * self._vu.ijk + v * self._vv.ijk +
               w * self._vn.ijk)
        if is_array_type(rtype):
            return pnt
        else:
            return Point(pnt)
Ejemplo n.º 8
0
    def norm(self, u, v, rtype='Vector', **kwargs):
        """
        Compute the plane normal.

        :param float u: Parametric point.
        :param float v: Parametric point.
        :param str rtype: Option to return a NumPy array or a Vector instance
            (rtype = 'Vector' or 'ndarray).


        :return:
        """
        vnorm = self._vn.ijk
        if is_array_type(rtype):
            return vnorm
        p0 = self.eval(u, v)
        return Vector(vnorm, p0)
Ejemplo n.º 9
0
    def deriv(self, u, rtype='Vector'):
        """
        Compute the line derivative. This only returns the line direction
        vector with magnitude, and is implemented only for consistency with
        Bezier and NURBS curve objects.

        :param float u: Parametric point (-inf < u < inf).
        :param str rtype: Option to return a NumPy array or :class:`.Vector`
            instance (rtype = 'ndarray' or 'Vector').

        :return: Line derivative.
        :rtype: :class:`.Vector` or ndarray
        """
        if is_array_type(rtype):
            return self._v.vxyz
        else:
            p0 = self.eval(u)
            return Vector(self._v.vxyz, p0)
Ejemplo n.º 10
0
    def eval(self, dx, dy, dz, rtype='Point', *args, **kwargs):
        """
        Evaluate a point relative to the system.

        :param dx:
        :param dy:
        :param dz:
        :param rtype:
        :param args:
        :param kwargs:

        :return:
        """
        pnt = (self._origin.xyz + dx * self._vx.ijk + dy * self._vy.ijk +
               dz * self._vz.ijk)
        if is_array_type(rtype):
            return pnt
        else:
            return Point(pnt)
Ejemplo n.º 11
0
    def curve_eval2d(curve,
                     u,
                     sref=None,
                     rtype='Point',
                     domain='local',
                     tol=None):
        """
        Evaluate a curve in the parametric space of the surface.

        :param curve_like curve: Curve to evaluate.
        :param float u: Curve parameter.
        :param surface_like sref: The surface to return the 2-D parameters on.
        :param str rtype: Option to return a NumPy array or Point2D instance
            (rtype = 'Point' or 'ndarray').
        :param str domain: Option to use local (0 <= u <= 1) or global
            (a <= u <= b) domain ('local', 'l', 'global', 'g').
        :param float tol: Tolerance for point refinement (ICurve only).

        :return: Parameters on surface at curve parameter.
        :rtype: tuple
        """
        if not CheckGeom.is_curve_like(curve) or not \
                CheckGeom.is_surface_like(sref):
            return None

        if tol is None:
            tol = Settings.gtol / 100.

        # ICurve already has built-in method.
        if CheckGeom.is_icurve(curve) and curve.has_surf(sref):
            return curve.eval2d(u, rtype, domain, tol, sref)

        # Evaluate curve and invert on surface.
        p3d = curve.eval(u, domain=domain)
        u, v = ProjectGeom.invert(p3d, sref, True)
        if None in [u, v]:
            return None

        # Return desired type.
        if is_array_type(rtype):
            return array([u, v], dtype=float64)
        return CreateGeom.point2d((u, v))
Ejemplo n.º 12
0
    def tangent(self, u, v, rtype='Vector', domain='local'):
        """
        Surface tangent at (u, v).

        :param float u: Parametric point.
        :param float v: Parametric point.
        :param str rtype: Option to return a NumPy array or a Vector instance
            (rtype = 'Vector' or 'ndarray).
        :param str domain: Option to use local (0 <= u, v <= 1) or global
            (a <= u, v <= b) domain ('local', 'l', 'global', 'g').

        :return: Surface tangent vector.
        :rtype: :class:`.Vector` or ndarray
        """
        du = self.deriv(u, v, 1, 0, rtype='ndarray', domain=domain)
        dv = self.deriv(u, v, 0, 1, rtype='ndarray', domain=domain)
        if is_array_type(rtype):
            return du + dv
        else:
            p0 = self.eval(u, v, domain=domain)
            return Vector(du + dv, p0)
Ejemplo n.º 13
0
    def norm(self, u, v, rtype='Vector', domain='local'):
        """
        Compute the surface normal.

        :param float u: Parametric point.
        :param float v: Parametric point.
        :param str rtype: Option to return a NumPy array or a Vector instance
            (rtype = 'Vector' or 'ndarray).
        :param str domain: Option to use local (0 <= u, v <= 1) or global
            (a <= u, v <= b) domain ('local', 'l', 'global', 'g').

        :return: Surface normal.
        :rtype: :class:`.Vector` or ndarray
        """
        du = self.deriv(u, v, 1, 0, rtype='ndarray', domain=domain)
        dv = self.deriv(u, v, 0, 1, rtype='ndarray', domain=domain)
        norm = cross(du, dv)
        if is_array_type(rtype):
            return norm
        else:
            p0 = self.eval(u, v, domain=domain)
            return Vector(norm, p0)
Ejemplo n.º 14
0
    def eval(self, u, rtype='Point', domain='local', tol=None):
        """
        Evaluate curve at parametric point.

        :param float u: Parametric point.
        :param str rtype: Option to return a NumPy array or Point instance
            (rtype = 'Point' or 'ndarray').
        :param str domain: Option to use local (0 <= u <= 1) or global
            (a <= u <= b) domain ('local', 'l', 'global', 'g').
        :param float tol: Tolerance for point refinement.

        :return: Point on curve.
        :rtype: :class:`.Point` or ndarray
        """
        if is_local_domain(domain):
            u = self.local_to_global_param(u)
        uv1, uv2 = self.eval2d(u, rtype='ndarray', domain='global', tol=tol)
        p3d = self._s1.eval(uv1[0], uv1[1], rtype='ndarray', domain='global')
        if is_array_type(rtype):
            return p3d
        else:
            return Point(p3d)
Ejemplo n.º 15
0
    def eval_params(self, ulist, rtype='Point', domain='local'):
        """
        Evaluate the curve at multiple parameters.

        :param array_like ulist: Curve parameters.
        :param str rtype: Option to return a NumPy array or list of Point
            instances (rtype = 'Point' or 'ndarray').
        :param str domain: Option to use local (0 <= u <= 1) or global
            (a <= u <= b) domain ('local', 'l', 'global', 'g').

        :return: Points at parameters.
        :rtype: List of :class:`.Point` instances or NumPy array
        """
        if not is_array_like(ulist):
            return self.eval(ulist, rtype, domain)

        if is_local_domain(domain):
            ulist = map(self.global_to_local_param, ulist)
        pnts = curve_points(self._n, self._p, self._uk, self._cpw, ulist)
        if is_array_type(rtype):
            return pnts
        else:
            return [Point(pi) for pi in pnts]
Ejemplo n.º 16
0
    def eval(self, u, rtype='Point', domain='local'):
        """
        Evaluate curve at parametric point.

        :param float u: Parametric point.
        :param str rtype: Option to return a NumPy array or Point instance
            (rtype = 'Point' or 'ndarray').
        :param str domain: Option to use local (0 <= u <= 1) or global
            (a <= u <= b) domain ('local', 'l', 'global', 'g').

        :return: Point on curve.
        :rtype: :class:`.Point` or ndarray
        """
        if is_array_like(u):
            return self.eval_params(u, rtype, domain)

        if is_local_domain(domain):
            u = self.local_to_global_param(u)
        pnt = curve_point(self._n, self._p, self._uk, self._cpw, u)
        if is_array_type(rtype):
            return pnt
        else:
            return Point(pnt)
Ejemplo n.º 17
0
    def eval(self, u, v, rtype='Point', domain='local'):
        """
        Evaluate surface at parametric points.

        :param float u: Parametric point in u-direction.
        :param float v: Parametric point in v-direction.
        :param str rtype: Option to return a NumPy array or Point instance
            (rtype = 'Point' or 'ndarray').
        :param str domain: Option to use local (0 <= u, v <= 1) or global
            (a <= u, v <= b) domain ('local', 'l', 'global', 'g').

        :return: Point on surface.
        :rtype: :class:`.Point` or ndarray
        """
        if not is_local_domain(domain):
            u = self.global_to_local_param('u', u)
            v = self.global_to_local_param('v', v)
        pw = deCasteljau2(self._cpw, self._n, self._m, u, v)
        pnt = pw[:-1] / pw[-1]
        if is_array_type(rtype):
            return pnt
        else:
            return Point(pnt)
Ejemplo n.º 18
0
    def deriv(self, u, k=1, d=1, rtype='Vector', domain='local', tol=None):
        """
        Compute the derivative of the intersection curve. Only supports
        first derivates.

        :param float u: Parametric point.
        :param int k: Derivative to return (0 <= k <= 1).
        :param int d: Highest derivative to compute. Currently only supports
            first derivative.
        :param str rtype: Option to return a NumPy array or a Vector instance
            (rtype = 'Vector' or 'ndarray').
        :param str domain: Option to use local (0 <= u <= 1) or global
            (a <= u <= b) domain ('local', 'l', 'global', 'g').
        :param float tol: Tolerance for point refinement.

        :return: First derivative or intersection curve.
        :rtype: :class:`.Vector` or ndarray
        """
        if is_local_domain(domain):
            u = self.local_to_global_param(u)
        # Evaluate 2-D points.
        s1, s2 = self._s1, self._s2
        uv1, uv2 = self.eval2d(u, rtype='ndarray', domain='global', tol=tol)
        # Evaluate surface normals.
        vn1 = s1.norm(uv1[0], uv1[1], rtype='ndarray', domain='global')
        if self.is_spi:
            vn2 = s2.vn.ijk
        else:
            vn2 = s2.norm(uv2[0], uv2[1], rtype='ndarray', domain='global')
        # First derivative is cross product
        du = cross(vn1, vn2)
        if is_array_type(rtype):
            return du
        else:
            p0 = self.eval(u, domain='global')
            return Vector(du, p0)