| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| |
|
| | from math import pi |
| | import unittest |
| |
|
| | import FreeCAD |
| | from FreeCAD import Base |
| | import Part |
| | import Sketcher |
| | import TestSketcherApp |
| |
|
| | """ Test various helixes """ |
| |
|
| |
|
| | class TestHelix(unittest.TestCase): |
| | """Test various helixes""" |
| |
|
| | def setUp(self): |
| | self.Doc = FreeCAD.newDocument("PartDesignTestHelix") |
| |
|
| | def testHelicalTubeCase(self): |
| | body = self.Doc.addObject("PartDesign::Body", "Body") |
| | sketch = body.newObject("Sketcher::SketchObject", "Sketch") |
| | sketch.AttachmentSupport = (self.Doc.getObject("XY_Plane"), [""]) |
| | sketch.MapMode = "FlatFace" |
| |
|
| | geoList = [] |
| | geoList.append(Part.Circle(Base.Vector(-40.0, 0.0, 0.0), Base.Vector(0.0, 0.0, 1.0), 7.5)) |
| | geoList.append(Part.Circle(Base.Vector(-40.0, 0.0, 0.0), Base.Vector(0.0, 0.0, 1.0), 10.0)) |
| | sketch.addGeometry(geoList, False) |
| | del geoList |
| |
|
| | sketch.addConstraint(Sketcher.Constraint("PointOnObject", 0, 3, -1)) |
| | sketch.addConstraint(Sketcher.Constraint("Coincident", 1, 3, 0, 3)) |
| | self.Doc.recompute() |
| |
|
| | helix = body.newObject("PartDesign::AdditiveHelix", "AdditiveHelix") |
| | helix.Profile = sketch |
| | helix.ReferenceAxis = (sketch, ["V_Axis"]) |
| | helix.Mode = 0 |
| | helix.Pitch = 35 |
| | helix.Height = 100 |
| | helix.Turns = 3 |
| | helix.Angle = 0 |
| | helix.Growth = 0 |
| | helix.LeftHanded = 0 |
| | helix.Reversed = 0 |
| |
|
| | self.Doc.recompute() |
| | self.assertEqual(len(helix.Shape.Solids), 1) |
| |
|
| | def testCircleQ1(self): |
| | """Test helix based on circle in Quadrant 1""" |
| | body = self.Doc.addObject("PartDesign::Body", "Body") |
| | profileSketch = self.Doc.addObject("Sketcher::SketchObject", "ProfileSketch") |
| | body.addObject(profileSketch) |
| | TestSketcherApp.CreateCircleSketch(profileSketch, (2, 0), 1) |
| | self.Doc.recompute() |
| | helix = self.Doc.addObject("PartDesign::AdditiveHelix", "AdditiveHelix") |
| | body.addObject(helix) |
| | helix.Profile = profileSketch |
| | helix.ReferenceAxis = (profileSketch, "V_Axis") |
| | helix.Placement = FreeCAD.Placement( |
| | FreeCAD.Vector(0, 0, 0), |
| | FreeCAD.Rotation(FreeCAD.Vector(0, 0, 1), 0), |
| | FreeCAD.Vector(0, 0, 0), |
| | ) |
| | helix.Pitch = 3 |
| | helix.Height = 9 |
| | helix.Turns = 2 |
| | helix.Angle = 0 |
| | helix.Mode = 1 |
| | self.Doc.recompute() |
| | self.assertAlmostEqual(helix.Shape.Volume, 78.957, places=3) |
| |
|
| | helix.Angle = 25 |
| | self.Doc.recompute() |
| | self.assertAlmostEqual(helix.Shape.Volume, 134.17, places=2) |
| |
|
| | profileSketch.addGeometry( |
| | Part.Circle(FreeCAD.Vector(2, 0, 0), FreeCAD.Vector(0, 0, 1), 0.5) |
| | ) |
| | self.Doc.recompute() |
| | self.assertAlmostEqual(helix.Shape.Volume, 100.63, places=2) |
| |
|
| | def testRectangle(self): |
| | """Test helix based on a rectangle""" |
| | body = self.Doc.addObject("PartDesign::Body", "GearBody") |
| | gearSketch = self.Doc.addObject("Sketcher::SketchObject", "GearSketch") |
| | body.addObject(gearSketch) |
| | TestSketcherApp.CreateRectangleSketch(gearSketch, (0, 0), (5, 5)) |
| | self.Doc.recompute() |
| |
|
| | |
| | |
| | |
| | helix = self.Doc.addObject("PartDesign::AdditiveHelix", "AdditiveHelix") |
| | body.addObject(helix) |
| | helix.Profile = gearSketch |
| | helix.ReferenceAxis = (gearSketch, "V_Axis") |
| | helix.Placement = FreeCAD.Placement( |
| | FreeCAD.Vector(0, 0, 0), |
| | FreeCAD.Rotation(FreeCAD.Vector(0, 0, 1), 0), |
| | FreeCAD.Vector(0, 0, 0), |
| | ) |
| |
|
| | helix.Pitch = 50 |
| | helix.Height = 150 |
| | helix.Turns = 3 |
| | helix.Angle = 0 |
| | helix.Mode = 0 |
| | self.Doc.recompute() |
| | bbox = helix.Shape.BoundBox |
| | self.assertAlmostEqual(bbox.YMin, 0) |
| | |
| | |
| | |
| | expected = pi * 25 * 5 * 3 |
| | self.assertAlmostEqual(helix.Shape.Volume, expected, places=2) |
| |
|
| | def testGiantHelix(self): |
| | """Test giant helix""" |
| | _OCC_VERSION = [int(v) for v in Part.OCC_VERSION.split(".") if v.isnumeric()] |
| | if _OCC_VERSION[0] > 7 or (_OCC_VERSION[0] == 7 and _OCC_VERSION[1] > 3): |
| | mine = -1 |
| | maxe = 10 |
| | else: |
| | mine = -1 |
| | maxe = 9 |
| | for iexponent in range(mine, maxe): |
| | exponent = float(iexponent) |
| | body = self.Doc.addObject("PartDesign::Body", "GearBody") |
| | gearSketch = self.Doc.addObject("Sketcher::SketchObject", "GearSketch") |
| | body.addObject(gearSketch) |
| | TestSketcherApp.CreateRectangleSketch( |
| | gearSketch, (10 * (10**exponent), 0), (1 * (10**exponent), 1 * (10**exponent)) |
| | ) |
| | xz_plane = body.Origin.OriginFeatures[4] |
| | gearSketch.AttachmentSupport = xz_plane |
| | gearSketch.MapMode = "FlatFace" |
| | self.Doc.recompute() |
| |
|
| | helix = self.Doc.addObject("PartDesign::AdditiveHelix", "AdditiveHelix") |
| | body.addObject(helix) |
| | helix.Profile = gearSketch |
| | helix.ReferenceAxis = (gearSketch, "V_Axis") |
| | helix.Placement = FreeCAD.Placement( |
| | FreeCAD.Vector(0, 0, 0), |
| | FreeCAD.Rotation(FreeCAD.Vector(0, 0, 1), 0), |
| | FreeCAD.Vector(0, 0, 0), |
| | ) |
| |
|
| | helix.Pitch = 2 * (10**exponent) |
| | helix.Turns = 2 |
| | helix.Height = helix.Turns * helix.Pitch |
| | helix.Angle = 0 |
| | helix.Mode = 0 |
| | self.Doc.recompute() |
| |
|
| | self.assertTrue(helix.Shape.isValid()) |
| | bbox = helix.Shape.BoundBox |
| | self.assertAlmostEqual(bbox.ZMin / ((10**exponent) ** 3), 0, places=4) |
| | |
| | |
| | |
| | expected = ( |
| | pi |
| | * (((11 * (10**exponent)) ** 2) - ((10 * (10**exponent)) ** 2)) |
| | * 1 |
| | * (10**exponent) |
| | * helix.Turns |
| | ) |
| | self.assertAlmostEqual( |
| | helix.Shape.Volume / ((10**exponent) ** 3), |
| | expected / ((10**exponent) ** 3), |
| | places=2, |
| | ) |
| |
|
| | def testGiantHelixAdditive(self): |
| | """Test giant helix added to Cylinder""" |
| | _OCC_VERSION = [int(v) for v in Part.OCC_VERSION.split(".") if v.isnumeric()] |
| | if _OCC_VERSION[0] > 7 or (_OCC_VERSION[0] == 7 and _OCC_VERSION[1] > 3): |
| | mine = -1 |
| | maxe = 8 |
| | else: |
| | mine = -1 |
| | maxe = 6 |
| | for iexponent in range(mine, maxe): |
| | exponent = float(iexponent) |
| | body = self.Doc.addObject("PartDesign::Body", "GearBody") |
| | gearSketch = self.Doc.addObject("Sketcher::SketchObject", "GearSketch") |
| | body.addObject(gearSketch) |
| | TestSketcherApp.CreateRectangleSketch( |
| | gearSketch, (10 * (10**exponent), 0), (1 * (10**exponent), 1 * (10**exponent)) |
| | ) |
| | xz_plane = body.Origin.OriginFeatures[4] |
| | gearSketch.AttachmentSupport = xz_plane |
| | gearSketch.MapMode = "FlatFace" |
| | self.Doc.recompute() |
| |
|
| | cylinder = self.Doc.addObject("PartDesign::AdditiveCylinder", "Cylinder") |
| | cylinder.Radius = 10 * (10**exponent) |
| | cylinder.Height = 8 * (10**exponent) |
| | cylinder.Angle = 360 |
| | body.addObject(cylinder) |
| | self.Doc.recompute() |
| |
|
| | helix = self.Doc.addObject("PartDesign::AdditiveHelix", "AdditiveHelix") |
| | body.addObject(helix) |
| | helix.Profile = gearSketch |
| | helix.ReferenceAxis = (gearSketch, "V_Axis") |
| | helix.Placement = FreeCAD.Placement( |
| | FreeCAD.Vector(0, 0, 0), |
| | FreeCAD.Rotation(FreeCAD.Vector(0, 0, 1), 0), |
| | FreeCAD.Vector(0, 0, 0), |
| | ) |
| |
|
| | helix.Pitch = 2 * (10**exponent) |
| | helix.Turns = 2.5 |
| | helix.Height = helix.Turns * helix.Pitch |
| | helix.Angle = 0 |
| | helix.Mode = 0 |
| | self.Doc.recompute() |
| |
|
| | self.assertTrue(helix.Shape.isValid()) |
| | bbox = helix.Shape.BoundBox |
| | self.assertAlmostEqual(bbox.ZMin / ((10**exponent) ** 3), 0, places=4) |
| | |
| | |
| | |
| | cyl = pi * ((10 * (10**exponent)) ** 2) * 8 * (10**exponent) |
| | expected = cyl + ( |
| | pi |
| | * (((11 * (10**exponent)) ** 2) - ((10 * (10**exponent)) ** 2)) |
| | * 1 |
| | * (10**exponent) |
| | * helix.Turns |
| | ) |
| | self.assertAlmostEqual( |
| | helix.Shape.Volume / ((10**exponent) ** 3), |
| | expected / ((10**exponent) ** 3), |
| | places=2, |
| | ) |
| |
|
| | def testGiantHelixSubtractive(self): |
| | """Test giant helix subtracted from Cylinder""" |
| | _OCC_VERSION = [int(v) for v in Part.OCC_VERSION.split(".") if v.isnumeric()] |
| | if _OCC_VERSION[0] > 7 or (_OCC_VERSION[0] == 7 and _OCC_VERSION[1] > 3): |
| | mine = -1 |
| | maxe = 8 |
| | else: |
| | mine = -1 |
| | maxe = 6 |
| | for iexponent in range(mine, maxe): |
| | exponent = float(iexponent) |
| | body = self.Doc.addObject("PartDesign::Body", "GearBody") |
| | gearSketch = self.Doc.addObject("Sketcher::SketchObject", "GearSketch") |
| | body.addObject(gearSketch) |
| | TestSketcherApp.CreateRectangleSketch( |
| | gearSketch, (10 * (10**exponent), 0), (1 * (10**exponent), 1 * (10**exponent)) |
| | ) |
| | xz_plane = body.Origin.OriginFeatures[4] |
| | gearSketch.AttachmentSupport = xz_plane |
| | gearSketch.MapMode = "FlatFace" |
| | self.Doc.recompute() |
| |
|
| | cylinder = self.Doc.addObject("PartDesign::AdditiveCylinder", "Cylinder") |
| | cylinder.Radius = 11 * (10**exponent) |
| | cylinder.Height = 8 * (10**exponent) |
| | cylinder.Angle = 360 |
| | body.addObject(cylinder) |
| | self.Doc.recompute() |
| |
|
| | helix = self.Doc.addObject("PartDesign::SubtractiveHelix", "SubtractiveHelix") |
| | body.addObject(helix) |
| | helix.Profile = gearSketch |
| | helix.ReferenceAxis = (gearSketch, "V_Axis") |
| | helix.Placement = FreeCAD.Placement( |
| | FreeCAD.Vector(0, 0, 0), |
| | FreeCAD.Rotation(FreeCAD.Vector(0, 0, 1), 0), |
| | FreeCAD.Vector(0, 0, 0), |
| | ) |
| |
|
| | helix.Pitch = 2 * (10**exponent) |
| | helix.Turns = 2.5 |
| | helix.Height = helix.Turns * helix.Pitch |
| | helix.Angle = 0 |
| | helix.Mode = 0 |
| | self.Doc.recompute() |
| |
|
| | self.assertTrue(helix.Shape.isValid()) |
| | bbox = helix.Shape.BoundBox |
| | self.assertAlmostEqual(bbox.ZMin / ((10**exponent) ** 3), 0, places=4) |
| | |
| | |
| | |
| | cyl = pi * ((11 * (10**exponent)) ** 2) * 8 * (10**exponent) |
| | expected = cyl - ( |
| | pi |
| | * (((11 * (10**exponent)) ** 2) - ((10 * (10**exponent)) ** 2)) |
| | * 1 |
| | * (10**exponent) |
| | * helix.Turns |
| | ) |
| | self.assertAlmostEqual( |
| | helix.Shape.Volume / ((10**exponent) ** 3), |
| | expected / ((10**exponent) ** 3), |
| | places=2, |
| | ) |
| |
|
| | def testCone(self): |
| | """Test helix following a cone""" |
| | body = self.Doc.addObject("PartDesign::Body", "ConeBody") |
| | coneSketch = self.Doc.addObject("Sketcher::SketchObject", "ConeSketch") |
| | body.addObject(coneSketch) |
| |
|
| | geoList = [] |
| | geoList.append(Part.LineSegment(FreeCAD.Vector(-5, -5, 0), FreeCAD.Vector(-3, 0, 0))) |
| | geoList.append(Part.LineSegment(FreeCAD.Vector(-3, 0, 0), FreeCAD.Vector(-2, 0, 0))) |
| | geoList.append(Part.LineSegment(FreeCAD.Vector(-2, 0, 0), FreeCAD.Vector(-4, -5, 0))) |
| | geoList.append(Part.LineSegment(FreeCAD.Vector(-4, -5, 0), FreeCAD.Vector(-5, -5, 0))) |
| | (l1, l2, l3, l4) = coneSketch.addGeometry(geoList) |
| |
|
| | conList = [] |
| | conList.append(Sketcher.Constraint("Coincident", 0, 2, 1, 1)) |
| | conList.append(Sketcher.Constraint("Coincident", 1, 2, 2, 1)) |
| | conList.append(Sketcher.Constraint("Coincident", 2, 2, 3, 1)) |
| | conList.append(Sketcher.Constraint("Coincident", 3, 2, 0, 1)) |
| | conList.append(Sketcher.Constraint("Horizontal", 1)) |
| | conList.append( |
| | Sketcher.Constraint("Angle", l3, 1, -2, 2, FreeCAD.Units.Quantity("30.000000 deg")) |
| | ) |
| | conList.append(Sketcher.Constraint("DistanceX", 1, 2, -5)) |
| | conList.append(Sketcher.Constraint("DistanceY", 1, 2, 0)) |
| | conList.append(Sketcher.Constraint("Equal", 0, 2)) |
| | conList.append(Sketcher.Constraint("Equal", 1, 3)) |
| | conList.append(Sketcher.Constraint("DistanceY", 0, 50)) |
| | conList.append(Sketcher.Constraint("DistanceX", 1, 10)) |
| | coneSketch.addConstraint(conList) |
| |
|
| | xz_plane = body.Origin.OriginFeatures[4] |
| | coneSketch.AttachmentSupport = xz_plane |
| | coneSketch.MapMode = "FlatFace" |
| | helix = self.Doc.addObject("PartDesign::AdditiveHelix", "AdditiveHelix") |
| | body.addObject(helix) |
| | helix.Profile = coneSketch |
| | helix.ReferenceAxis = (coneSketch, "V_Axis") |
| | helix.Placement = FreeCAD.Placement( |
| | FreeCAD.Vector(0, 0, 0), |
| | FreeCAD.Rotation(FreeCAD.Vector(0, 0, 1), 0), |
| | FreeCAD.Vector(0, 0, 0), |
| | ) |
| |
|
| | helix.Pitch = 50 |
| | helix.Height = 110 |
| | helix.Turns = 2.2 |
| | helix.Angle = 30 |
| | helix.Mode = 0 |
| | helix.Reversed = True |
| | self.Doc.recompute() |
| | self.assertAlmostEqual(helix.Shape.Volume / 1e5, 3.8828, places=4) |
| |
|
| | def testNegativeCone(self): |
| | """Test helix following a cone with a negative angle""" |
| | body = self.Doc.addObject("PartDesign::Body", "ConeBody") |
| | coneSketch = self.Doc.addObject("Sketcher::SketchObject", "ConeSketch") |
| | body.addObject(coneSketch) |
| |
|
| | geoList = [] |
| | geoList.append(Part.LineSegment(FreeCAD.Vector(5, 5, 0), FreeCAD.Vector(3, 0, 0))) |
| | geoList.append(Part.LineSegment(FreeCAD.Vector(3, 0, 0), FreeCAD.Vector(2, 0, 0))) |
| | geoList.append(Part.LineSegment(FreeCAD.Vector(2, 0, 0), FreeCAD.Vector(4, 5, 0))) |
| | geoList.append(Part.LineSegment(FreeCAD.Vector(4, 5, 0), FreeCAD.Vector(5, 5, 0))) |
| | (l1, l2, l3, l4) = coneSketch.addGeometry(geoList) |
| |
|
| | conList = [] |
| | conList.append(Sketcher.Constraint("Coincident", 0, 2, 1, 1)) |
| | conList.append(Sketcher.Constraint("Coincident", 1, 2, 2, 1)) |
| | conList.append(Sketcher.Constraint("Coincident", 2, 2, 3, 1)) |
| | conList.append(Sketcher.Constraint("Coincident", 3, 2, 0, 1)) |
| | conList.append(Sketcher.Constraint("Horizontal", 1)) |
| | conList.append(Sketcher.Constraint("Angle", l3, 1, -2, 2, FreeCAD.Units.Quantity("30 deg"))) |
| | conList.append(Sketcher.Constraint("DistanceX", 1, 2, -100)) |
| | conList.append(Sketcher.Constraint("DistanceY", 1, 2, 0)) |
| | conList.append(Sketcher.Constraint("Equal", 0, 2)) |
| | conList.append(Sketcher.Constraint("Equal", 1, 3)) |
| | conList.append(Sketcher.Constraint("DistanceY", 0, 50)) |
| | conList.append(Sketcher.Constraint("DistanceX", 1, 10)) |
| | coneSketch.addConstraint(conList) |
| |
|
| | xz_plane = body.Origin.OriginFeatures[4] |
| | coneSketch.AttachmentSupport = xz_plane |
| | coneSketch.MapMode = "FlatFace" |
| | helix = self.Doc.addObject("PartDesign::AdditiveHelix", "AdditiveHelix") |
| | body.addObject(helix) |
| | helix.Profile = coneSketch |
| | helix.ReferenceAxis = (coneSketch, "V_Axis") |
| |
|
| | helix.Pitch = 50 |
| | helix.Height = 110 |
| | helix.Angle = -30 |
| | helix.Mode = 0 |
| | helix.Reversed = False |
| | self.Doc.recompute() |
| | self.assertAlmostEqual(helix.Shape.Volume / 1e5, 6.0643, places=4) |
| |
|
| | def tearDown(self): |
| | FreeCAD.closeDocument("PartDesignTestHelix") |
| |
|