# 贝塞尔曲线
贝塞尔曲线用于计算机图形绘制形状,CSS 动画和许多其他地方。
它们其实非常简单,值得学习一次并且在矢量图形和高级动画的世界里非常受用。
# 一阶贝塞尔曲线
一阶贝塞尔曲线就是线段
// a 10, 50 // b 310, 100
ctx.moveTo(10, 50);
ctx.lineTo(310, 100);
ctx.stroke();
// a 10, 150 // b 310, 200
oneBezier(10, 150, 310, 200);
function oneBezier(x0, y0, x1, y1) {
for (let i = 0; i < 100; i++) {
let t = i / 100;
// q = (1-t)p_0+ tp_1
let a = (1 - t) * x0 + t * x1;
let b = (1 - t) * y0 + t * y1;
ctx.fillRect(a, b, 1, 1);
}
}
# 二阶贝塞尔曲线
(三个点) 一个起始点 一个控制点 一个终点
quadraticCurveTo(cp1x, cp1y, x, y)
两个基准向量的二次函数拟合路径
// a 50,50 // b 100,100 // b 300,50
ctx.moveTo(50, 50);
ctx.quadraticCurveTo(100, 100, 300, 50);
ctx.stroke();
// a 50,150 // b 100,200 // b 300,150
twoBezier(50, 150, 100, 200, 300, 150);
function twoBezier(x0, y0, x1, y1, x2, y2) {
for (let i = 0; i < 100; i++) {
let t = i / 100;
// q = (1-t)^2p_0+2t(1-t)p_1+t^2p_2
let a = Math.pow(1 - t, 2) * x0 + 2 * t * (1 - t) * x1 + t * t * x2;
let b = Math.pow(1 - t, 2) * y0 + 2 * t * (1 - t) * y1 + t * t * y2;
ctx.fillRect(a, b, 1, 1);
}
}
# 三阶贝塞尔曲线
(四个点) 一个起始点 两个控制点 一个终点
bezierCurveTo(cp1x, cp1y, cp2x, cp2y, x, y);
三个基准向量的三次函数拟合路径
// a 50,0 // b 100,50 // c 200, 120 // d 300,75
ctx.moveTo(50, 0);
ctx.bezierCurveTo(100, 50, 200, 120, 300, 75);
ctx.stroke();
// a 50,120 // b 100,170 // c 200,240 // d 300,195
threeBezier(50, 100, 100, 170, 200, 240, 300, 195);
function threeBezier(x0, y0, x1, y1, x2, y2, x3, y3) {
for (let i = 0; i < 100; i++) {
const t = i / 100;
// q = (1-t)^3p_0+3t(1-t)^2p_1+3t^2(1-t)p_2+t^3p_3
const x =
Math.pow(1 - t, 3) * x0 +
3 * t * Math.pow(1 - t, 2) * x1 +
3 * Math.pow(t, 2) * (1 - t) * x2 +
Math.pow(t, 3) * x3;
const y =
Math.pow(1 - t, 3) * y0 +
3 * t * Math.pow(1 - t, 2) * y1 +
3 * Math.pow(t, 2) * (1 - t) * y2 +
Math.pow(t, 3) * y3;
ctx.fillRect(x, y, 1, 1);
}
}
实际渲染效果