求高手解答 贝塞尔曲线问题

怎么使得一个物体的运动速度(不是运动轨迹)变化按照我们设定的贝塞尔曲线进行变化呢, 就像css3的设置贝塞尔曲线那样,

假如cc.EaseIn这种速率变化不满足需求的时候 怎么写出这种速率变化的公式,css3的可以直接给他一个贝塞尔曲线的几个值 就可以了 好像用js非常困难

①在动画控制中,一般使用三次贝塞尔曲线控制动画的“完成度”而不是“运动速度”,我相信楼主问的也是用贝塞尔曲线控制动画“完成度”的问题;

上图是我做贝塞尔曲线编辑器。在一般的动画完成度编辑器中,x轴代表的是时间完成度,y轴代表动画完成度,x和y都在[0, 1]区间内。当x=1时,y=1,y值代表的并不是“运动速度”。

②贝塞尔曲线中除了有已知的4个坐标点,还有3个可变参数: t,x,y。其中t代表曲线的完成度(1%-100%),t对应一个或者多个(x, y)坐标点(因为4个已知坐标点被控制在了一定区间内,所以贝塞尔曲线编辑器中t仅仅对应一个(x, y)坐标);

③在已知t的情况下求解x和y是很容易的,但是已知x求y是非常困难的

④正面去求值很困难,那就需要换一种方式去近似地去求值了(后面附代码)。

值得一提的是,Cocos2d-x中有贝塞尔曲线控制动画完成度的类,但实际上这个功能的实现却是错误的。
在CCTweenFunction.cpp中的bezieratFunction中可以看到在求解动作完成度y时错误地把x当做了t。
所有x坐标值都完全不参与计算过程
但由于在这种情况下t和y是正相关的,和x也是正相关的,所以也很难看出来动画有什么问题

两个解决方案
1.使用CCActionEase.cpp的EaseBezierAction类糊弄过去;
2.自己求解贝塞尔曲线来控制动画的完成度:首先需要采样,假设采样步长是0.1,那么t = 0.1、0.2、0.3… 的条件下求解x和y的值,设为x1,y1,x2,y2,x3,y3…;然后进行线性插值,已知目前的时间完成度x,可以求解出x所在的区间[xn, xn+1],y的值就在[yn, yn+1]之间,线性插值就可以得到近似结果。Lua版本的代码如附件,只有求解贝塞尔曲线的部分,具体的动画控制需要再编码完成。
BezierCurve.zip (1.2 KB)

6赞

看懂了,赞!

感谢大神。。。