我需要找出在画布贝塞尔曲线的特定点的Y坐标。 你知道,如何找到它呢? 谢谢
Answer 1:
使用德卡斯特里奥算法,你可以找到一个贝塞尔曲线的坐标x和y的任意t,百分比或插值步骤。 因此,在.1会给你的X和Y在从一开始曲线的10%。 .9一件T是90%从一开始,依此类推。
在我们的三次Bezier我们P0(0点),CP0(控制点0),CP1(控制点1),和P1(点1)。
在算法的第一步,我们绘制连接P0和CP0,另一条线连接CP0和CP1,另外还连接CP1和P1线。 那么对于这些线路,我们会发现他们的点的所有3是T%从他们开始。
我会打电话的要点如下:
- P0 - > CP0 = A
- CP0 - > CP1 = B
CP1 - > P1 = C
Ax = ( (1 - t) * p0x ) + (t * cp0x); Ay = ( (1 - t) * p0y ) + (t * cp0y); Bx = ( (1 - t) * cp0x ) + (t * cp1x); By = ( (1 - t) * cp0y ) + (t * cp1y); Cx = ( (1 - t) * cp1x ) + (t * p1x); Cy = ( (1 - t) * cp1y ) + (t * p1y);
第二个步骤是非常喜欢第一。 在第一个,我们连接这四个点与线,然后发现他们3个新点。 在这一步用线找到他们2分新,我们将连接这些3分。 我会打电话给这两个新的点d和E.
Dx = ( (1 - t) * Ax ) + (t * Bx);
Dy = ( (1 - t) * Ay ) + (t * By);
Ex = ( (1 - t) * Bx ) + (t * Cx);
Ey = ( (1 - t) * By ) + (t * Cy);
最后,我们可以用另一条线最后两个点的连线,并且在它身上找到的最后一个点,这将给我们是t的贝塞尔曲线上的点。 我会打电话给这点P.
Px = ( (1 - t) * Dx ) + (t * Ex);
Py = ( (1 - t) * Dy ) + (t * Ey);
在那里,我们走了,我们现在有X和贝塞尔一个点,从一开始就为t%的y坐标。 我很快就会添加一些图片。
Answer 2:
剪切和粘贴现成的答案:
// Points are objects with x and y properties
// p0: start point
// p1: handle of start point
// p2: handle of end point
// p3: end point
// t: progression along curve 0..1
// returns an object containing x and y values for the given t
BezierCubicXY = function(p0, p1, p2, p3, t) {
var ret = {};
var coords = ['x', 'y'];
var i, k;
for (i in coords) {
k = coords[i];
ret[k] = Math.pow(1 - t, 3) * p0[k] + 3 * Math.pow(1 - t, 2) * t * p1[k] + 3 * (1 - t) * Math.pow(t, 2) * p2[k] + Math.pow(t, 3) * p3[k];
}
return ret;
}
Answer 3:
我一直在试图找出同样的事情,我想我解决了这个问题至少在方贝塞尔曲线,这是只有一个单一的控制点贝塞尔曲线。
数学解释
对于正方形贝塞尔曲线的数学式为:
其中“X”是结果,“A”是起点,“B”的控制点和“C”的结束点的位置。
“T”是0和1之间的数字,指示在要计算线路哪个点。 0表示开始点,1终点和0.5将参考曲线的中心。
该函数被用于计算两个X和上线的点的Y坐标。 如果要计算X只需填写X的A,B和C点的坐标。
现在,为了确定属于我们需要确定的“T”为表示X坐标X与Y。
我们可以写在二次型相同贝塞尔方程( ):
这使我们能够使用二次公式导出的“T”即解方程的值。 二次公式实际上是2个公式。
和
将得到的公式为:
和
代码解决方案
我们可以在代码中的描述如下:
GetYValues(StartPoint, ControlPoint, EndPoint, X)
{
Ax = StartPoint.X
Bx = ControlPoint.X
Cx = EndPoint.X
q1 = 2*Ax - 2*Bx;
q2 = Sqrt(5*Ax*Ax - 10*Ax*Bx + Ax*Cx - Ax*X + 2*Bx*X + 4*Bx*Bx)
q3 = 2*Ax - 4*Bx + 2*Cx
t1 = (q1 + q2) / q3
t2 = (q1 - q2) / q3
Ay = StartPoint.Y
By = ControlPoint.Y
Cy = EndPoint.Y
Y1 = Ay*(1-t1)*(1-t1) + By*2*(1-t1)*t1 + Cy*t1
Y2 = Ay*(1-t2)*(1-t2) + By*2*(1-t2)*t2 + Cy*t2
return [Y1,Y2]
}
现在,我没有测试此,并且功能不检查是否其实有任何有效的点,所以有一定值,它会抛出异常。 确保“0分”检查和“低于0的数字的平方根”。
这种解决方案的问题
这个方程的一个大问题是,它仅适用于多的贝塞尔曲线,而大多数Bezier曲线实际上立方米。 我一直试图找到一种类似的方式来解决这个问题的立方版本,可惜这是幅度比较难的顺序。 我已经能够找到解决三次方程的唯一公式可以在这里找到三次函数 。 这个配方中含有虚数,我不知道该怎么做这些。
另一个问题是,对于具有4个控制点或多个贝塞尔曲线,也没有办法来解决方程在所有。
结论
最后,你最好的选择是简单地将贝塞尔曲线转换为直线,这是无限更容易计算。
Answer 4:
对于圆形的公式为:(XH)^ 2 +(YK)^ 2 = R ^ 2其中,h,k分别是x,y坐标为中心。 所以y的方程将是Y = SQRT(R ^ 2 - (XH)^ 2)+ K。 大多数语言都配有数学包,所以我想你可以做某种Math.sqrt(..)
和Math.pow(..)
有人纠正我,如果我的数学是关闭的。
Answer 5:
@DerekR:虽然你在这里提出的是明确的,可能是很多有用的,我想答案和全部由自己和IMMO以下意见都没有解决的问题。
(我的数学太臭,我一直在试图解决同样的问题,所以我可能不明白的后续评论。)
我认为这个问题是:知道了X,Y坐标的两个端点和两个控制点,并假设范围是0到1,再给予Y,什么为Y?
我是新的,还不能发表图片,但你可以看到在duck.cc/images/beziercurve_findY.png曲线