Skip to content

Bezier curve

베지에 곡선 혹은 베지어 곡선(Bézier Curve)은 n개의 점으로부터 얻어지는 n-1차 곡선으로 수치 해석 분야에서 상당히 중요한 위치를 차지하고 있다. 특히 3차 베지에 곡선은 포스트스크립트 글꼴, 메타폰트(METAFONT), 김프 등에서 부드러운 곡선을 생성하는 데에 이용되고 있으며, 트루 타입 폰트에는 2차 베지에 곡선 알고리즘을 사용한다.

in HTML5

HTML:canvas#quadraticCurveTo와 HTML:canvas#bezierCurveTo API 참조. 각각 2차, 3차 베지어 곡선이다.

구현 방법

godot으로 구현한 내용이다. 참고로 사용 언어는 C# 이다.

Quadratic Bezier

Godot_-_bezier_quadratic_points.png

private List<Vector2> QuadraticBezierPoints(Vector2 p0, Vector2 p1, Vector2 p2, float step, bool ignoreStart = false, bool ignoreStop = false)
{
    Debug.Assert(0 < step && step <= 1);
    var cursor = step;
    var result = new List<Vector2>();
    if (!ignoreStart)
    {
        result.Add(QuadraticBezier(p0, p1, p2, 0));
    }
    while (cursor < 1)
    {
        result.Add(QuadraticBezier(p0, p1, p2, cursor));
        cursor += step;
    }
    if (!ignoreStop)
    {
        result.Add(QuadraticBezier(p0, p1, p2, 1));
    }
    return result;
}

private Vector2 QuadraticBezier(Vector2 p0, Vector2 p1, Vector2 p2, float t)
{
    var q0 = p0.LinearInterpolate(p1, t);
    var q1 = p1.LinearInterpolate(p2, t);
    return q0.LinearInterpolate(q1, t);
}

출력 결과:

Godot_-_bezier_quadratic_points.gif

Cubic Bezier

Godot_-_bezier_cubic_points.png

private List<Vector2> CubicBezierPoints(Vector2 p0, Vector2 p1, Vector2 p2, Vector2 p3, float step, bool ignoreStart = false, bool ignoreStop = false)
{
    Debug.Assert(0 < step && step <= 1);
    var cursor = step;
    var result = new List<Vector2>();
    if (!ignoreStart)
    {
        result.Add(CubicBezier(p0, p1, p2, p3, 0));
    }
    while (cursor < 1)
    {
        result.Add(CubicBezier(p0, p1, p2, p3, cursor));
        cursor += step;
    }
    if (!ignoreStop)
    {
        result.Add(CubicBezier(p0, p1, p2, p3, 1));
    }
    return result;
}

private Vector2 CubicBezier(Vector2 p0, Vector2 p1, Vector2 p2, Vector2 p3, float t)
{
    var q0 = p0.LinearInterpolate(p1, t);
    var q1 = p1.LinearInterpolate(p2, t);
    var q2 = p2.LinearInterpolate(p3, t);

    var r0 = q0.LinearInterpolate(q1, t);
    var r1 = q1.LinearInterpolate(q2, t);

    return r0.LinearInterpolate(r1, t);
}

출력 결과:

Godot_-_bezier_cubic_points.gif

참고로 Vector2의 LinearInterpolate 함수 구현체는 다음과 같다:

Vector2 linear_interpolate(const Vector2 &p_a, const Vector2 &p_b, real_t p_t)
{
    Vector2 res = p_a;

    res.x += (p_t * (p_b.x - p_a.x));
    res.y += (p_t * (p_b.y - p_a.y));

    return res;
}

De Casteljau's algorithm

Casteljau 알고리즘은 베지어 곡선을 계산하는 기법으로, 주어진 제어점을 사용해 곡선 상의 점을 반복적으로 보간(interpolation)하는 방식입니다.

DEFAULT_CURVE_TESSELLATION_TOL: Final[float] = 1.25
"""
Tessellation tolerance when using BezierCurve without a specific number of segments.
Decrease for highly tessellated curves (higher quality, more polygons),
Increase to reduce quality.
"""

Slug 알고리듬

  • Slug 알고리듬 10주년 | GeekNews
  • GPU에서 Bézier 곡선 기반 폰트 렌더링을 수행하는 Slug 알고리듬은 텍스처 없이 직접 벡터 데이터를 렌더링하며, 게임·CAD·영상 편집·의료 장비 등 다양한 산업에서 사용됨
  • 독점권을 2026/3/17부로 포기하여 특허가 공공 도메인으로 완전 해제되어 누구나 자유롭게 사용가능해졌음
  • 최근 버전에서는 band split 최적화와 supersampling 제거, 이모지 렌더링 방식 단순화 등으로 성능과 코드 효율을 개선
  • 가장 큰 변화는 동적 팽창(dynamic dilation) 기능으로, 글리프 크기와 시점에 따라 자동으로 최적 경계 확장을 계산함
  • MIT 라이선스로 공개된 GitHub 레퍼런스 셰이더 코드를 통해 누구나 자유롭게 구현 가능

See also

Favorite site