def bulge2arc(self, Ps, Pe, bulge): """ bulge2arc() """ c = (1 / bulge - bulge) / 2 #Berechnung des Mittelpunkts (Formel von Mickes!) #Calculation of the center (Micke's formula) O = Point(x=(Ps.x + Pe.x - (Pe.y - Ps.y) * c) / 2, \ y=(Ps.y + Pe.y + (Pe.x - Ps.x) * c) / 2) #Radius = Distance between the centre and Ps r = O.distance(Ps) #Kontrolle ob beide gleich sind (passt ...) #Check if they are equal (fits ...) #r=O.distance(Pe) #Unterscheidung f�r den �ffnungswinkel. #Distinction for the opening angle. ??? if bulge > 0: return ArcGeo(Ps=Ps, Pe=Pe, O=O, r=r) else: arc = ArcGeo(Ps=Pe, Pe=Ps, O=O, r=r) arc.reverse() return arc
def fit_triac_by_inc_biarc(self, arc, eps): """ fit_triac_by_inc_biarc() """ #Errechnen von tb V0 = arc[0].Ps.unit_vector(arc[0].O) V2 = arc[2].Pe.unit_vector(arc[2].O) #Errechnen der Hilfgr�ssen t0 = (arc[2].r - arc[0].r) D = (arc[2].O - arc[0].O) X0 = (t0 * t0) - (D * D) X1 = 2 * (D * V0 - t0) Y0 = 2 * (t0 - D * V2) Y1 = 2 * (V0 * V2 - 1) #Errechnen von tb tb = (pow((arc[1].r - arc[0].r + eps), 2) - ((arc[1].O - arc[0].O) * (arc[1].O - arc[0].O))) / \ (2 * (arc[1].r - arc[0].r + eps + (arc[1].O - arc[0].O) * V0)) #Errechnen von tc tc = (pow(t0, 2) - (D * D)) / (2 * (t0 - D * V0)) #Auswahl von t t = min([tb, tc]) #Errechnen von u u = (X0 + X1 * t) / (Y0 + Y1 * t) #Errechnen der neuen Arcs Oa = arc[0].O + t * V0 ra = arc[0].r + t Ob = arc[2].O - u * V2 rb = arc[2].r - u Vn = Ob.unit_vector(Oa) Pn = Oa + ra * Vn Arc0 = ArcGeo(Ps=arc[0].Ps, Pe=Pn, O=Oa, r=ra, direction=arc[0].ext) Arc1 = ArcGeo(Ps=Pn, Pe=arc[2].Pe, O=Ob, r=rb, direction=arc[2].ext) ## print('\nAlte') ## print arc[0] ## print arc[1] ## print arc[2] ## print("tb: %0.3f; tc: %0.3f; t: %0.3f; u: %0.3f" %(tb,tc,t,u)) ## print 'Neue' ## print Arc0 ## print Arc1 return Arc0, Arc1
def fit_triac_by_dec_biarc(self, arc, eps): """ fit_triac_by_dec_biarc() """ V0 = arc[2].Pe.unit_vector(arc[2].O) V2 = arc[0].Ps.unit_vector(arc[0].O) #Errechnen der Hilfgr�ssen t0 = (arc[0].r - arc[2].r) D = (arc[0].O - arc[2].O) X0 = (t0 * t0) - (D * D) X1 = 2 * (D * V0 - t0) Y0 = 2 * (t0 - D * V2) Y1 = 2 * (V0 * V2 - 1) #Errechnen von tb tb = (pow((arc[1].r - arc[2].r + eps), 2) - ((arc[1].O - arc[2].O) * (arc[1].O - arc[2].O))) / \ (2 * (arc[1].r - arc[2].r + eps + (arc[1].O - arc[2].O) * V0)) #Errechnen von tc tc = (pow(t0, 2) - (D * D)) / (2 * (t0 - D * V0)) #Auswahl von t t = min([tb, tc]) #Errechnen von u u = (X0 + X1 * t) / (Y0 + Y1 * t) #Errechnen der neuen Arcs Oa = arc[0].O - u * V2 ra = arc[0].r - u Ob = arc[2].O + t * V0 rb = arc[2].r + t Vn = Oa.unit_vector(Ob) Pn = Ob + rb * Vn Arc0 = ArcGeo(Ps=arc[0].Ps, Pe=Pn, O=Oa, r=ra, \ s_ang=Oa.norm_angle(arc[0].Ps), e_ang=Oa.norm_angle(Pn), direction=arc[0].ext) Arc1 = ArcGeo(Ps=Pn, Pe=arc[2].Pe, O=Ob, r=rb, \ s_ang=Ob.norm_angle(Pn), e_ang=Ob.norm_angle(arc[2].Pe), direction=arc[2].ext) return Arc0, Arc1
def breakArcGeo(self, arcGeo, breakLayers): """ Try to break passed arcGeo with any of the shapes on a break layers. Will break arcGeos recursively. @return: The list of geometries after breaking (arcGeo itself if no breaking happened) """ newGeos = [] for breakLayer in breakLayers: for breakShape in breakLayer.shapes: intersections = self.intersectArcGeometry(arcGeo, breakShape) if len(intersections) == 2: (near, far) = self.classifyIntersections(arcGeo, intersections) logger.debug( "Arc %s broken from (%f, %f) to (%f, %f)" % (arcGeo.toShortString(), near.x, near.y, far.x, far.y)) newGeos.extend( self.breakArcGeo( ArcGeo(Ps=arcGeo.Ps, Pe=near, O=arcGeo.O, r=arcGeo.r, s_ang=arcGeo.s_ang, direction=arcGeo.ext), breakLayers)) newGeos.append( BreakGeo(near, far, breakLayer.axis3_mill_depth, breakLayer.f_g1_plane, breakLayer.f_g1_depth)) newGeos.extend( self.breakArcGeo( ArcGeo(Ps=far, Pe=arcGeo.Pe, O=arcGeo.O, r=arcGeo.r, e_ang=arcGeo.e_ang, direction=arcGeo.ext), breakLayers)) return newGeos return [arcGeo]
def bulge2arc(self, Pa, Pe, bulge): """ bulge2arc() """ c = (1 / bulge - bulge) / 2 #Calculate the centre point (Micke's formula!) O = Point(x=(Pa.x + Pe.x - (Pe.y - Pa.y) * c) / 2, \ y=(Pa.y + Pe.y + (Pe.x - Pa.x) * c) / 2) #Radius = Distance between the centre and Pa r = O.distance(Pa) #Check if they are equal (fits ...) #r=O.distance(Pe) #Unterscheidung für den Öffnungswinkel. #Distinction for the opening angle. ??? if bulge > 0: return ArcGeo(Pa=Pa, Pe=Pe, O=O, r=r) else: arc = ArcGeo(Pa=Pe, Pe=Pa, O=O, r=r) arc.reverse() return arc
def bulge2arc(self, Ps, Pe, bulge): """ bulge2arc() """ c = (1 / bulge - bulge) / 2 #Calculate the centre point (Micke's formula!) O = Point(x=(Ps.x + Pe.x - (Pe.y - Ps.y) * c) / 2, \ y=(Ps.y + Pe.y + (Pe.x - Ps.x) * c) / 2) #Radius = Distance between the centre and Ps r = O.distance(Ps) #Check if they are equal (fits ...) #r=O.distance(Pe) #Unterscheidung f�r den �ffnungswinkel. #Distinction for the opening angle. ??? if bulge > 0: return ArcGeo(Ps=Ps, Pe=Pe, O=O, r=r) else: arc = ArcGeo(Ps=Pe, Pe=Ps, O=O, r=r) arc.reverse() return arc
def make_swivelknife_move(self): """ Set these variables for your tool and material @param offset: knife tip distance from tool centerline. The radius of the tool is used for this. """ offset = self.shape.LayerContent.tool_diameter / 2 dragAngle = self.shape.dragAngle startnorm = offset * Point(1, 0, 0) prvend, prvnorm = Point(0, 0), Point(0, 0) first = 1 #start = self.startp #Use The same parent as for the shape self.parent = self.shape.parent for geo in self.shape.geos: if geo.type == 'LineGeo': geo_b = deepcopy(geo) if first: first = 0 prvend = geo_b.Pa + startnorm prvnorm = startnorm norm = offset * geo_b.Pa.unit_vector(geo_b.Pe) geo_b.Pa += norm geo_b.Pe += norm if not prvnorm == norm: swivel = ArcGeo(Pa=prvend, Pe=geo_b.Pa, r=offset, direction=prvnorm.cross_product(norm).z) swivel.drag = dragAngle < abs(swivel.ext) self.geos.append(swivel) self.geos.append(geo_b) prvend = geo_b.Pe prvnorm = norm elif geo.type == 'ArcGeo': geo_b = deepcopy(geo) if first: first = 0 prvend = geo_b.Pa + startnorm prvnorm = startnorm if geo_b.ext > 0.0: norma = offset * Point(cos(geo_b.s_ang + pi / 2), sin(geo_b.s_ang + pi / 2)) norme = Point(cos(geo_b.e_ang + pi / 2), sin(geo_b.e_ang + pi / 2)) else: norma = offset * Point(cos(geo_b.s_ang - pi / 2), sin(geo_b.s_ang - pi / 2)) norme = Point(cos(geo_b.e_ang - pi / 2), sin(geo_b.e_ang - pi / 2)) geo_b.Pa += norma if norme.x > 0: geo_b.Pe = Point( geo_b.Pe.x + offset / (sqrt(1 + (norme.y / norme.x)**2)), geo_b.Pe.y + (offset * norme.y / norme.x) / (sqrt(1 + (norme.y / norme.x)**2))) elif norme.x == 0: geo_b.Pe = Point(geo_b.Pe.x, geo_b.Pe.y) else: geo_b.Pe = Point( geo_b.Pe.x - offset / (sqrt(1 + (norme.y / norme.x)**2)), geo_b.Pe.y - (offset * norme.y / norme.x) / (sqrt(1 + (norme.y / norme.x)**2))) if not prvnorm == norma: swivel = ArcGeo(Pa=prvend, Pe=geo_b.Pa, r=offset, direction=prvnorm.cross_product(norma).z) swivel.drag = dragAngle < abs(swivel.ext) self.geos.append(swivel) prvend = geo_b.Pe prvnorm = offset * norme if -pi < geo_b.ext < pi: self.geos.append( ArcGeo(Pa=geo_b.Pa, Pe=geo_b.Pe, r=sqrt(geo_b.r**2 + offset**2), direction=geo_b.ext)) else: geo_b = ArcGeo(Pa=geo_b.Pa, Pe=geo_b.Pe, r=sqrt(geo_b.r**2 + offset**2), direction=-geo_b.ext) geo_b.ext = -geo_b.ext self.geos.append(geo_b) #else: # self.geos.append(copy(geo)) if not prvnorm == startnorm: self.geos.append( ArcGeo(Pa=prvend, Pe=prvend - prvnorm + startnorm, r=offset, direction=prvnorm.cross_product(startnorm).z)) self.geos.insert(0, self.geos[0].Pa)
def make_start_moves(self): """ This function called to create the start move. It will be generated based on the given values for start and angle. """ del (self.geos[:]) if g.config.machine_type == 'drag_knife': self.make_swivelknife_move() return #BaseEntitie created to add the StartMoves etc. This Entitie must not #be offset or rotated etc. BaseEntitie = EntitieContentClass(Nr=-1, Name='BaseEntitie', parent=None, children=[], p0=Point(x=0.0, y=0.0), pb=Point(x=0.0, y=0.0), sca=[1, 1, 1], rot=0.0) self.parent = BaseEntitie #Get the start rad. and the length of the line segment at begin. start_rad = self.shape.LayerContent.start_radius start_ver = start_rad #Get tool radius based on tool diameter. tool_rad = self.shape.LayerContent.tool_diameter / 2 #Calculate the starting point with and without compensation. start = self.startp angle = self.angle if self.shape.cut_cor == 40: self.geos.append(start) #Cutting Compensation Left elif self.shape.cut_cor == 41: #Center of the Starting Radius. Oein = start.get_arc_point(angle + pi / 2, start_rad + tool_rad) #Start Point of the Radius Pa_ein = Oein.get_arc_point(angle + pi, start_rad + tool_rad) #Start Point of the straight line segment at begin. Pg_ein = Pa_ein.get_arc_point(angle + pi / 2, start_ver) #Get the dive point for the starting contour and append it. start_ein = Pg_ein.get_arc_point(angle, tool_rad) self.geos.append(start_ein) #generate the Start Line and append it including the compensation. start_line = LineGeo(Pg_ein, Pa_ein) self.geos.append(start_line) #generate the start rad. and append it. start_rad = ArcGeo(Pa=Pa_ein, Pe=start, O=Oein, r=start_rad + tool_rad, direction=1) self.geos.append(start_rad) #Cutting Compensation Right elif self.shape.cut_cor == 42: #Center of the Starting Radius. Oein = start.get_arc_point(angle - pi / 2, start_rad + tool_rad) #Start Point of the Radius Pa_ein = Oein.get_arc_point(angle + pi, start_rad + tool_rad) #Start Point of the straight line segment at begin. Pg_ein = Pa_ein.get_arc_point(angle - pi / 2, start_ver) #Get the dive point for the starting contour and append it. start_ein = Pg_ein.get_arc_point(angle, tool_rad) self.geos.append(start_ein) #generate the Start Line and append it including the compensation. start_line = LineGeo(Pg_ein, Pa_ein) self.geos.append(start_line) #generate the start rad. and append it. start_rad = ArcGeo(Pa=Pa_ein, Pe=start, O=Oein, r=start_rad + tool_rad, direction=0) self.geos.append(start_rad)
def Read(self, caller): """ Read() """ #Assign short name lp = caller.line_pairs e = lp.index_code(0, caller.start + 1) #Assign layer s = lp.index_code(8, caller.start + 1) self.Layer_Nr = caller.Get_Layer_Nr(lp.line_pair[s].value) #X Value s = lp.index_code(10, s + 1) x0 = float(lp.line_pair[s].value) #Y Value s = lp.index_code(20, s + 1) y0 = float(lp.line_pair[s].value) #Radius s = lp.index_code(40, s + 1) r = float(lp.line_pair[s].value) #Searching for an extrusion direction s_nxt_xt = lp.index_code(230, s + 1, e) #If there is a extrusion direction given flip around x-Axis if s_nxt_xt != None: extrusion_dir = float(lp.line_pair[s_nxt_xt].value) logger.debug( self.tr('Found extrusion direction: %s') % extrusion_dir) if extrusion_dir == -1: x0 = -x0 O = Point(x0, y0) #Calculate the start and end values of the circle without clipping s_ang = -3 * pi / 4 m_ang = s_ang - pi e_ang = -3 * pi / 4 #Calculate the start and end values of the arcs Pa = Point(x=cos(s_ang) * r, y=sin(s_ang) * r) + O Pm = Point(x=cos(m_ang) * r, y=sin(m_ang) * r) + O Pe = Point(x=cos(e_ang) * r, y=sin(e_ang) * r) + O #Annexes to ArcGeo class for geometry self.geo.append( ArcGeo(Pa=Pa, Pe=Pm, O=O, r=r, s_ang=s_ang, e_ang=m_ang, direction=-1)) self.geo.append( ArcGeo(Pa=Pm, Pe=Pe, O=O, r=r, s_ang=m_ang, e_ang=e_ang, direction=-1)) #Length corresponds to the length (circumference?) of the circle self.length = self.geo[-1].length + self.geo[-2].length #New starting value for the next geometry caller.start = s
def __init__(self, Ps=Point(), tan_a=0.0, Pb=Point, tan_b=0.0, min_r=1e-6): """ Std. method to initialise the class. @param Ps: Start Point for the Biarc @param tan_a: Tangent of the Start Point @param Pb: End Point of the Biarc @param tan_b: Tangent of the End Point @param min_r: The minimum radius of a arc section. """ min_len = 1e-12 #Min Abstand f�r doppelten Punkt / Minimum clearance for double point min_alpha = 1e-4 #Winkel ab welchem Gerade angenommen wird inr rad / Angle for which it is assumed straight inr rad max_r = 5e3 #Max Radius ab welchem Gerade angenommen wird (5m) / Max radius is assumed from which line (5m) min_r = min_r #Min Radius ab welchem nichts gemacht wird / Min radius beyond which nothing is done self.Ps = Ps self.tan_a = tan_a self.Pb = Pb self.tan_b = tan_b self.l = 0.0 self.shape = None self.geos = [] self.k = 0.0 #Errechnen der Winkel, L�nge und Shape #Calculate the angle, length and shape norm_angle, self.l = self.calc_normal(self.Ps, self.Pb) alpha, beta, self.teta, self.shape = self.calc_diff_angles(norm_angle, \ self.tan_a, \ self.tan_b, \ min_alpha) if(self.l < min_len): self.shape = "Zero" elif(self.shape == "LineGeo"): #Erstellen der Geometrie #Create the geometry self.shape = "LineGeo" self.geos.append(LineGeo(self.Ps, self.Pb)) else: #Berechnen der Radien, Mittelpunkte, Zwichenpunkt #Calculate the radii, midpoints Zwichenpunkt r1, r2 = self.calc_r1_r2(self.l, alpha, beta, self.teta) if (abs(r1) > max_r)or(abs(r2) > max_r): #Erstellen der Geometrie #Create the geometry self.shape = "LineGeo" self.geos.append(LineGeo(self.Ps, self.Pb)) return elif (abs(r1) < min_r)or(abs(r2) < min_r): self.shape = "Zero" return O1, O2, k = self.calc_O1_O2_k(r1, r2, self.tan_a, self.teta) #Berechnen der Start und End- Angles f�r das drucken #Calculate the start and end angles for the print s_ang1, e_ang1 = self.calc_s_e_ang(self.Ps, O1, k) s_ang2, e_ang2 = self.calc_s_e_ang(k, O2, self.Pb) #Berechnen der Richtung und der Extend #Calculate the direction and extent dir_ang1 = (tan_a - s_ang1) % (-2 * pi) dir_ang1 -= ceil(dir_ang1 / (pi)) * (2 * pi) dir_ang2 = (tan_b - e_ang2) % (-2 * pi) dir_ang2 -= ceil(dir_ang2 / (pi)) * (2 * pi) #Erstellen der Geometrien #Create the geometries self.geos.append(ArcGeo(Ps=self.Ps, Pe=k, O=O1, r=r1, \ s_ang=s_ang1, e_ang=e_ang1, direction=dir_ang1)) self.geos.append(ArcGeo(Ps=k, Pe=self.Pb, O=O2, r=r2, \ s_ang=s_ang2, e_ang=e_ang2, direction=dir_ang2))
def Read(self, caller): """ Read() """ #Assign short name lp = caller.line_pairs e = lp.index_code(0, caller.start + 1) #Assign layer s = lp.index_code(8, caller.start + 1) self.Layer_Nr = caller.Get_Layer_Nr(lp.line_pair[s].value) #X Value s = lp.index_code(10, s + 1) x0 = float(lp.line_pair[s].value) #Y Value s = lp.index_code(20, s + 1) y0 = float(lp.line_pair[s].value) O = Point(x0, y0) #Radius s = lp.index_code(40, s + 1) r = float(lp.line_pair[s].value) #Start angle s = lp.index_code(50, s + 1) s_ang = radians(float(lp.line_pair[s].value)) #End angle s = lp.index_code(51, s + 1) e_ang = radians(float(lp.line_pair[s].value)) #Searching for an extrusion direction s_nxt_xt = lp.index_code(230, s + 1, e) #If there is a extrusion direction given flip around x-Axis if s_nxt_xt != None: extrusion_dir = float(lp.line_pair[s_nxt_xt].value) logger.debug( self.tr('Found extrusion direction: %s') % extrusion_dir) if extrusion_dir == -1: x0 = -x0 s_ang = s_ang + pi e_ang = e_ang + pi #Calculate the start and end points of the arcs Pa = Point(x=cos(s_ang) * r, y=sin(s_ang) * r) + O Pe = Point(x=cos(e_ang) * r, y=sin(e_ang) * r) + O #Anhängen der ArcGeo Klasse für die Geometrie #Annexes to ArcGeo class for geometry self.geo.append( ArcGeo(Pa=Pa, Pe=Pe, O=O, r=r, s_ang=s_ang, e_ang=e_ang, direction=1)) #Länge entspricht der Länge des Kreises #Length is the length (circumference?) of the circle self.length = self.geo[-1].length # logger.debug(self.geo[-1]) #Neuen Startwerd für die nächste Geometrie zurückgeben #New starting value for the next geometry caller.start = s
def make_swivelknife_move(self): """ Set these variables for your tool and material @param offset: knife tip distance from tool centerline. The radius of the tool is used for this. """ offset = self.shape.LayerContent.tool_diameter/2 dragAngle = self.shape.dragAngle startnorm = offset*Point(1, 0, 0) # TODO make knife direction a config setting prvend, prvnorm = Point(), Point() first = 1 #Use The same parent as for the shape self.parent = self.shape.parent for geo in self.shape.geos: if geo.type == 'LineGeo': geo_b = deepcopy(geo) if first: first = 0 prvend = geo_b.Ps + startnorm prvnorm = startnorm if geo_b.Ps != geo_b.Pe: # TODO this "fix" should be done during import norm = offset * geo_b.Ps.unit_vector(geo_b.Pe) geo_b.Ps += norm geo_b.Pe += norm if not prvnorm == norm: swivel = ArcGeo(Ps=prvend, Pe=geo_b.Ps, r=offset, direction=prvnorm.cross_product(norm).z) swivel.drag = dragAngle < abs(swivel.ext) self.geos.append(swivel) self.geos.append(geo_b) prvend = geo_b.Pe prvnorm = norm elif geo.type == 'ArcGeo': geo_b = deepcopy(geo) if first: first = 0 prvend = geo_b.Ps + startnorm prvnorm = startnorm if geo_b.ext > 0.0: norma = offset*Point(cos(geo_b.s_ang+pi/2), sin(geo_b.s_ang+pi/2)) norme = Point(cos(geo_b.e_ang+pi/2), sin(geo_b.e_ang+pi/2)) else: norma = offset*Point(cos(geo_b.s_ang-pi/2), sin(geo_b.s_ang-pi/2)) norme = Point(cos(geo_b.e_ang-pi/2), sin(geo_b.e_ang-pi/2)) geo_b.Ps += norma if norme.x > 0: geo_b.Pe = Point(geo_b.Pe.x+offset/(sqrt(1+(norme.y/norme.x)**2)), geo_b.Pe.y+(offset*norme.y/norme.x)/(sqrt(1+(norme.y/norme.x)**2))) elif norme.x == 0: geo_b.Pe = Point(geo_b.Pe.x, geo_b.Pe.y) else: geo_b.Pe = Point(geo_b.Pe.x-offset/(sqrt(1+(norme.y/norme.x)**2)), geo_b.Pe.y-(offset*norme.y/norme.x)/(sqrt(1+(norme.y/norme.x)**2))) if prvnorm != norma: swivel = ArcGeo(Ps=prvend, Pe=geo_b.Ps, r=offset, direction=prvnorm.cross_product(norma).z) swivel.drag = dragAngle < abs(swivel.ext) self.geos.append(swivel) prvend = geo_b.Pe prvnorm = offset*norme if -pi < geo_b.ext < pi: self.geos.append(ArcGeo(Ps=geo_b.Ps, Pe=geo_b.Pe, r=sqrt(geo_b.r**2+offset**2), direction=geo_b.ext)) else: geo_b = ArcGeo(Ps=geo_b.Ps, Pe=geo_b.Pe, r=sqrt(geo_b.r**2+offset**2), direction=-geo_b.ext) geo_b.ext = -geo_b.ext self.geos.append(geo_b) # TODO support different geos, or disable them in the GUI # else: # self.geos.append(copy(geo)) if not prvnorm == startnorm: self.geos.append(ArcGeo(Ps=prvend, Pe=prvend-prvnorm+startnorm, r=offset, direction=prvnorm.cross_product(startnorm).z)) self.geos.insert(0, self.geos[0].Ps)