Added flipping of edge to PathGeom.
This commit is contained in:
@@ -23,10 +23,10 @@
|
||||
# ***************************************************************************
|
||||
|
||||
import FreeCAD
|
||||
import math
|
||||
import Part
|
||||
import Path
|
||||
import PathScripts.PathLog as PathLog
|
||||
import math
|
||||
|
||||
from FreeCAD import Vector
|
||||
from PySide import QtCore
|
||||
@@ -455,3 +455,21 @@ def removeDuplicateEdges(wire):
|
||||
unique.append(e)
|
||||
return Part.Wire(unique)
|
||||
|
||||
def flipEdge(edge):
|
||||
'''flipEdge(edge)
|
||||
Flips given edge around so the new Vertexes[0] was the old Vertexes[-1] and vice versa, without changing the shape.
|
||||
Currently only lines, line segments, circles and arcs are supported.'''
|
||||
|
||||
if Part.Line == type(edge.Curve) and not edge.Vertexes:
|
||||
return Part.Edge(Part.Line(edge.valueAt(edge.LastParameter), edge.valueAt(edge.FirstParameter)))
|
||||
elif Part.Line == type(edge.Curve) or Part.LineSegment == type(edge.Curve):
|
||||
return Part.Edge(Part.LineSegment(edge.Vertexes[-1].Point, edge.Vertexes[0].Point))
|
||||
elif Part.Circle == type(edge.Curve):
|
||||
return Part.makeCircle(edge.Curve.Radius, edge.Curve.Center, -edge.Curve.Axis, -math.degrees(edge.LastParameter), -math.degrees(edge.FirstParameter))
|
||||
elif Part.BSplineCurve == type(edge.Curve):
|
||||
spline = edge.Curve
|
||||
poles = [p for p in reversed(spline.getPoles())]
|
||||
weights = [w for w in reversed(spline.getWeights())]
|
||||
degree = spline.Degree
|
||||
return Part.Edge(Part.BSplineCurve(poles, degree=degree, weights=weights))
|
||||
|
||||
|
||||
@@ -135,3 +135,27 @@ class PathTestBase(unittest.TestCase):
|
||||
q2=FreeCAD.Units.Quantity(s2)
|
||||
self.assertEqual(q1.UserString, q2.UserString)
|
||||
|
||||
def assertEdgeShapesMatch(self,e1,e2):
|
||||
"""Verify that 2 edges have the same start/end points and the mid point matches too."""
|
||||
self.assertEqual(type(e1.Curve), type(e2.Curve))
|
||||
self.assertEqual(len(e1.Vertexes), len(e2.Vertexes))
|
||||
if not e1.Vertexes:
|
||||
self.assertEqual(Part.Line, type(e1.Curve))
|
||||
k1 = e1.valueAt(e1.LastParameter) - e1.valueAt(e1.FirstParameter)
|
||||
k2 = e2.valueAt(e2.LastParameter) - e2.valueAt(e2.FirstParameter)
|
||||
self.assertCoincide(k1, -k2)
|
||||
elif 1 == len(e1.Vertexes):
|
||||
self.assertEqual(Part.Circle, type(e1.Curve))
|
||||
self.assertRoughly(e1.Curve.Radius, e2.Curve.Radius)
|
||||
self.assertCoincide(e1.Curve.Center, e2.Curve.Center)
|
||||
self.assertCoincide(e1.Curve.Axis, -e2.Curve.Axis)
|
||||
else:
|
||||
if PathGeom.pointsCoincide(e1.Vertexes[0].Point, e2.Vertexes[0].Point):
|
||||
self.assertCoincide(e1.Vertexes[-1].Point, e2.Vertexes[-1].Point)
|
||||
else:
|
||||
self.assertCoincide(e1.Vertexes[0].Point, e2.Vertexes[-1].Point)
|
||||
self.assertCoincide(e1.Vertexes[-1].Point, e2.Vertexes[0].Point)
|
||||
pm1 = e1.valueAt((e1.FirstParameter + e1.LastParameter)/2)
|
||||
pm2 = e2.valueAt((e2.FirstParameter + e2.LastParameter)/2)
|
||||
self.assertCoincide(pm1, pm2)
|
||||
|
||||
|
||||
@@ -145,12 +145,12 @@ class TestPathGeom(PathTestBase):
|
||||
"""Verify isVertical/isHorizontal for faces"""
|
||||
|
||||
# planes
|
||||
xPlane = Part.makePlane(100, 100, FreeCAD.Vector(), FreeCAD.Vector(1, 0, 0))
|
||||
yPlane = Part.makePlane(100, 100, FreeCAD.Vector(), FreeCAD.Vector(0, 1, 0))
|
||||
zPlane = Part.makePlane(100, 100, FreeCAD.Vector(), FreeCAD.Vector(0, 0, 1))
|
||||
xyPlane = Part.makePlane(100, 100, FreeCAD.Vector(), FreeCAD.Vector(1, 1, 0))
|
||||
xzPlane = Part.makePlane(100, 100, FreeCAD.Vector(), FreeCAD.Vector(1, 0, 1))
|
||||
yzPlane = Part.makePlane(100, 100, FreeCAD.Vector(), FreeCAD.Vector(0, 1, 1))
|
||||
xPlane = Part.makePlane(100, 100, Vector(), Vector(1, 0, 0))
|
||||
yPlane = Part.makePlane(100, 100, Vector(), Vector(0, 1, 0))
|
||||
zPlane = Part.makePlane(100, 100, Vector(), Vector(0, 0, 1))
|
||||
xyPlane = Part.makePlane(100, 100, Vector(), Vector(1, 1, 0))
|
||||
xzPlane = Part.makePlane(100, 100, Vector(), Vector(1, 0, 1))
|
||||
yzPlane = Part.makePlane(100, 100, Vector(), Vector(0, 1, 1))
|
||||
|
||||
self.assertTrue(PathGeom.isVertical(xPlane))
|
||||
self.assertTrue(PathGeom.isVertical(yPlane))
|
||||
@@ -167,12 +167,12 @@ class TestPathGeom(PathTestBase):
|
||||
self.assertFalse(PathGeom.isHorizontal(yzPlane))
|
||||
|
||||
# cylinders
|
||||
xCylinder = [f for f in Part.makeCylinder(1, 1, FreeCAD.Vector(), FreeCAD.Vector(1, 0, 0)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
yCylinder = [f for f in Part.makeCylinder(1, 1, FreeCAD.Vector(), FreeCAD.Vector(0, 1, 0)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
zCylinder = [f for f in Part.makeCylinder(1, 1, FreeCAD.Vector(), FreeCAD.Vector(0, 0, 1)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
xyCylinder = [f for f in Part.makeCylinder(1, 1, FreeCAD.Vector(), FreeCAD.Vector(1, 1, 0)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
xzCylinder = [f for f in Part.makeCylinder(1, 1, FreeCAD.Vector(), FreeCAD.Vector(1, 0, 1)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
yzCylinder = [f for f in Part.makeCylinder(1, 1, FreeCAD.Vector(), FreeCAD.Vector(0, 1, 1)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
xCylinder = [f for f in Part.makeCylinder(1, 1, Vector(), Vector(1, 0, 0)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
yCylinder = [f for f in Part.makeCylinder(1, 1, Vector(), Vector(0, 1, 0)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
zCylinder = [f for f in Part.makeCylinder(1, 1, Vector(), Vector(0, 0, 1)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
xyCylinder = [f for f in Part.makeCylinder(1, 1, Vector(), Vector(1, 1, 0)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
xzCylinder = [f for f in Part.makeCylinder(1, 1, Vector(), Vector(1, 0, 1)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
yzCylinder = [f for f in Part.makeCylinder(1, 1, Vector(), Vector(0, 1, 1)).Faces if type(f.Surface) == Part.Cylinder][0]
|
||||
|
||||
self.assertTrue(PathGeom.isHorizontal(xCylinder))
|
||||
self.assertTrue(PathGeom.isHorizontal(yCylinder))
|
||||
@@ -381,3 +381,59 @@ class TestPathGeom(PathTestBase):
|
||||
pl = e[1].valueAt((e[1].FirstParameter + e[1].LastParameter)/2)
|
||||
self.assertCurve(e[0], p1, p12, p2)
|
||||
self.assertCurve(e[1], p2, p23, p3)
|
||||
|
||||
def test70(self):
|
||||
'''Flip a line.'''
|
||||
edge = Part.Edge(Part.Line(Vector(0,0,0), Vector(3, 2, 1)))
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.Edge(Part.Line(Vector(0,0,0), Vector(-3, -2, -1)))
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
|
||||
def test71(self):
|
||||
'''Flip a line segment.'''
|
||||
edge = Part.Edge(Part.LineSegment(Vector(0,0,0), Vector(3, 2, 1)))
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.Edge(Part.LineSegment(Vector(4,2,1), Vector(-3, -7, 9)))
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.makeLine(Vector(1,0,3), Vector(3, 2, 1))
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
|
||||
def test72(self):
|
||||
'''Flip a circle'''
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, 1))
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, -1))
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
|
||||
def test73(self):
|
||||
'''Flip an arc'''
|
||||
# make sure all 4 quadrants work
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, 1), 45, 90)
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, 1), 100, 170)
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, 1), 200, 250)
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, 1), 300, 340)
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
|
||||
# and the other way around too
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, -1), 45, 90)
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, -1), 100, 170)
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, -1), 200, 250)
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
edge = Part.makeCircle(3, Vector(1, 3, 2), Vector(0, 0, -1), 300, 340)
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
|
||||
|
||||
def xtest75(self):
|
||||
'''Flip a b-spline'''
|
||||
# Disabling for now, there's a bit of a difference
|
||||
spline = Part.BSplineCurve()
|
||||
spline.interpolate([Vector(1,2,3), Vector(-3,0,7), Vector(-3,1,9), Vector(1, 3, 5)])
|
||||
edge = Part.Edge(spline)
|
||||
self.assertEdgeShapesMatch(edge, PathGeom.flipEdge(edge))
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user