iva*_*off 13 math graphics drawing coordinates
假设我正在使用一些图形API,它允许我通过指定4个必要点来绘制贝塞尔曲线: 开始,结束,两个控制点.
我可以重复使用此功能来绘制"原始"曲线的x%(通过调整控制点和终点)吗?
还是不可能?
不必要的信息,如果有人关心:
我正在使用Java的Path2D绘制贝塞尔曲线:
Path2D p = new GeneralPath();
p.moveTo(x1, y1);
p.curveTo(bx1, by1, bx2, by2, x2, y2);
g2.draw(p);
Run Code Online (Sandbox Code Playgroud)Naa*_*aff 19
你需要的是De Casteljau算法.这样您就可以将曲线分割成您想要的任何片段.
但是,由于你只处理三次曲线,我想建议一个稍微容易使用的配方,它会给你一个段t0到t1哪里0 <= t0 <= t1 <= 1.这是一些伪代码:
u0 = 1.0 - t0
u1 = 1.0 - t1
qxa = x1*u0*u0 + bx1*2*t0*u0 + bx2*t0*t0
qxb = x1*u1*u1 + bx1*2*t1*u1 + bx2*t1*t1
qxc = bx1*u0*u0 + bx2*2*t0*u0 + x2*t0*t0
qxd = bx1*u1*u1 + bx2*2*t1*u1 + x2*t1*t1
qya = y1*u0*u0 + by1*2*t0*u0 + by2*t0*t0
qyb = y1*u1*u1 + by1*2*t1*u1 + by2*t1*t1
qyc = by1*u0*u0 + by2*2*t0*u0 + y2*t0*t0
qyd = by1*u1*u1 + by2*2*t1*u1 + y2*t1*t1
xa = qxa*u0 + qxc*t0
xb = qxa*u1 + qxc*t1
xc = qxb*u0 + qxd*t0
xd = qxb*u1 + qxd*t1
ya = qya*u0 + qyc*t0
yb = qya*u1 + qyc*t1
yc = qyb*u0 + qyd*t0
yd = qyb*u1 + qyd*t1
Run Code Online (Sandbox Code Playgroud)
然后,只需画所形成的贝塞尔曲线(xa,ya),(xb,yb),(xc,yc)和(xd,yd).
请注意,t0并且t1不是曲线距离的精确百分比,而是曲线参数空间.如果你绝对必须有距离那么事情要困难得多.尝试一下,看看它是否符合你的需要.
编辑:值得注意的是,如果其中一个t0或者t1是0或1(即你只想从一侧修剪),这些方程式会简化很多.
而且,这种关系0 <= t0 <= t1 <= 1并不是一个严格的要求.例如t0 = 1和t1 = 0可向后用于"翻转"的曲线,或t0 = 0与t1 = 1.5可用于延长曲线超出原始端.但是,如果您尝试将曲线延伸超出[0,1]范围,则曲线可能与您预期的不同.
编辑2:在我的原始答案超过3年后,MvG在我的方程式中指出了一个错误.我忘记了最后一步(额外的线性插值来获得最终控制点).上面的等式已得到纠正.
MvG*_*MvG 10
在另一个问题的答案中,我只包括一些公式来计算三次曲线的一部分的控制点.当u = 1- t时,立方贝塞尔曲线被描述为
B(t)= u 3 P 1 + 3 u 2 t P 2 + 3 ut 2 P 3 + t 3 P 4
P 1是曲线的起点,P 4是其终点.P 2和P 3是控制点.
给定两个参数t 0和t 1(并且u 0 =(1- t 0),u 1 =(1- t 1)),区间[ t 0,t 1 ] 中的曲线部分由下式描述:新的控制点
请注意,在带括号的表达式中,至少有一些术语是相同的并且可以组合.我没有这样做,因为这里所说的公式将使模式更清晰,我相信.您可以单独为x和y方向执行这些计算,以计算新的控制点.
注意,t的参数范围的给定百分比通常不对应于长度的相同百分比.因此,您很可能必须在曲线上进行积分,以将路径长度转换回参数.或者你使用一些近似值.
| 归档时间: |
|
| 查看次数: |
4525 次 |
| 最近记录: |