[OpenSCAD] Improve helical extrusion, fix scaling

Modify the auxiliary spine to be a true helix, resulting in a much
smoother linear extrusion when a twist angle is applied. This also
corrects a bug in the scaling during linear extrusion, where non-uniform
scaling was not handled correctly.
This commit is contained in:
Chris Hennes
2021-03-18 11:39:34 -05:00
committed by wwmayer
parent a0464d1b00
commit 57c93cd6b3
2 changed files with 80 additions and 46 deletions

View File

@@ -26,6 +26,7 @@ import OpenSCAD
import importCSG
import tempfile
import os
import math
from os.path import join
@@ -244,22 +245,26 @@ polyhedron(
self.assertAlmostEqual (object.Shape.Volume, 4000.000, 3)
FreeCAD.closeDocument(doc.Name)
doc = self.utility_create_scad("linear_extrude(height = 20, scale = 0.2) square([20, 10], center = true);", "linear_extrude_scale")
object = doc.ActiveObject
self.assertTrue (object is not None)
self.assertAlmostEqual (object.Shape.Volume, 1945.2745, 3)
FreeCAD.closeDocument(doc.Name)
doc = self.utility_create_scad("linear_extrude(height = 20, twist = 90) square([20, 10], center = true);", "linear_extrude_twist")
object = doc.ActiveObject
self.assertTrue (object is not None)
self.assertAlmostEqual (object.Shape.Volume, 3999.9961, 3)
self.assertAlmostEqual (object.Shape.Volume, 4000.000, 2)
FreeCAD.closeDocument(doc.Name)
doc = self.utility_create_scad("linear_extrude(height = 40, twist = 180, scale=0.25) square([20, 10], center = true);", "linear_extrude_twist")
doc = self.utility_create_scad("linear_extrude(height = 20, scale = 0.2) square([20, 10], center = true);", "linear_extrude_scale")
object = doc.ActiveObject
self.assertTrue (object is not None)
self.assertAlmostEqual (object.Shape.Volume, 4144.9071, 3)
h = 20
a1 = 20*10
a2 = 20*0.2 * 10*0.2
expected_volume = (h/3) * (a1+a2+math.sqrt(a1*a2))
self.assertAlmostEqual (object.Shape.Volume, expected_volume, 3)
FreeCAD.closeDocument(doc.Name)
doc = self.utility_create_scad("linear_extrude(height = 20, twist = 180, scale=0.2) square([20, 10], center = true);", "linear_extrude_twist_scale")
object = doc.ActiveObject
self.assertTrue (object is not None)
self.assertAlmostEqual (object.Shape.Volume, expected_volume, 2)
FreeCAD.closeDocument(doc.Name)
def test_import_rotate_extrude_file(self):
@@ -369,7 +374,36 @@ resize(newsize = [0,0,10], auto = [0,0,0]) {
os.chdir(cwd)
def test_import_projection(self):
pass
base_shape = "linear_extrude(height=5,center=true,twist=90,scale=0.5){square([1,1],center=true);}"
hole = "cube([0.25,0.25,6],center=true);"
cut_shape = f"difference() {{ {base_shape} {hole} }}"
doc = self.utility_create_scad(f"projection(cut=true) {base_shape}", "projection_slice_square")
object = doc.getObject("projection_cut")
self.assertTrue (object is not None)
self.assertAlmostEqual (object.Shape.Area, 0.75*0.75, 3)
FreeCAD.closeDocument(doc.Name)
doc = self.utility_create_scad(f"projection(cut=true) {cut_shape}", "projection_slice_square_with_hole")
object = doc.getObject("projection_cut")
self.assertTrue (object is not None)
self.assertAlmostEqual (object.Shape.Area, 0.75*0.75 - 0.25*0.25, 3)
FreeCAD.closeDocument(doc.Name)
# Unimplemented functionality:
# With cut=false, the twisted unit square projects to a circle of radius sqrt(0.5)
#doc = self.utility_create_scad(f"projection(cut=false) {base_shape}", "projection_circle")
#object = doc.getObject("projection")
#self.assertTrue (object is not None)
#self.assertAlmostEqual (object.Shape.Area, 2*math.pi*math.sqrt(2), 3)
#FreeCAD.closeDocument(doc.Name)
#doc = self.utility_create_scad(f"projection(cut=false) {cut_shape}", "projection_circle_with_hole")
#object = doc.getObject("projection")
#self.assertTrue (object is not None)
#self.assertAlmostEqual (object.Shape.Area, 2*math.pi*math.sqrt(0.5) - 0.125, 3)
#FreeCAD.closeDocument(doc.Name)
def test_import_hull(self):
pass