基本思想
通过Dlib获得当前人脸的特征点,然后通过旋转平移标准模型的特征点进行拟合,计算标准模型求得的特征点与Dlib获得的特征点之间的差,使用Ceres不断迭代优化,最终得到最佳的旋转和平移参数。
使用环境
系统环境:Ubuntu 18.04
使用语言:C++
编译工具:CMake
第三方工具
Dlib:用于获得人脸特征点
Ceres:用于进行非线性优化
CMinpack:用于进行非线性优化 (OPTIONAL)
源代码
基础概念
旋转矩阵
头部的任意姿态可以转化为6个参数(yaw, roll, pitch, tx, ty, tz),前三个为旋转参数,后三个为平移参数。
平移参数好理解,原坐标加上对应的变化值即可;旋转参数需要构成旋转矩阵,三个参数分别对应了绕y轴旋转的角度、绕z轴旋转的角度和绕x轴旋转的角度。
具体代码实现我们可以通过Dlib已经封装好的API,rotate_around_x/y/z(angle)。该函数返回的类型是dlib::point_transform_affine3d,可以通过括号进行三维的变形,我们将其封装成一个rotate函数使用如下:void rotate(std::vector& points, const double yaw, const double pitch, const double roll)
{
dlib::point_transform_affine3d around_z = rotate_around_z(roll * pi / 180);
dlib::point_transform_affine3d around_y = rotate_around_y(yaw * pi / 180);
dlib::point_transform_affine3d around_x = rotate_around_x(pitch * pi / 180);
for(std::vector::iterator iter=points.begin(); iter!=points.end(); ++iter)
*iter = around_z(around_y(around