如何将该项目更改为OpenCV实时人脸检测应用程序? [英] How can I change this project to a OpenCV realtime face detection app?

查看:79
本文介绍了如何将该项目更改为OpenCV实时人脸检测应用程序?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

Project 是与我的Project相同的实时图像处理程序,但它使用输入和输出两个值(我记得这些项目正在使用frame进行这样的处理). 我更改了它的native-lib.cpp文件

Project is a realtime image processer same as my Project but it uses two values wich are input and output(i remember that these projects are using frame for processing like that). I changed its native-lib.cpp file this

#include <jni.h>
#include "opencv2/objdetect.hpp"
#include "opencv2/highgui.hpp"
#include <android/log.h>
#include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>

#define TAG "NativeLib"

using namespace std;
using namespace cv;

extern "C" {
//void detect(Mat& input);
void JNICALL Java_com_example_nativeopencvandroidtemplate_MainActivity_adaptiveThresholdFromJNI(JNIEnv *env, jobject instance, jlong inputAddr, jlong outputAddr) {

    Mat &input = *(Mat *) inputAddr;
    Mat &output = *(Mat *) outputAddr;

    clock_t begin = clock();

    cv::adaptiveThreshold(input, output, 255, ADAPTIVE_THRESH_MEAN_C, THRESH_BINARY_INV, 21, 5);

    double total_time = double (clock() - begin ) / CLOCKS_PER_SEC;
    __android_log_print(ANDROID_LOG_INFO, TAG, "adaptiveThreshold computation time = %f seconds\n",  total_time);
}
}

对此

#include <jni.h>
#include "opencv2/objdetect.hpp"
#include "opencv2/highgui.hpp"
#include <android/log.h>
#include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>



using namespace std;
using namespace cv;

extern "C" {
void detect(Mat &input);
void JNICALL
Java_com_example_nativeopencvandroidtemplate_MainActivity_adaptiveThresholdFromJNI(JNIEnv *env, jobject instance,
                                                                                   jlong inputAddr) {

    Mat &input = *(Mat *) inputAddr;
    detect(input);
 }
void detect(Mat &input) {
    String face_cascade_name = "/storage/emulated/0/ony.xml";
    String eyes_cascade_name = "/storage/emulated/0/moe.xml";
    CascadeClassifier face_cascade;
    CascadeClassifier eyes_cascade;


    if (!face_cascade.load(face_cascade_name)) {
        printf("--(!)Error loading\n");
        return;
    };
    if (!eyes_cascade.load(eyes_cascade_name)) {
        printf("--(!)Error loading\n");
        return;
    };


    std::vector<Rect> faces;
    Mat frame_gray;


    cvtColor( input, frame_gray, COLOR_RGB2GRAY );
    equalizeHist(frame_gray, frame_gray);

    //-- Detect faces
    face_cascade.detectMultiScale(frame_gray, faces, 1.1, 2, 0 | CASCADE_SCALE_IMAGE, Size(30, 30));

    for (size_t i = 0; i < faces.size(); i++) {
        Point center(faces[i].x + faces[i].width * 0.5, faces[i].y + faces[i].height * 0.5);
        ellipse(input, center, Size(faces[i].width * 0.5, faces[i].height * 0.5), 0, 0, 360, Scalar(255, 0, 255), 4, 8,
                0);

        Mat faceROI = frame_gray(faces[i]);
        std::vector<Rect> eyes;

        //-- In each face, detect eyes
        eyes_cascade.detectMultiScale(faceROI, eyes, 1.1, 2, 0 | CASCADE_SCALE_IMAGE, Size(30, 30));

        for (size_t j = 0; j < eyes.size(); j++) {
            Point center(faces[i].x + eyes[j].x + eyes[j].width * 0.5, faces[i].y + eyes[j].y + eyes[j].height * 0.5);
            int radius = cvRound((eyes[j].width + eyes[j].height) * 0.25);
            circle(input, center, radius, Scalar(255, 0, 0), 4, 8, 0);
        }
    }
}
}

但是在我的手机中,黑屏可能持续了五秒钟,并且应用程序反复停止.

But in my phone there was a black screen for probably five seconds and app stopping repeatedly.

注意:同步和构建成功完成,并且在我更改cpp文件应用程序之前,成功运行了

Note: Sync and build were succesfully and before i changed cpp file app was working succesfully

请帮助我有关我的项目.

Please help me about my Project.

谢谢

推荐答案

在这里,您对C ++方法 Java_com_example_nativeopencvandroidtemplate_MainActivity_adaptiveThresholdFromJNI 的定义进行了一些更改,因此您必须在Kotlin方面反映这些更改,因为使用JNI从您的 MainActivity.kt 调用此方法.这是您必须在 MainActivity.kt 中修改的代码:

Here you made some changes to the definition of the C++ method Java_com_example_nativeopencvandroidtemplate_MainActivity_adaptiveThresholdFromJNI, you will therefore have to reflect these changes on the Kotlin side, as this method is called from your MainActivity.kt using JNI. Here is the code you'll have to adapt in MainActivity.kt:

class MainActivity : Activity(), CameraBridgeViewBase.CvCameraViewListener2 {

    ...

    override fun onCameraFrame(inputFrame: CameraBridgeViewBase.CvCameraViewFrame): Mat {
        val mat = inputFrame.gray()

        adaptiveThresholdFromJNI(mat.nativeObjAddr)

        return mat
    }

    private external fun adaptiveThresholdFromJNI(matAddr: Long)

    ...

}

此处 adaptiveThresholdFromJNI 被修改为仅处理一个参数(与C ++等效),然后从 onCameraFrame 返回一个参数以显示在屏幕上

Here adaptiveThresholdFromJNI was adapted to handle only one argument (as you did with the C++ equivalent) and that one argument is then returned from onCameraFrame to be displayed on the screen.

我在您的C ++代码中看到,您尝试做的第一件事是将输入的 Mat 转换为 gray ,但这不是必需的,因为传递给您的C ++代码的Mat 已经是灰色(请参见val mat = inputFrame.gray()).

I see in your C++ code that the first thing you try to do is to convert your input Mat to gray, but this is not necessary because the Mat passed to your C++ code is already gray (see val mat = inputFrame.gray()).

如果您希望保持C ++代码完整无缺,还可以使用val mat = inputFrame.rgba()将相机视图框架的彩色版本传递给C ++代码.

If you want to keep your C++ code intact, you can also pass the colorized version of the camera view frame to your C++ code by using val mat = inputFrame.rgba().

这篇关于如何将该项目更改为OpenCV实时人脸检测应用程序?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆