当前位置:  开发笔记 > 编程语言 > 正文

如何在C++中实现Bézier曲线?

如何解决《如何在C++中实现Bézier曲线?》经验,为你挑选了4个好方法。

我想实现Bézier曲线.我以前在C#中做过这个,但我对C++库完全不熟悉.我该如何创建二次曲线?

void printQuadCurve(float delta, Vector2f p0, Vector2f p1, Vector2f p2);

显然我们需要使用线性插值,但这是否存在于标准数学库中?如果没有,我在哪里可以找到它?

更新1:

对不起,我忘了提到我正在使用Linux.



1> Jakob Riedle..:

最近我遇到了同样的问题,并希望自己实现它.维基百科的这张图片帮助了我:

http://upload.wikimedia.org/wikipedia/commons/3/35/Bezier_quadratic_anim.gif

以下代码是用C++编写的,并展示了如何计算二次贝塞尔曲线.

int getPt( int n1 , int n2 , float perc )
{
    int diff = n2 - n1;

    return n1 + ( diff * perc );
}    

for( float i = 0 ; i < 1 ; i += 0.01 )
{
    // The Green Line
    xa = getPt( x1 , x2 , i );
    ya = getPt( y1 , y2 , i );
    xb = getPt( x2 , x3 , i );
    yb = getPt( y2 , y3 , i );

    // The Black Dot
    x = getPt( xa , xb , i );
    y = getPt( ya , yb , i );

    drawPixel( x , y , COLOR_RED );
}

(x1 | y1),(x2 | y2)和(x3 | y3)是图像中的P0,P1和P2.只是为了展示基本理念......

对于那些要求立方贝塞尔曲线的人来说,它只是模拟(也来自维基百科):

http://upload.wikimedia.org/wikipedia/commons/a/a3/Bezier_cubic_anim.gif

这个答案为它提供了代码.



2> iforce2d..:

以下是具有任意点数的曲线的一般实现.

vec2 getBezierPoint( vec2* points, int numPoints, float t ) {
    vec2* tmp = new vec2[numPoints];
    memcpy(tmp, points, numPoints * sizeof(vec2));
    int i = numPoints - 1;
    while (i > 0) {
        for (int k = 0; k < i; k++)
            tmp[k] = tmp[k] + t * ( tmp[k+1] - tmp[k] );
        i--;
    }
    vec2 answer = tmp[0];
    delete[] tmp;
    return answer;
}

请注意,它使用堆内存作为临时数组,这并不是那么有效.如果您只需要处理固定数量的点,则可以对numPoints值进行硬编码并使用堆栈内存.

当然,上面假设你有一个vec2结构和运算符,如下所示:

struct vec2 {
    float x, y;
    vec2(float x, float y) : x(x), y(y) {}
};

vec2 operator + (vec2 a, vec2 b) {
    return vec2(a.x + b.x, a.y + b.y);
}

vec2 operator - (vec2 a, vec2 b) {
    return vec2(a.x - b.x, a.y - b.y);
}

vec2 operator * (float s, vec2 a) {
    return vec2(s * a.x, s * a.y);
}


?? 根据问题和函数名称"getBezierPoint",它更加bezier

3> Malcolm McLe..:

您可以选择de Casteljau的方法,即递归分割控制路径,直到您使用线性插值到达点,如上所述,或Bezier的方法,即混合控制点.

贝齐尔的方法是

 p = (1-t)^3 *P0 + 3*t*(1-t)^2*P1 + 3*t^2*(1-t)*P2 + t^3*P3 

用于立方体和

 p = (1-t)^2 *P0 + 2*(1-t)*t*P1 + t*t*P2

对于二次方.

t通常在0-1,但这不是必要的 - 实际上曲线延伸到无穷大.P0,P1等是控制点.曲线通过两个端点,但通常不通过其他点.



4> dirkgently..:

你之前是否使用过C#库?

在C++中,Bezier曲线的标准库函数尚未可用(尚未).您当然可以自己滚动(CodeProject 示例)或查找数学库.

这篇博文很好地解释了这个想法,但是在Actionscript中.翻译不应该是一个很大的问题.

推荐阅读
放ch养奶牛
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有