假设我有嘴巴和眼睛的位置/坐标,我如何在二维图像上进行基本的人脸对齐。
有没有我可以实施的算法来纠正图像上的人脸对齐?
假设我有嘴巴和眼睛的位置/坐标,我如何在二维图像上进行基本的人脸对齐。
有没有我可以实施的算法来纠正图像上的人脸对齐?
人脸(或图像)对齐是指将一个图像(或您的情况下的人脸)与另一张图像(或参考图像/人脸)对齐。它也称为图像配准。您可以使用外观(基于强度的配准)或关键点位置(基于特征的配准)来做到这一点。第二类源于图像运动模型,其中一个图像被认为是另一个图像的位移版本。
在您的情况下,地标位置(眼睛和鼻子 3 个点?)为直接基于特征的配准提供了一个很好的参考集。假设您在两个 2D 图像中都有一组点的位置,x_1
并且x_2
您可以估计相似变换S
(旋转、平移、缩放),即映射x_1
到的平面 2D 变换x_2
。您还可以为此添加反射,但对于面部而言,这很可能是不必要的。
可以通过形成正规方程并x_1 = Sx_2
使用线性回归解决系统的线性最小二乘 (LS) 问题来进行估计。对于 5 个未知参数(2 个旋转、2 个平移、1 个缩放),您需要 3 个点(准确地说是 2.5)来求解 5 个方程。可以通过直接线性变换(例如通过应用 SVD 或矩阵伪逆)获得上述 LS 的解。对于足够多的参考点(即自动检测)的情况,用于点过滤和不确定性消除的 RANSAC 类型的方法(尽管这不是您的情况)。
估计后S
,对第二张图像应用图像变形,得到整个 的变换后的网格(像素)坐标image 2
。变换将改变像素位置,但不会改变它们的外观。不可避免地, 的某些变换区域image 2
将位于 的网格之外image 1
,您可以决定那些空位置的值(例如 0、NaN 等)。
更多详细信息:R. Szeliski,“图像对齐和拼接:教程”(第 4.3 节“几何配准”)
在 OpenCV 中,请参阅:Geometric Image Transformations,例如cv::getRotationMatrix2D
cv::getAffineTransform
并cv::warpAffine.
注意您应该估计并应用相似性变换(仿射的特殊情况)以保留角度和形状。
对于人脸,特征点有很多可变性。因此,仅通过仿射变换不可能完美拟合所有特征点。完美对齐所有点的唯一方法是在给定点的情况下扭曲图像。基本上,您可以对给定点的图像进行三角剖分,并对每个三角形进行仿射扭曲,以获得所有点对齐的扭曲图像。
可以根据眼睛的位置来处理人脸检测。
在这里,OpenCV、Dlib 和 MTCNN 提供了检测面部和眼睛的功能。此外,它是一个基于 python 的框架,但 deepface 封装了这些方法并提供了开箱即用的检测和对齐功能。
detectFace 函数分别在后台应用检测和对齐。
#!pip install deepface
from deepface import DeepFace
backends = ['opencv', 'ssd', 'dlib', 'mtcnn']
DeepFace.detectFace("img.jpg", detector_backend = backends[0])
此外,您可以手动应用检测和对齐。
from deepface.commons import functions
img = functions.load_image("img.jpg")
backends = ['opencv', 'ssd', 'dlib', 'mtcnn']
detected_face = functions.detect_face(img = img, detector_backend = backends[3])
plt.imshow(detected_face)
aligned_face = functions.align_face(img = img, detector_backend = backends[3])
plt.imshow(aligned_face)
processed_img = functions.detect_face(img = aligned_face, detector_backend = backends[3])
plt.imshow(processed_img)
OpenCV的人脸识别指南中有一个对齐人脸图像的部分:
该脚本在眼睛处对齐给定的图像。它是用 Python 编写的,但应该很容易翻译成其他语言。我知道 Sorin Miron 的 C# 实现: