Skip to content

staticbezier/ffd

Repository files navigation

A static C++17 bezier function generator

This lib can be used to generate arbitrary bezier functions (e.g. for free form deformations). The function generation is static (happens at compile time). The end result is an optimized function.

Introduction

The bezier function template is a variadic. It expects a list of integers, which defines the bernstein polynomials used in the generated bezier function.

bezier<x, y, z, ...>(in_position, in_control_points)

The number of template parameters also defines the dimension of the control point array in_control_points. If you work with images, you will have two template parameters and a 2D control point array. If you work with 3D meshes, you will have three template parameters and a 3D control point array. The value of the template parameters x, y, z, .. is the number of control points per dimension (row, column, ..) in in_control_points.

Parameters

The function itself expects two input parameters

in_position: A vector with dimension equal to the number of template parameters (e.g. glm::vec, or an vector/array type). The values of the vector must be within 0 < x < 1.

in_control_points: A control point array (with a dimension equal to the number of template parameters) holding vectors with a dimension equal to the number of template parameters

Return

The function returns a vector with dimension equal to the input.

Build

The library itself requires C++17. The demos Qt5, QtQuick and Qt3D.

cd StaticBezier
mkdir build
cmake ..
make

Demos

All demos are included as subfolders within the project's root directory.

Image Manipulation - 3x3 control points for 2D image manipulation

Small demo to perform a free form deformation on an image. Note that the black lines in the output are just resampling artifacts.

int w = img.width();
int h = img.height();
std::map<std::array<float, 2>, QRgb> transf_img_arr;

std::array<glm::vec2, 3> a1 = { glm::vec2(0.0, 0.0), glm::vec2(0.0, 0.5), glm::vec2(0.0, 1.0) };
std::array<glm::vec2, 3> a2 = { glm::vec2(0.5, 0.0), glm::vec2(0.5, 0.5), glm::vec2(0.5, 1.4) };
std::array<glm::vec2, 3> a3 = { glm::vec2(0.9, 0.0), glm::vec2(1.0, 0.5), glm::vec2(1.0, 1.0) };
std::array<std::array<glm::vec2, 3>, 3> ctrl2d = { a1, a2, a3 };

// scaling, ffd, boundary estimation
float mx(-FLT_MAX), my(-FLT_MAX);
for(int i = 0; i < w; i++)
for(int j = 0; j < h; j++) {
    glm::vec2 t = bezier<3,3>(glm::vec2((float)i/w, (float)j/h), ctrl2d) * glm::vec2(w, h);
    transf_img_arr[{t.x, t.y}] = img.pixel(i, j);
    mx = mx < t.x ? t.x : mx;
    my = my < t.y ? t.y : my;
}
Image Before Image After

QML Demo: FFD on *.stl files

The demo shows how to use the template to generate a function for a 3x3x3 control point grid to deform 3D-meshes.

Mesh Before FFD Mesh After FFD

About

Static Bezier Function Generator (C++17) for Free Form Deformations (FFD).

Topics

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published