DesignScript
- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic to the Top
- Bookmark
- Subscribe
- Printer Friendly Page
Some more curves
- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content
Hi,
DesignScript is relatively poor in native curves (Line, Arc, Circle and BSplineCurve).
I thought it might be interesting to define some others.
I tried to do this as classes with constructors, these classes may be required to evolve with the addition of new features.
The generated curves are spline whose control points or smoothing are calculated from the equations of these curves.
The Catenary, Ellipse, EllpticalArc and Parabola classes:
import("ProtoGeometry.dll");
import("Math.dll");
class Catenary
{
Curve : Curve;
Chord : double;
Param : double;
Sagitta : double;
Length : double;
def argCosh(x : double)
{
return = Math.Log(x + Math.Sqrt(x * x - 1));
}
constructor FromChordParam(chord : double, param : double, numPts : int)
{
Chord = chord;
Param = param;
Sagitta = param * Math.Cosh(chord / (2 * param)) - param;
Length = 2 * param * Math.Sinh(chord / (2 * param));
x = chord / -2..chord / 2..#numPts;
y = param * Math.Cosh(x / param);
Curve = BSplineCurve.ByPoints(Point.ByCoordinates(x, y, 0));
}
constructor FromLenthSagitta(length : double, sagitta : double, numPts : int)
{
Length = length;
Sagitta = sagitta;
Param = (length * length - 4 * sagitta * sagitta) / (8 * sagitta);
Chord = 2 * Param * argCosh((sagitta + Param) / Param);
x = Chord / -2..Chord / 2..#numPts;
y = Param * Math.Cosh(x / Param);
Curve = BSplineCurve.ByPoints(Point.ByCoordinates(x, y, 0));
}
}
class Ellipse
{
Curve : Curve;
constructor FromRadii(majRadius : double, minRadius : double)
{
Curve = Circle.ByCenterPointRadius(Point.ByCoordinates(0, 0, 0), 1)
.Transform(CoordinateSystem.WCS,
CoordinateSystem.Identity().Scale(majRadius, minRadius, 1));
}
}
class EllipticalArc
{
Curve : Curve;
constructor FromRadii(majRadius : double, minRadius : double, startAngle : double, sweepAngle : double)
{
endAngle = startAngle + sweepAngle;
startParam = Math.Atan(majRadius * Math.Tan(startAngle) / minRadius);
endParam = Math.Atan(majRadius * Math.Tan(endAngle) / minRadius);
[Imperative]
{
if (startAngle == 0 || startAngle == 90 || startAngle == 180 || startAngle == 270 || startAngle == 360)
startParam = startAngle;
else if (startAngle > 90 && startAngle < 270)
startParam = startParam + 180;
if (endAngle == 0 || endAngle == 90 || endAngle == 180 || endAngle == 270 || endAngle == 360)
endParam = endAngle;
else if (endAngle > 90 && endAngle < 270)
endParam = endParam + 180;
if (endParam <= startParam)
endParam = endParam + 360;
}
Curve = Arc.ByCenterPointRadiusAngle(Point.ByCoordinates(0 , 0, 0),
1, startParam, endParam - startParam, Vector.ByCoordinates(0, 0, 1))
.Transform(CoordinateSystem.WCS,
CoordinateSystem.Identity().Scale(majRadius, minRadius, 1));
}
}
class Parabola
{
Curve : Curve;
Focus : Point;
constructor FromChordSagitta(chord : double, sagitta : double, numPts : int, focusVisible : bool)
{
a = 4 * sagitta / (chord * chord);
Focus = Point.ByCoordinates(0, 1 / (4 * a), 0).SetVisibility(focusVisible);
x = chord / - 2..chord / 2..#numPts;
y = a * x * x;
Curve = BSplineCurve.ByPoints(Point.ByCoordinates(x, y, 0));
}
}
Using examples
Ellipses with incremented major axis.
el = Ellipse.FromRadii(30..80..5, 30);
Parabolas with decremented chords and incrmented sagittas.
parabs = Parabola.FromChordSagitta(200..100..-10, 20..120..10, 19, false);
Catenaries with incremented params.
Each curve is moved so that start and end point lies ont the X axis. This is done using the Param and Sagitta properties of the Catenary instance.
def catenar(chord : double, param : double, numPts : int)
{
cat = Catenary.FromChordParam(chord, param, numPts);
return = cat.Curve.Translate(0, -cat.Param - cat.Sagitta, 0);
}
cats = catenar(160, 35..75..#10, 19);
Re: Some more curves
- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content
Thanks!
These definitions are very useful.
Re: Some more curves
- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content
This is great! How did you find writing your own classes? Any surprises?
Luke
Re: Some more curves
- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content
Thanks Luke.
I found an example of class in the tutorial and try to build my own ones.
Re: Some more curves
- Mark as New
- Bookmark
- Subscribe
- Subscribe to RSS Feed
- Highlight
- Email to a Friend
- Report Inappropriate Content
One more: a cylindrical helix.
The constructor arguments are:
- the radius
- the total height
- the total angle, if the input is negative the helix turns clockwise
import("ProtoGeometry.dll");
import("Math.dll");
class Helix
{
Curve : Curve;
constructor FromRadiusHeightAngle(radius : double, height : double, totalAngle : double)
{
pi = 3.141592653589793;
numPts = Math.Abs(Math.Round(totalAngle / 15)) + 1;
step = height / (numPts - 1);
ccw = Math.Sign(totalAngle);
tanZ = (180 * height) / (pi * totalAngle * radius);
startTan = Vector.ByCoordinates(0, ccw, ccw * tanZ);
endTan = Vector.ByCoordinates(ccw * -Math.Sin(totalAngle), ccw * Math.Cos(totalAngle), ccw * tanZ);
x = radius * Math.Cos(0 .. totalAngle .. #numPts);
y = radius * Math.Sin(0 .. totalAngle .. #numPts);
z = step * (0 .. numPts);
Curve = BSplineCurve.ByPoints(Point.ByCoordinates(x, y, z), startTan, endTan);
}
}

