Пример #1
0
def mapping(discretization_spacing, surface_guid, curve_features_guids = [], point_features_guids = []):
    """Creates planar polylines from the boundaries of a NURBS surface, NURBS curves and point on the NURBS surface
    by using the UV parameterisation with a user-input discretisation spacing.

    Parameters
    ----------
    discretization_spacing: real
        Spacing value for discretisation of NURBS surface borders and curves into polylines.
    surface: Rhino surface guid
        Untrimmed or trimmed Rhino NURBS surface.
    curve_features: Rhino curve guid
        Rhino NURBS curve on the surface.
    point_features: Rhino point guid
        Rhino point on the surface.

    Returns
    -------
    output: list
        Planar parameterised geometrical output: boundary, holes, polyline features and point features.

    Raises
    ------
    -

    """
    
    boundaries = surface_borders(surface_guid, border_type = 1)
    boundary_polylines = [curve_discretisation(boundary, discretization_spacing) for boundary in boundaries]
    uv_boundary_polylines = [[rs.SurfaceClosestPoint(surface_guid, vertex) for vertex in rs.PolylineVertices(boundary_polyline)] for boundary_polyline in boundary_polylines]
    planar_boundary_polylines = [[[u, v, 0] for u, v in uv_boundary_polyline] for uv_boundary_polyline in uv_boundary_polylines]
    planar_boundary_polyline = []
    for polyline in planar_boundary_polylines:
        planar_boundary_polyline += polyline[: -1]
    planar_boundary_polyline.append(planar_boundary_polyline[0])
    rs.DeleteObjects(boundaries)
    rs.DeleteObjects(boundary_polylines)

    holes = surface_borders(surface_guid, border_type = 2)
    if len(holes) > 1:
        holes = rs.JoinCurves(holes, delete_input = True)
    hole_polylines = [curve_discretisation(hole, discretization_spacing) for hole in holes]
    uv_hole_polylines = [[rs.SurfaceClosestPoint(surface_guid, vertex) for vertex in rs.PolylineVertices(hole_polyline)] for hole_polyline in hole_polylines]
    planar_hole_polylines = [[[u, v, 0] for u, v in hole] for hole in uv_hole_polylines]
    rs.DeleteObjects(holes)
    rs.DeleteObjects(hole_polylines)

    polyline_features = [curve_discretisation(curve_features_guid, discretization_spacing) for curve_features_guid in curve_features_guids]
    uv_polyline_features = [[rs.SurfaceClosestPoint(surface_guid, vertex) for vertex in rs.PolylineVertices(polyline_feature)] for polyline_feature in polyline_features]
    planar_polyline_features = [[[u, v, 0] for u, v in feature] for feature in uv_polyline_features]
    rs.DeleteObjects(polyline_features)

    uv_point_features = [rs.SurfaceClosestPoint(surface_guid, point) for point in point_features_guids]
    planar_point_features = [[u, v, 0] for u, v in uv_point_features]

    return planar_boundary_polyline, planar_hole_polylines, planar_polyline_features, planar_point_features
Пример #2
0
def depressCrvs(srf, crvs, paths, startPt, radius, sd):
    newCrvs = []
    for i in range(len(crvs)):
        divPts = rs.DivideCurve(crvs[i], 400)
        for j in range(len(divPts)):
            path = rs.PointClosestObject(divPts[j], paths)[0]
            param = rs.CurveClosestPoint(path, divPts[j])
            close = rs.EvaluateCurve(path, param)
            srfParam = rs.SurfaceClosestPoint(srf, close)
            vec = rs.SurfaceNormal(srf, srfParam)
            dist = rs.Distance(close, divPts[j])
            vec = rs.VectorUnitize(vec)
            border = 1
            entry = 1
            if j > len(divPts) / 2:
                border = rs.Distance(rs.CurveEndPoint(crvs[i]), divPts[j])
            else:
                border = rs.Distance(rs.CurveStartPoint(crvs[i]), divPts[j])
            if border < sd * 3:
                border = border / (sd * 3)
            else:
                border = 1
            entryDist = rs.Distance(startPt, divPts[j])
            if entryDist < sd * 10:
                entry = entryDist / (sd * 10)
            else:
                entry = 1
            if dist < sd * 2:
                val = radius * (bellCrv(dist, sd))
                divPts[j] = rs.PointAdd(divPts[j], vec * val * border * entry)
        newCrvs.append(rs.AddCurve(divPts))
    return divPts
Пример #3
0
def offsetext():
    def RepresentsInt(s):
        try: 
            int(s)
            return True
        except ValueError:
            return False
    
    
    viste = rs.ViewNames()
    for viewport in viste:
        rs.ViewDisplayMode(viewport,"Shaded")
    diametro = rs.StringBox("dimensione della punta","10","scontornatura")
    if RepresentsInt(diametro):
        diametro = int(diametro)
    else:
        diametro = 10
    brep =  rs.GetObjects("dammi un solido",16)
    brepexp = rs.ExplodePolysurfaces(brep)
    get_val = rs.GetEdgeCurves("dammi le curve")
    surf_edge = []
    
    for i in get_val:
        surf_edge.append(i[0])
    surf_edge = rs.coerceguidlist(surf_edge)
    if len(surf_edge)>1:
        surf_edge = rs.JoinCurves(surf_edge,True)
    surface = rs.GetObjects("conferma la selezione",8,False,True,1,1)

    print surf_edge
    uv= []
    temp_edge = rs.ExplodeCurves(surf_edge,False)
    new_surface = rs.CopyObject(surface,(0,0,0))
    list_evpt =[]
    for i in temp_edge:
        evpt =rs.CurveMidPoint(i)
        print evpt
        list_evpt.append(evpt)
    for i in list_evpt:
        bord= rs.SurfaceClosestPoint(new_surface,i)
        uv.append(bord)
    for i in uv:
        rs.ExtendSurface(new_surface,i,diametro*10)
    edge = rs.OffsetCurveOnSurface(surf_edge,new_surface,-diametro)
    print edge
    if rs.CurveLength(edge)<rs.CurveLength(surf_edge):
        rs.DeleteObject(edge)
        edge =  rs.OffsetCurveOnSurface(surf_edge,new_surface,diametro)
    surf_edge = rs.ExplodeCurves(surf_edge,True)
    print edge
    
    rs.ObjectColor(edge,(0,0,255))
    for i in brepexp:
        rs.DeleteObject(i)
    for i in temp_edge:
        rs.DeleteObject(i)
    for i in surf_edge:
        rs.DeleteObject(i)
    
    rs.DeleteObjects([new_surface,surface])
Пример #4
0
def get_dist(p):
    param = rs.SurfaceClosestPoint(surf, p)
    cp = rs.EvaluateSurface(surf, param[0], param[1])
    #n = rs.SurfaceNormal(surf,param)
    #dv = map_values(param,axis.Domain[0],axis.Domain[1],0,1)
    #r = (1-dv)*start_radius + dv*end_radius
    d = rs.Distance(p, cp) - thickness / 2.0
    return d
Пример #5
0
def divCrv(srf, pts, uv, vec, eq):
    param = map(lambda x: rs.SurfaceClosestPoint(srf, x), pts)
    railcrv = map(lambda x: rs.ExtractIsoCurve(srf, x, trp.intFlipBool(uv)),
                  param)
    frames = map(lambda x, y, z: sweepRail(srf, x, vec, y, z), railcrv, param,
                 pts)
    # rs.DeleteObject(domaincrv)
    return railcrv
Пример #6
0
def getSrfFrame(srf):
    domainU = rs.SurfaceDomain(srf, 0)
    domainV = rs.SurfaceDomain(srf, 1)
    u = domainU[1] / 2.0
    v = domainV[1] / 2.0
    point = rs.EvaluateSurface(srf, u, v)
    param = rs.SurfaceClosestPoint(srf, point)
    return rs.SurfaceFrame(srf, param)
def evaluatedeviation( surface_id, threshold, sample ):
    r2point = rs.SurfaceClosestPoint(surface_id, sample)#Returns the UV parameter of the point on a surface that is closest to a test point.
    if not r2point: return
    r3point = rs.EvaluateSurface(surface_id, r2point[0], r2point[1])#evaluates the surface with UV parameters(U=[0] and v[1])
    if not r3point: return
    deviation = rs.Distance(r3point, sample)#sample refers to the previous point
    if deviation<=threshold: return#if deviation is less than threshold do nothing
    rs.AddPoint(sample)#if deviation is more than threshold add point
    rs.AddLine(sample, r3point)#if deviation is more than threshold add line
Пример #8
0
def extframe(srf):
    crv = rs.DuplicateSurfaceBorder(srf, type=1)
    point = rs.EvaluateCurve(crv, 0)
    parameter = rs.SurfaceClosestPoint(srf, point)
    plane = rs.SurfaceFrame(srf, parameter)
    direction = rs.CurveTangent(crv, 0)
    newplane = rs.PlaneFromNormal(point, direction, plane.ZAxis)
    frame = sweepSec(crv, newplane, vec1)
    if crv: rs.DeleteObjects(crv)
    return frame
Пример #9
0
def getr2PathOnSurface(surface, segments, prompt1, prompt2):
    startPt = rs.GetPointOnSurface(surface, prompt1)
    if not startPt:
        return
    
    endPt = rs.GetPointOnSurface(surface, prompt2)
    if not endPt:
        return
    
    #if our start and end points are coincedents, why bother?
    if rs.Distance(startPt, endPt) == 0.0:
        return
    
    #GetPointOnSurface returns a Point3D, to get the UV coords, we need to SCP to the Point3D
    uva = rs.SurfaceClosestPoint(surface, startPt)
    uvb = rs.SurfaceClosestPoint(surface, endPt)
    
    #store our new vertices for the path in a list
    path = []
    
    #the shortest path between two points is a straight line, but in our case this 
    #needs to follow the contours of the surface.  We divide the straight path into
    #segments and check each vertex of the segments and find the closest corrisponding point
    #on the surface itself
    #range is non inclusive in python, I had to add 1 here to get the last point to align
    #with the last point selected
    for i in range(segments + 1):
        
        #we will decompose the UV r2 space into U and V r1 spaces and find where we
        #are using a single parameter at each segment vertex
        t = i / segments
        
        # U and V parameters are calculated by taking the individual U and V domains
        # and multiplying them by the t value.  The t paramter is added to the start of
        #both domains. SCP will return a list of values [0] is the U and [1] is the V
        u = uva[0] + t * (uvb[0] - uva[0])
        v = uva[1] + t * (uvb[1] - uva[1])
        
        #get that closes point on the surface and add it to the path list of vertices
        pt = rs.EvaluateSurface(surface, u, v)
        path.append(pt)
    return path
Пример #10
0
def isHorizontalUpSrf(srf,tolerance=TOLERANCE):
    boundary=rs.DuplicateSurfaceBorder(srf)
    if type(boundary is list):boundary=boundary[0]
    sp=rs.CurveStartPoint(boundary)
    uv=rs.SurfaceClosestPoint(srf,sp)
    normal=rs.SurfaceNormal(srf,uv)
    normal=rs.VectorUnitize(normal)
    nz=normal[2]
    rs.DeleteObject(boundary)
    if abs(nz-1)<tolerance:return True
    return False
Пример #11
0
def getr2pathonsurface(surface_id, segments, prompt1, prompt2):
    start_point = rs.GetPointOnSurface(surface_id, prompt1)
    if not start_point: return

    end_point = rs.GetPointOnSurface(surface_id, prompt2)
    if not end_point: return

    if rs.Distance(start_point, end_point) == 0.0: return

    uva = rs.SurfaceClosestPoint(surface_id, start_point)
    uvb = rs.SurfaceClosestPoint(surface_id, end_point)

    path = []
    for i in range(segments):
        t = i / segments
        u = uva[0] + t * (uvb[0] - uva[0])
        v = uva[1] + t * (uvb[1] - uva[1])
        pt = rs.EvaluateSurface(surface_id, u, v)
        path.append(pt)
    return path
Пример #12
0
def isoframe(srf, uv, spacing, vec):
    points = intervalpts(srf, uv, spacing)
    sweeps = []
    for i in points:
        point = rs.EvaluateSurface(srf, i[0], i[1])
        parameter = rs.SurfaceClosestPoint(srf, point)
        plane = rs.SurfaceFrame(srf, parameter)
        crv = rs.ExtractIsoCurve(srf, parameter, flipBool(uv))
        direction = rs.CurveTangent(crv, 0)
        newplane = rs.PlaneFromNormal(point, direction, plane.ZAxis)
        sweeps.append(sweepSec(crv, newplane, vec))
    return sweeps
Пример #13
0
def getCurvatureOfClosestPoint(pt, srf, scale=None):
    if scale is None:
        global curvatureScale
        scale = curvatureScale

    u, v = rs.SurfaceClosestPoint(srf, pt)
    c = rs.SurfaceCurvature(srf, (u, v))

    if c is None:
        return 0
    else:
        return c[7] * scale
Пример #14
0
def evaluatedeviation( surface_id, threshold, sample ):
    r2point = rs.SurfaceClosestPoint(surface_id, sample)
    if not r2point: return

    r3point = rs.EvaluateSurface(surface_id, r2point[0], r2point[1])
    if not r3point: return

    deviation = rs.Distance(r3point, sample)
    if deviation<=threshold: return

    rs.AddPoint(sample)
    rs.AddLine(sample, r3point)
Пример #15
0
def MovePt2PtBasedOnSrf(fromPt, toPt, toSrf):

    u, v = rs.SurfaceClosestPoint(toSrf, toPt)

    vt = rs.VectorCreate(toPt, fromPt)
    vt = rs.VectorUnitize(vt)

    c = rs.SurfaceCurvature(toSrf, (u, v))
    c = c[7]

    vt = rs.VectorScale(vt, 10 * c)

    return rs.PointAdd(toPt, vt)
Пример #16
0
def ConvertToUVW(srf_id, xyz_points):
    uvw_points = []
    for point in xyz_points:
        Suv = rs.SurfaceClosestPoint(srf_id, point)
        Sxyz = rs.EvaluateSurface(srf_id, Suv)
        Snormal = rs.SurfaceNormal(srf_id, Suv)
        dirPos = rs.PointAdd(Sxyz, Snormal)
        dirNeg = rs.PointSubtract(Sxyz, Snormal)
        Sdist = rs.Distance(Sxyz, point)
        if rs.Distance(point, dirPos) > rs.Distance(point, dirNeg):
            Sdist = -Sdist
        uvw_points.append((Suv(0), Suv(1), Sdist))
    return uvw_points
Пример #17
0
def XYZ_To_UVW(srf_id, pXYZ):
    pUVW = []
    for point in pXYZ:
        uvClosest = rs.SurfaceClosestPoint(srf_id, point)
        ptClosest = rs.EvaluateSurface(srf_id, uvClosest)
        srfNormal = rs.SurfaceNormal(srf_id, uvClosest)
        pPositive = rs.PointAdd(ptClosest, srfNormal)
        pNegative = rs.PointSubtract(ptClosest, srfNormal)
        fDistance = rs.Distance(ptClosest, point)
        if rs.Distance(point,pPositive) > rs.Distance(point, pNegative):
            fDistance = -fDistance
        pUVW.append( (uvClosest[0], uvClosest[1], fDistance) )
    return pUVW
Пример #18
0
def isHorizonalSrf(srf,return_dir=False,tolerance=TOLERANCE):
    boundary=rs.DuplicateSurfaceBorder(srf)
    if type(boundary is list):boundary=boundary[0]
    sp=rs.CurveStartPoint(boundary)
    uv=rs.SurfaceClosestPoint(srf,sp)
    normal=rs.SurfaceNormal(srf,uv)
    normal=rs.VectorUnitize(normal)
    direct=normal[2]
    nz=abs(normal[2])
    rs.DeleteObject(boundary)
    if abs(nz-1)<tolerance:
        if return_dir:return True,direct
        return True
    if return_dir:return False,direct
    return False
Пример #19
0
    def point_xyz_to_uv(self, xyz):
        """Return the UV point from the mapping of a XYZ point based on the UV parameterisation of the surface.

        Parameters
        ----------
        xyz : list
            (x, y, z) coordinates.

        Returns
        -------
        list
            The (u, v, 0) coordinates of the mapped point.

        """
        return rs.SurfaceClosestPoint(self.guid, xyz) + (0., )
Пример #20
0
    def closest_point(self, xyz):
        """Return the XYZ coordinates of the closest point on the surface from input XYZ-coordinates.
    
        Parameters
        ----------
        xyz : list
            XYZ coordinates.

        Returns
        -------
        list
            The XYZ coordinates of the closest point on the surface.

        """

        return rs.EvaluateSurface(self.guid, *rs.SurfaceClosestPoint(self.guid, xyz))
Пример #21
0
def MapCurvatureStep(srf_id, uvPt, max, reverse, accuracy):
    data_curvature = rs.SurfaceCurvature(srf_id, uvPt)
    if not data_curvature: return
    vec = data_curvature[5]
    if max: vec = data_curvature[3]

    if reverse: vec = rs.VectorReverse(vec)
    vec = rs.VectorUnitize(vec)
    vec = rs.VectorScale(vec, accuracy)

    dPoint = rs.VectorAdd(data_curvature[0], vec)
    nPoint = rs.SurfaceClosestPoint(srf_id, dPoint)
    mPoint = rs.EvaluateSurface(srf_id, nPoint)

    if rs.Distance(mPoint, data_curvature[0])< (0.5*accuracy): return
    return nPoint
Пример #22
0
def extframe(srf, vec):
    frames = []
    crv = rs.DuplicateSurfaceBorder(srf, type=1)
    rs.SimplifyCurve(crv)

    domain = rs.CurveDomain(crv)
    param = (domain[0] + domain[1]) / 2.0
    rs.CurveSeam(crv, param)

    point = rs.EvaluateCurve(crv, 0)
    parameter = rs.SurfaceClosestPoint(srf, point)
    plane = rs.SurfaceFrame(srf, parameter)
    direction = rs.CurveTangent(crv, 0)
    newplane = rs.PlaneFromNormal(point, direction, plane.ZAxis)
    frame.append(sweepSec(crv, newplane, vec))
    if crv: rs.DeleteObjects(crv)
    return frames
Пример #23
0
def GetTimberSectionLenght(tim_srf, base_point):
    closest_pra = rs.SurfaceClosestPoint(tim_srf.Faces[0], base_point)
    V = rs.SurfaceDomain(tim_srf.Faces[0], 1)

    if V[0] < 0:
        divide_V = abs(V[0] / 10)
    else:
        divide_V = abs(V[1] / 10)

    list_point = []
    for i in range(10):
        point = rs.EvaluateSurface(tim_srf.Faces[0], closest_pra[0],
                                   V[0] + divide_V * i)
        list_point.append(point)

    length = rs.Distance(list_point[0], list_point[5])

    return length
Пример #24
0
 def offset_vector(self, point, cross_section_index, point_index):
     modulo = len(self.point_lists[cross_section_index - 1])
     prev_point_1 = self.point_lists[cross_section_index - 1][
         (point_index - 2) %
         modulo] if cross_section_index % 2 == 0 else self.point_lists[
             cross_section_index - 1][(point_index - 1) % modulo]
     prev_point_2 = self.point_lists[cross_section_index - 1][
         (point_index - 1) %
         modulo] if cross_section_index % 2 == 0 else self.point_lists[
             cross_section_index - 1][point_index]
     in_between_vector = rs.VectorAdd(rs.VectorCreate(prev_point_1, point),
                                      rs.VectorCreate(prev_point_2, point))
     normal_vector = rs.SurfaceNormal(
         self.brep, rs.SurfaceClosestPoint(self.brep, point))
     plane = rs.PlaneFromFrame(point, in_between_vector, normal_vector)
     vector = rs.SurfaceNormal(rs.AddPlaneSurface(plane, 1, 1), [0, 0])
     unit_vector = rs.VectorUnitize(vector)
     return [rs.VectorScale(unit_vector, 2), in_between_vector]
Пример #25
0
def HorizPlaneFromSurface(srf):
    rhsrf = rs.coercesurface(srf)
    centerPoint = utils.FindMostDistantPointOnSrf(srf)
    u, v = rs.SurfaceClosestPoint(srf, centerPoint)
    origPlane = rhsrf.FrameAt(u,v)[1]
    if abs(origPlane.Normal.Z) == 1:
        #SURFACE HORIZONTAL
        plane = rs.WorldXYPlane()
        plane.Origin = centerPoint
        return plane
    else:
        #SURFACE NOT HORIZONTAL
        upVec = utils.GetUphillVectorFromPlane(srf)
        ptUp = rc.Geometry.Point3d.Add(centerPoint, upVec)
        line1 = rc.Geometry.Line(centerPoint, ptUp)
        ptY = rc.Geometry.Point3d.Add(centerPoint, origPlane.YAxis)
        line2 = rc.Geometry.Line(centerPoint, ptY)
        angle = math.radians(min(rs.Angle2(line1, line2)))
        origPlane.Rotate(angle, origPlane.Normal, centerPoint)
        return origPlane
Пример #26
0
def main():
  rs.AddLayer("laydown")

  while True:
    panel, face = getsubsurface.GetSubSurface("select down face")
    if panel is None or face is None:
      break

    # compute the plane
    normal = rs.VectorUnitize(rs.SurfaceNormal(face, (0.5,0.5)))
    plane = rs.PlaneFromNormal(rs.EvaluateSurface(face, 0.5, 0.5), normal)

    rs.ViewCPlane(plane=plane)
    box = rs.BoundingBox(face, rs.ViewCPlane(), in_world_coords=True)

    proj_coords = [rs.SurfaceClosestPoint(face, coord) + (0,) for coord in box]
    laydown = rs.OrientObject(panel, box[0:3], proj_coords[0:3], flags=1)
    rs.ObjectLayer(laydown, "laydown")

    rs.DeleteObject(face)
    rs.HideObject(panel)
Пример #27
0
def offsetCurveOnSurface():
    curve = rs.GetObject("sel curve", 4)
    num = rs.GetReal("Offset Distance:", 200)
    points = rs.DivideCurve(curve, num)
    surface = rs.GetObject("sel surface", 8)
    offset_ptsA0 = []
    offset_ptsA1 = []
    offset_ptsB0 = []
    offset_ptsB1 = []

    rs.EnableRedraw(False)
    for point in points:
        parameter = rs.SurfaceClosestPoint(surface, point)
        crv = rs.ExtractIsoCurve(surface, parameter, 2)
        #create sphere at end
        try:
            offsetEndPtsA = offsetCrvEndPt(crv[0], num)
            rs.DeleteObject(crv[0])
        except IndexError:
            offsetEndPtsA = None

        try:
            offsetEndPtsB = offsetCrvEndPt(crv[1], num)
            rs.DeleteObject(crv[1])
        except IndexError:
            offsetEndPtsB = None
        #offset_points.append(offset_point)

        if not (offsetEndPtsA is None):
            offset_ptsA0.append(offsetEndPtsA[0])
            offset_ptsA1.append(offsetEndPtsA[1])
        if not (offsetEndPtsB is None):
            offset_ptsB0.append(offsetEndPtsB[0])
            offset_ptsB1.append(offsetEndPtsB[1])

    rs.EnableRedraw(True)
    rs.AddInterpCurve(offset_ptsA0)
    rs.AddInterpCurve(offset_ptsA1)
    rs.AddInterpCurve(offset_ptsB0)
    rs.AddInterpCurve(offset_ptsB1)
Пример #28
0
def convert_to_uv_space(srf,pts):
    
    tol = rs.UnitAbsoluteTolerance()
    uv_pts = []
    for pt in pts:
        #need for issues in cases points lie on a seam
        if not rs.IsPointOnSurface (srf, pt):
            pts_dis = []
            pts_dis.append((pt[0]+tol,pt[1],pt[2]))
            pts_dis.append((pt[0]-tol,pt[1],pt[2]))
            pts_dis.append((pt[0],pt[1]+tol,pt[2]))
            pts_dis.append((pt[0],pt[1]-tol,pt[2]))
            pts_dis.append((pt[0],pt[1],pt[2]+tol))
            pts_dis.append((pt[0],pt[1],pt[2]-tol))    
            for pt_dis in pts_dis:
                data= rs.BrepClosestPoint(srf,pt_dis)
                if rs.IsPointOnSurface(srf,data[0]):
                    pt = data[0]
                    break
        u,v = rs.SurfaceClosestPoint(srf,pt)             
        uv_pts.append((u,v,0))
        
        #rs.AddTextDot(str(data[2] ) + " / " + str(rs.IsPointOnSurface (srf, pt)) + " / " + str(u) + " / " + str(v),pt)
    return uv_pts
Пример #29
0
def splitSrfVerticallyByPts(srf,pts):
    normals=[]
    up=(0,0,1000000000)
    half=(0,0,500000000)
    cutters=[]
    for p in pts:
        uv=rs.SurfaceClosestPoint(srf,p)
        normal=rs.SurfaceNormal(srf,uv)
        normal=rs.VectorScale(normal,1000)
        normals.append(normal)
        botStart=rs.VectorAdd(rs.VectorSubtract(p,half),normal)
        botEnd=rs.VectorSubtract(rs.VectorSubtract(p,half),normal)

        l=rs.AddLine(botStart,botEnd)
        path=rs.AddLine(botStart,rs.VectorAdd(botStart,up))
        cutter=rs.ExtrudeCurve(l,path)
        rs.DeleteObjects([l,path])

        #print(rs.IsBrep(cutter))
        #print(cutter)
        cutters.append(cutter)
    # rs.SelectObjects(cutters)
    srfs=splitSrfBySrfs(srf,cutters)
    return srfs
Пример #30
0
def main():
    global inner_curves, outer_curves, curve_coords

    # save for later
    orig_hidden_objects = rs.HiddenObjects()

    # we put reference points in the dogbone-ref layer, so create it if it doesn't exist
    rs.AddLayer("dogbone-ref")

    panel, face = getsubsurface.GetSubSurface("select dogbone face")

    diameter = rs.GetReal("enter cutter diameter", number=0.25)
    diameter = diameter * 1.1

    rs.EnableRedraw(False)

    # compute the plane
    normal = rs.VectorUnitize(rs.SurfaceNormal(face, (0.5, 0.5)))
    plane = rs.PlaneFromNormal(rs.EvaluateSurface(face, 0.5, 0.5), normal)

    rs.ViewCPlane(plane=plane)
    rs.ProjectOsnaps(True)

    outer_curves = rs.DuplicateSurfaceBorder(face, 1)
    inner_curves = rs.DuplicateSurfaceBorder(face, 2)

    # make a dict mapping each curve to the coords in that curve
    curve_coords = dict()
    for curve in outer_curves + inner_curves:
        coords = rs.CurvePoints(curve)[:-1]
        curve_coords[curve] = coords

    # make a dict mapping each curve to the z component of its cross product at each index
    curve_cross_zs = dict()
    for curve, coords in curve_coords.items():
        proj_coords = [rs.SurfaceClosestPoint(face, coord) for coord in coords]
        cross_zs = []
        for idx in range(len(proj_coords)):
            triplet = [
                proj_coords[(idx + 1) % len(proj_coords)], proj_coords[idx],
                proj_coords[(idx - 1) % len(proj_coords)]
            ]

            v0 = (triplet[1][0] - triplet[0][0], triplet[1][1] - triplet[0][1],
                  0)
            v1 = (triplet[2][0] - triplet[1][0], triplet[2][1] - triplet[1][1],
                  0)
            cross_z = rs.VectorCrossProduct(v0, v1)[2]
            cross_zs.append(cross_z)
        curve_cross_zs[curve] = cross_zs

    points = []
    bones = []
    temp_points = []
    rs.EnableRedraw(True)
    while True:
        coord = rs.GetPoint("select corner")
        if coord is None:
            break
        try:
            curve, idx = get_curve_and_idx_for_coord(coord)
            point = rs.AddPoint(coord)
            rs.ObjectColor(point, (255, 0, 0))
            temp_points.append(point)
            bones.append((curve, idx))
        except ValueError:
            print "invalid curve point"
            continue
    rs.EnableRedraw(False)
    rs.DeleteObjects(temp_points)

    # try to automatically identify dogbone points if user selected none
    if len(bones) == 0:
        for curve, coords in curve_coords.items():
            proj_coords = [
                rs.SurfaceClosestPoint(face, coord) for coord in coords
            ]
            for idx in range(len(proj_coords)):
                triplet = [
                    proj_coords[(idx + 1) % len(proj_coords)],
                    proj_coords[idx], proj_coords[(idx - 1) % len(proj_coords)]
                ]
                if curve_cross_zs[curve][idx] > 0:
                    bones.append((curve, idx))

    # make the bones
    extrusions = []
    for bone in bones:
        curve, idx = bone

        coords = curve_coords[curve]

        point = rs.AddPoint(coords[idx])
        rs.ObjectLayer(point, "dogbone-ref")

        triplet = [
            coords[(idx + 1) % len(coords)],
            coords[idx],
            coords[(idx - 1) % len(coords)],
        ]

        angle = rs.Angle2(
            (triplet[1], triplet[0]),
            (triplet[1], triplet[2]),
        )
        angle = angle[0]

        # This is a hacky method to determine the handedness of the curve
        # the cross product SHOULD have worked here, but for some reason
        # it did not.
        v0 = triplet[2][0] - triplet[1][0], triplet[2][1] - triplet[1][1], 0
        v1 = triplet[1][0] - triplet[0][0], triplet[1][1] - triplet[0][1], 0
        _angle = math.degrees(
            math.atan2(v0[1], v0[0]) - math.atan2(v1[1], v1[0]))
        while _angle > 180:
            _angle -= 360
        while _angle < -180:
            _angle += 360
        if math.copysign(1, angle) != math.copysign(1, _angle):
            angle -= 180

        point = rs.VectorAdd(
            triplet[1],
            rs.VectorRotate(
                0.5 * diameter *
                rs.VectorUnitize(rs.VectorSubtract(triplet[2], triplet[1])),
                angle / 2, (0, 0, 1)))

        circle = rs.AddCircle((point.X, point.Y, -10), diameter / 2.0)
        circle_srf = rs.AddPlanarSrf(circle)
        p0 = (point.X, point.Y, -10)
        p1 = (point.X, point.Y, 10)
        line = rs.AddLine(p0, p1)

        extrusion = rs.ExtrudeSurface(circle_srf, line)
        extrusions.append(extrusion)
        rs.DeleteObjects([circle, circle_srf, line])

    rs.BooleanDifference([panel], extrusions, delete_input=True)

    rs.DeleteObject(panel)
    rs.DeleteObjects(extrusions)
    rs.DeleteObjects(points)
    rs.DeleteObjects(inner_curves)
    rs.DeleteObjects(outer_curves)
    rs.DeleteObject(face)
    rs.ShowObject(rs.AllObjects())
    rs.HideObjects(orig_hidden_objects)

    rs.EnableRedraw(True)