Пример #1
0
    def pocket(self, args, dbg=None):
        if dbg is None:
            dbg = self.dbg
        layer = args[1]
        cfg = self.cfg
        # dir = CCW
        # if cfg.dir is not None and cfg.dir == 'CW':
        #     dir = CW
        stepOver = cfg.endMillSize * self.stepOver
        cfg.ncInit()
        segments = cfg.dxfInput.getPath(layer)
        pco = PyclipperOffset()
        mp = cfg.getMillPath()
        self.last = cfg.mill.last
        for seg in segments:
            self.pDir = pathDir(seg)
            pco.Clear()
            mainPath = []
            for (i, l) in enumerate(seg):
                l.draw()
                if dbg:
                    l.prt()
                if l.type == LINE:
                    mainPath.append(intScale(l.p0))
                elif l.type == ARC:
                    self.arcLines(mainPath, l, dbg=dbg)
            if dbg:
                dprt()
                for (i, p) in enumerate(mainPath):
                    (x, y) = floatScale(p)
                    dprt("%3d (%7.4f %7.4f)" % (i, x, y))
                dprt()
            
            pco.AddPath(mainPath, pyclipper.JT_ROUND, \
                        pyclipper.ET_CLOSEDPOLYGON)
            offset = cfg.endMillSize / 2.0 + cfg.finishAllowance
            step = 0
            offsetPaths = []
            while True:
                result = pco.Execute(-int(offset * SCALE))
                if dbg:
                    dprt("%2d offset %7.4f results %d" % \
                         (step, offset, len(result)))
                if len(result) == 0:
                    break
                rData = []
                for (rNum, r) in enumerate(result):

                    # convert from list of points to lines

                    if self.arcs:
                        pLast = floatScale(r[-1])
                        index = 0
                        maxDist = -1
                        for (i, p) in enumerate(r):
                            p = floatScale(p)
                            dist = xyDist(p, pLast)
                            if dbg:
                                dprt("%3d (%7.4f %7.4f) dist %9.6f" % \
                                     (i, p[0], p[1], dist))
                            if dist > maxDist:
                                maxDist = dist
                                index = i
                            r[i] = p
                            pLast = p
                        r = r[index:] + r[:index]
                        if dbg:
                            dprt("index %d maxDist %7.4f" % (index, maxDist))
                            pLast = r[-1]
                            dprt("pLast (%7.4f %7.4f)" % (pLast[0], pLast[1]))
                            for (i, p) in enumerate(r):
                                dprt("%3d (%7.4f %7.4f) dist %9.6f" % \
                                     (i, p[0], p[1], xyDist(p, pLast)))
                                pLast = p
                                dprt()
                        path = self.makePath(r, step, rNum, dbg)
                    else:
                        pLast = floatScale(r[-1])
                        path = []
                        for (i, p) in enumerate(r):
                            p = floatScale(p)
                            if dbg:
                                dprt("%3d (%7.4f %7.4f)" % (i, p[0], p[1]))
                            l = Line(pLast, p, i)
                            txt = "s %d r %d i %d" % (step, rNum, i)
                            l.label(txt)
                            path.append(l)
                            pLast = p

                    result[rNum] = path
                        
                    if dbg:
                        dprt()
                        for l in path:
                            l.prt()
                        dprt()

                    # find shortest distance to each path

                    oData = []
                    for (oNum, oPath) in enumerate(offsetPaths):
                        lEnd = oPath[-1]
                        pEnd = lEnd.p1
                        minDist = MAX_VALUE
                        index = None
                        for (i, l) in enumerate(path):
                            dist = xyDist(pEnd, l.p0)
                            if dist < minDist:
                                minDist = dist
                                index = i
                        oData.append((index, minDist))
                    rData.append(oData)
                
                # connect to nearest path

                if dbg and len(result) > 1:
                    dprt("multiple results")
                oConnect = [False] * len(offsetPaths)
                while True:
                    minDist = MAX_VALUE
                    index = None
                    rPath = None
                    for (rNum, oData) in enumerate(rData):
                        if oData == None:
                            continue
                        rPath = rNum
                        for (oNum, (i, dist)) in enumerate(oData):
                            if dbg:
                                dprt("step %d rNum %d Onum %d index %3d "\
                                     "dist %9.6f" % \
                                     (step, rNum, oNum, i, dist))
                            if not oConnect[oNum] and dist < minDist:
                                minDist = dist
                                index = i
                                rIndex = rNum
                                oIndex = oNum
                                
                    if rPath is None:
                        break
                    if index is not None: # connect path
                        if dbg:
                            dprt("connect rIndex %d index %3d to "\
                                 "oIndex %d dist %9.6f" % \
                                 (rIndex, index, oIndex, minDist))
                        path = result[rIndex]
                        rData[rIndex] = None
                        oConnect[oIndex] = True
                        oPath = offsetPaths[oIndex]
                        oPath.append(Line(oPath[-1].p1, path[index].p0))
                        oPath += path[index:] + path[:index]
                    else:       # add new path
                        if dbg:
                            dprt("add rPath %d oNum %d" % \
                                 (rPath, len(offsetPaths)))
                        rData[rPath] = None
                        path = result[rPath]
                        path = self.closest(path)
                        offsetPaths.append(path)

                offset += stepOver
                step += 1
                if step > 99:
                    break
            for path in offsetPaths:
                mp.millPath(path, closed=False, minDist=False)
Пример #2
0
    def makePath(self, points, step, rNum, dbg=False):
        if False:
            r = 1
            for i in range(4):
                a0 = float(i) * pi / 2 + pi / 4
                a = a0
                p0 = (r * cos(a), r * sin(a))
                for j in range(2):
                    tmp = (pi, -pi)[j]
                    a = a0 + tmp / 2
                    p1 = (r * cos(a), r * sin(a))
                    a = a0 + tmp / 1
                    p2 = (r * cos(a), r * sin(a))
                    self.pointsArc(p0, p1, p2)
            dprt()
            sys.exit()

        numPoints = len(points)
        pLast = points[-1]
        i = 0
        path = []
        # points.append(points[0])
        o0 = orientation(pLast, points[0], points[1])
        if dbg:
            dprt("path orientation %s" % oStr(o0))
        while i < numPoints:
            p0 = points[i]
            if dbg:
                dprt("i %3d (%7.4f %7.4f)" % (i, p0[0], p0[1]))
            d0 = xyDist(p0, pLast)
            j = i + 1
            pa = p0
            while j < numPoints - 1:
                pj = points[j]
                dist = xyDist(pa, pj)
                if abs(dist - d0) > 0.001:
                    if dbg:
                        dprt("dist %9.6f d0 %9.6f" % (dist, d0))
                    break
                j += 1
                pa = pj
            delta = j - i
            if delta < 4:
                l = Line(pLast, p0, i)
                txt = "s %d r %d i %d" % (step, rNum, i)
                l.label(txt)
                i += 1
                pLast = p0
            else:
                p1 = points[i + delta / 2]
                (c, r) = self.pointsArc(pLast, p1, pa)
                o = orientation(pLast, p1, pa)
                if o != o0:
                    (pLast, pa) = (pa, pLast)
                a0 = degAtan2(pLast[1] - c[1], pLast[0] - c[0])
                a1 = degAtan2(pa[1] - c[1], pa[0] - c[0])
                l = Arc(c, r, a0, a1, direction=o)
                if dbg:
                    dprt("arc %s %2d i %d (%7.4f %7.4f) %8.3f "\
                         " %d (%7.4f %7.4f) %8.3f" % \
                         (oStr(o), delta, i, pLast[0], pLast[1], a0, \
                          j, pa[0], pa[1], a1))
                i = j
                pLast = pa
            if dbg:
                l.prt()
            path.append(l)
        return(path)