function for piece-wise length estimation.
And a recursive function to fit control points for the length of your pleasure.
function AdjustBezier(v,l, precision = 0.00001)=
l<norm(v[0]-v[3])?
let(e=echo("Cant be that short, sorry"))[v[0],v[0] ,v[3] ,v[3]]:
let(
current_lenght=len3bz(v),
error=l/current_lenght,
e=echo(l,current_lenght,error),
new_v=[v[0],v[0]+(v[1]-v[0])*error,v[3]+(v[2]-v[3])*error,v[3]]
)
abs(1-error)>precision?AdjustBezier(new_v,l):v;
function len3bz(v, precision = 0.001, t = 0, acc = 0) =
t > 1 ? acc :
len3bz(v, precision, t + precision, acc
+ norm(bez2(t, v) - bez2(t + precision, v)));
function bez2(t, v) = (len(v) > 2) ? bez2(t, [
for (i = [0: len(v) - 2]) v[i]* (t) + v[i + 1] * (1 - t)
]): v[0]* (t) + v[1]* (1 - t) ;
module ShowControl(v) { // translate(t(v[0])) sphere(v[0][3]);
for (i = [1: len(v) - 1]) {
// vg translate(t(v[i])) sphere(v[i][3]);
hull() {
translate(t(v[i])) sphere(0.5);
translate(t(v[i - 1])) sphere(0.5);
}
}
}
module ShowBezier(v,steps=50)
{ // translate(t(v[0])) sphere(v[0][3]);
step=1/steps;
for (i = [-step:step: 1+step]) {
// vg translate(t(v[i])) sphere(v[i][3]);
hull() {
translate(t(bez2(clamp(i), v) ))sphere(1);
translate(t(bez2(clamp(i+step), v))) sphere(1);
}
}
}
function t(v) = [v.x, v.y, v.z];
function clamp(a, b = 0, c = 1) = min(max(a, b), c);
MyBezier=[[0,0,0],[0,0,10],[50,0,50],[50,10,50]];
Newlengh=175;
ShowControl(MyBezier) ;
ShowBezier(MyBezier) ;
echo(len3bz(MyBezier));
MyNewBezier=AdjustBezier(MyBezier,Newlengh) ;
color("red"){
ShowControl(MyNewBezier) ;
ShowBezier(MyNewBezier) ;
echo(len3bz(MyNewBezier));}
No comments:
Post a Comment