根据landmark,标记出人脸左右眼,和嘴巴, 环境windows7 64位。
根据测试,左眼的点为:36至41,最左边位36,上面37,38,右边39,下边41,40
右眼,最左边42,上面43,44,右边45,下边47,46
嘴巴,最左边48,右边54,上边 49至53,下边,55至58.
#include <iostream>
#include <opencv2/opencv.hpp>
#include "seeta/FaceDetector.h"
#include "seeta/FaceLandmarker.h"
#include "seeta/FaceRecognizer.h"
void extract_feature(const seeta::FaceDetector &FD,
const seeta::FaceLandmarker &FL,
const seeta::FaceRecognizer &FR,
std::string image_path,
float* feature)
{
cv::Mat img = cv::imread(image_path);
SeetaImageData simg;
simg.height = img.rows;
simg.width = img.cols;
simg.channels = img.channels();
simg.data = img.data;
auto faces = FD.detect(simg);
if (faces.size <= 0)
{
std::cout << "no face detected in" << image_path << std::endl;
return;
}
SeetaPointF points[5];
FL.mark(simg, faces.data[0].pos, points);
FR.Extract(simg, points, feature);
}
typedef std::vector<std::vector<SeetaPointF>> doubleSeetaFace;
int extract_landmark(const seeta::FaceDetector &FD, const seeta::FaceLandmarker &FL, const cv::Mat& img, doubleSeetaFace& points)
{
points.clear();
SeetaImageData simg;
simg.height = img.rows;
simg.width = img.cols;
simg.channels = img.channels();
simg.data = img.data;
auto faces = FD.detect(simg);
//size_t face_s = faces.size()
if (faces.size <= 0)
{
std::cout << "no face detected in" << std::endl;
return 0;
}
for (int i = 0; i < faces.size; i++){
SeetaPointF spoints[68];
FL.mark(simg, faces.data[i].pos, spoints);
std::vector<SeetaPointF> pts(spoints, spoints + 68);
points.push_back(pts);
}
return faces.size;
}
int smain()
{
seeta::ModelSetting fd_setting;
fd_setting.set_device(SEETA_DEVICE_CPU);
fd_setting.append("models/face_detector.csta");
seeta::FaceDetector FD(fd_setting);
seeta::ModelSetting fl_setting;
fl_setting.set_device(SEETA_DEVICE_CPU);
fl_setting.append("models/face_landmarker_pts5.csta");
seeta::FaceLandmarker FL(fl_setting);
seeta::ModelSetting fr_setting;
fr_setting.set_id(0);
fr_setting.append("models/face_recognizer.csta");
fr_setting.set_device(SEETA_DEVICE_CPU);
seeta::FaceRecognizer FR(fr_setting);
std::shared_ptr<float> feature1(new float[FR.GetExtractFeatureSize()]);
std::shared_ptr<float> feature2(new float[FR.GetExtractFeatureSize()]);
extract_feature(FD, FL, FR, "1.jpg", feature1.get());
extract_feature(FD, FL, FR, "2.jpg", feature2.get());
float sim = FR.CalculateSimilarity(feature1.get(), feature2.get());
std::cout << "face's similarity in 1.png and 2.png is" << sim << std::endl;
system("pause");
return 0;
}
#include <stdio.h>
void detect_Face()
{
seeta::ModelSetting fd_setting;
fd_setting.set_device(SEETA_DEVICE_CPU);
fd_setting.append("models/face_detector.csta");
seeta::FaceDetector FD(fd_setting);
seeta::ModelSetting fl_setting;
fl_setting.set_device(SEETA_DEVICE_CPU);
fl_setting.append("models/face_landmarker_pts68.csta");
seeta::FaceLandmarker FL(fl_setting);
cv::VideoCapture cap(0);
cv::Mat frame;
doubleSeetaFace points;
int radiusCircle = 2;
cv::Scalar colorCircle1(0, 0, 255); // (B, G, R)
int thicknessCircle1 = 2;
int font_face = cv::FONT_HERSHEY_COMPLEX;
double font_scale = 0.3;
int thickness = 1;
while (cap.read(frame))
{
cv::flip(frame, frame, 1);
int face_nums = extract_landmark(FD, FL, frame, points);
cv::Rect leftEye, rightEye, mouth;
for (auto iter = points.begin(); iter != points.end(); iter++)
{
auto jter = iter->begin();
leftEye.x = (jter+36)->x;
leftEye.y = (jter+37)->y;
leftEye.width = (jter+39)->x - leftEye.x;
leftEye.height = (jter+41)->y - leftEye.y;
leftEye.x -= 10;
leftEye.y -= 10;
leftEye.width += 20;
leftEye.height += 20;
rightEye.x = (jter+42)->x;
rightEye.y = (jter+43)->y;
rightEye.width = (jter+45)->x - rightEye.x;
rightEye.height = (jter+47)->y - rightEye.y;
rightEye.x -= 10;
rightEye.y -= 10;
rightEye.width += 20;
rightEye.height += 20;
mouth.x = (jter+48)->x;
mouth.y = (jter+50)->y;
mouth.width = (jter+54)->x - mouth.x;
mouth.height = (jter+57)->y - mouth.y;
mouth.x -= 10;
mouth.y -= 10;
mouth.width += 20;
mouth.height += 20;
cv::rectangle(frame, leftEye, colorCircle1);
cv::rectangle(frame, rightEye, colorCircle1);
cv::rectangle(frame, mouth, colorCircle1);
#if 0
int count = 0;
std::vector<SeetaPointF> pt(iter->begin(), iter->end());
for (auto jter = iter->begin(); jter != iter->end(); jter++)
{
cv::Point ps(jter->x, jter->y);
cv::Point ws(ps.x, ps.y - 5);
/*char str[256];
sprintf_s(str, 256, "%d", count++);
cv::putText(frame, str, ws, font_face, font_scale, cv::Scalar(0, 255, 255), thickness, 8, 0);
cv::circle(frame, ps, radiusCircle, colorCircle1, thicknessCircle1);*/
}
#endif
}
//cv::resize(frame, frame, cv::Size(frame.cols * 2.5, frame.rows * 2.5));
cv::imshow("detect.jpg", frame);
cv::waitKey(20);
}
cap.release();
}
int main(int argc, char** argv)
{
detect_Face();
}