基于V4L2摄像头智能识别拍照(人脸和手掌)

1. 代码整个结构

2. 智能识别模块

c 复制代码
摄像头 → 读取 → 转换 → 缩放 → 🎯识别人脸/手掌 → 如有目标:保存图像
                                                    ↓
                                                合并 → 显示
c 复制代码
// detect_and_save.cpp
#include <opencv2/opencv.hpp>
#include <vector>
#include <string>
#include <ctime>
#include <unistd.h>

using namespace cv;
using namespace std;

static CascadeClassifier face_cascade;
static CascadeClassifier palm_cascade;
static bool initialized = false;

// 将像素数据(RGB)转为 OpenCV 图像,并检测人脸或手掌
extern "C" int DetectAndSaveIfNeeded(unsigned char *rgb_data, int width, int height)
{
    if (!initialized)
    {
        // 注意:路径需根据你系统中模型文件位置修改
        if (!face_cascade.load("/usr/share/opencv4/haarcascades/haarcascade_frontalface_default.xml"))
        {
            fprintf(stderr, "Failed to load face cascade\n");
            return -1;
        }
        if (!palm_cascade.load("/usr/share/opencv4/haarcascades/palm.xml")) // 自定义路径或手动下载
        {
            fprintf(stderr, "Failed to load palm cascade\n");
            return -1;
        }
        initialized = true;
    }

    // 构建 Mat 图像,RGB 格式
    Mat frame(height, width, CV_8UC3, rgb_data);

    // 转灰度图
    Mat gray;
    cvtColor(frame, gray, COLOR_BGR2GRAY);
    equalizeHist(gray, gray);

    // 检测人脸与手掌
    vector<Rect> faces, palms;
    face_cascade.detectMultiScale(gray, faces, 1.1, 3, 0, Size(30, 30));
    palm_cascade.detectMultiScale(gray, palms, 1.1, 3, 0, Size(50, 50));

    if (!faces.empty() || !palms.empty())
    {
        // 获取当前时间作为文件名
        time_t now = time(NULL);
        struct tm *t = localtime(&now);

        char filename[128];
        snprintf(filename, sizeof(filename), "/mnt/data/capture_%04d%02d%02d_%02d%02d%02d.jpg",
                 t->tm_year + 1900, t->tm_mon + 1, t->tm_mday,
                 t->tm_hour, t->tm_min, t->tm_sec);

        imwrite(filename, frame);
        printf("Saved: %s\n", filename);
        return 1;  // 表示检测成功
    }

    return 0; // 没检测到目标
}

3. 下载模型

下载手掌检测模型 palm.xml

c 复制代码
wget https://raw.githubusercontent.com/Aravindlivewire/Opencv/master/haarcascade/haarcascade_palm.xml -O ~/opencv/data/haarcascades/palm.xml

拷贝到目标板

c 复制代码
cp /home/book/opencv/data/haarcascades/palm.xml ~/nfs_rootfs/haarcascade/

4. 编译:

在# V4L2摄像头数据采集(读取、转换、缩放、合并、显示)的基础上

4.1 修改Makefire

  1. 添加对 C++ 编译器支持:
c 复制代码
CXX := $(CROSS_COMPILE)g++
export CXX
  1. 添加 OpenCV 头文件和链接库
c 复制代码
CFLAGS := -Wall -O2 -g
CFLAGS += -I $(shell pwd)/include
CFLAGS += -I/home/book/opencv-arm-install/include

LDFLAGS := -lm -ljpeg
LDFLAGS += -L/home/book/opencv-arm-install/lib \
           -Wl,-rpath=/home/book/opencv-arm-install/lib \
           -lopencv_core -lopencv_imgproc -lopencv_highgui -lopencv_objdetect -lopencv_imgcodecs
  1. 添加 detect_and_save.o 到编译对象中(在 obj-y 区)
c 复制代码
obj-y += main.o
obj-y += detect_and_save.o       # ✅ 添加这一行
obj-y += convert/
obj-y += display/
obj-y += render/
obj-y += video/

4.2 修改Makefire.build

  1. 添加 .cpp 文件的编译规则(添加在其后)
c 复制代码
%.o : %.cpp
	$(CXX) $(CFLAGS) -Wp,-MD,$(dep_file) -c -o $@ $<

4.3 编译测试命令

c 复制代码
make clean
make

5. 运行

1. 出现错误:./video2lcd: error while loading shared libraries: libopencv_core.so.412: cannot open shared object file: No such file or directory

2. 原因: 在Ubuntu上交叉编译opencv得到的库没有拷贝到开发板

3. 拷贝到开发板:

确保目标目录在开发板存在且有权限:mkdir -p /usr/lib/opencv

使用scp拷贝

bash 复制代码
# 方法 1:NFS 挂载方式
cp /home/book/opencv-arm-install/lib/libopencv_*.so* /home/book/nfs_rootfs/opencv-lib/

# 方法 2:通过 scp 拷贝
scp /home/book/opencv-arm-install/lib/libopencv_*.so* root@192.168.x.x:/usr/lib/opencv/

运行错误:

bash 复制代码
/dev/video1 supports streaming i/o Convert yuv2rgb, ret = 0 terminate called after throwing an instance of 'cv::Exception' 
what(): OpenCV(4.12.0-dev) /home/book/opencv/modules/core/src/persistence.cpp:742: 
error: (-215:Assertion failed) buf in function 'open'

原因:模型下载失败,需重新下载

c 复制代码
wget https://raw.githubusercontent.com/Aravindlivewire/Opencv/master/haarcascade/palm.xml -O ~/opencv/data/haarcascades/palm.xml

复制到开发板

cp /home/book/opencv/data/haarcascades/haarcascade_frontalface_default.xml ~/nfs_rootfs/haarcascade/

移除GUI

bash 复制代码
mv  /etc/init.d/S99myirhmi2  /root
mv  /etc/init.d/S05lvgl  /root

实验过程中LCD过几分钟就黑屏,这是正常的。 可以关闭黑屏的功能,执行以下命令即可: echo -e "\0339;0" > /dev/tty0

6. 总结

相关推荐
groundhappy10 小时前
idalib安装和codex ida-mcp配置
linux·开发语言·python
通信小小昕11 小时前
Ubuntu 26.04 中文输入法安装
linux·运维·ubuntu
张小姐的猫12 小时前
【Linux】网络编程 —— HTTP协议(上)
linux·运维·服务器·网络·http·单例模式·策略模式
栩栩云生12 小时前
AI 写代码犯的错,早被写进了错题集
linux·安全·ai编程
imc.1114 小时前
linux基础IO
linux·运维·服务器
BelongPanda15 小时前
Linux Nginx 纯手动 Let‘s Encrypt 泛域名证书配置教程
linux·nginx
酷可达拉斯16 小时前
Linux操作系统-shell编程(0)
linux·运维·服务器·python·云计算
2301_7779983416 小时前
Linux中断机制:操作系统如何高效运行
linux·运维·服务器
yunwei3716 小时前
eBPF 教程:检查 exec 后真正安装的可执行镜像
linux·开源
笑锝没心没肺17 小时前
yum update 报错:GPG key retrieval failed: [Errno 14] HTTPS Error 404 - Not Found
linux·运维·服务器