人脸识别+自定义裁取图片(opencv库)

官方下载opencv安装文件: http://opencv.org/releases.html,以windows版本为例,下载安装包安装到习惯的目录下

安装后,在build目录下 D:\opencv\opencv\build\java,获取opencv-341.jar(必须要用的)

同时需要dll文件 与 各识别xml文件,进行不同特征的识别(人脸,侧脸,眼睛等)

dll目录: D:\opencv\opencv\build\java\x64\opencv_java341.dll(dll库)(这个路径部和下面xml需要导入项目中,但是路径可以自定义)

xml目录:D:\opencv\opencv\sources\data\haarcascades\haarcascade_frontalface_alt.xml(目录中有各类识别文件)

因为项目需要本文是参考https://blog.csdn.net/zmx729618/article/details/78142271写的因为项目需求做了些简单的处理,将人脸识别画框改成截取并另存画框部分图片

1.先将opencv-341.jar 拷入项目里(注意版本问题)


2.将库和配置文件添加进去


3.下面就把你需要的方法拿去用吧!

import org.opencv.core.*;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
import org.opencv.objdetect.CascadeClassifier;


public class Test {


    static{
        // 载入opencv的库
        String opencvpath = System.getProperty("user.dir") + "\\opencv\\x64\\";
        String opencvDllName = opencvpath + Core.NATIVE_LIBRARY_NAME + ".dll";
        System.load(opencvDllName);
    }

        public static final String xmlfilePath="D:opencv\\opencv\\sources\\data\\haarcascades\\haarcascade_frontalface_alt.xml";
    //
//检测输入图像中的人脸,将最大的脸保存到指定的输出文件中
//

    public static double calcArea(Rect rect)
    {
        return rect.width*rect.height;
    }


    /**
     * opencv实现人脸识别
     * @param imagePath
     * @param outFile
     * @throws Exception
     */
    public static void detectFace(String imagePath,  String outFile) throws Exception
    {

        System.out.println("Running DetectFace ... ");
        // 从配置文件lbpcascade_frontalface.xml中创建一个人脸识别器,该文件位于opencv安装目录中
        CascadeClassifier faceDetector = new CascadeClassifier(
                "D:\\opencv\\opencv\\sources\\data\\haarcascades\\haarcascade_frontalface_alt.xml");

        Mat image = Imgcodecs.imread(imagePath);

        // 在图片中检测人脸
        MatOfRect faceDetections = new MatOfRect();

        faceDetector.detectMultiScale(image, faceDetections);

        System.out.println(String.format("Detected %s faces", faceDetections.toArray().length));

        Rect[] rects = faceDetections.toArray();
        if(rects != null && rects.length > 1){
            // 找出最大的1张脸
            Rect maxRect=new Rect(0,0,0,0);
            //throw new RuntimeException("超过一个脸");
            for (Rect rect : faceDetections.toArray())
            {
                if(calcArea(maxRect)<calcArea(rect))
                {
                    maxRect=rect;
                }
            }
            if(calcArea(maxRect)>0){
                //创建人脸拷贝区域
                Mat roi_img = new Mat(image,maxRect);
                //创建临时的人脸拷贝图形
                Mat tmp_img = new Mat();
                //人脸拷贝
                roi_img.copyTo(tmp_img);
            }
        }
        // 在每一个识别出来的人脸周围画出一个方框
        Rect rect = rects[0];
        Imgproc.rectangle(image, new Point(rect.x-100, rect.y-100),
                new Point(rect.x + rect.width+30, rect.y + rect.height+30),
                new Scalar(0, 255, 0));
        Imgcodecs.imwrite(outFile, image);//这里是输出原图并划框
        imageCut(imagePath,"C:/Users/Lenovo/Desktop/12.jpg", rect.x-100, rect.y-100,500,500);//进行图片裁剪
        System.out.println(String.format("人脸识别成功,人脸图片文件为: %s", outFile));


    }


    /**
     * 裁剪图片并重新装换大小
     * @param imagePath
     * @param posX
     * @param posY
     * @param width
     * @param height
     * @param outFile
     */
    public static void imageCut(String imagePath,String outFile, int posX,int posY,int width,int height ){

        //原始图像
        Mat image = Imgcodecs.imread(imagePath);

        //截取的区域:参数,坐标X,坐标Y,截图宽度,截图长度
        Rect rect = new Rect(posX,posY,width,height);

        //两句效果一样
        Mat sub = image.submat(rect);   //Mat sub = new Mat(image,rect);

        Mat mat = new Mat();
        Size size = new Size(300, 300);
        Imgproc.resize(sub, mat, size);//将人脸进行截图并保存

        Imgcodecs.imwrite(outFile, mat);
        System.out.println(String.format("图片裁切成功,裁切后图片文件为: %s", outFile));

    }
 
/**
 * 图片合成  
 * @param image1
 * @param image2
 * @param posw
 * @param posh
 * @param outFile
 * @return
 */
public static void simpleMerge(String image1, String image2, int posw, int posh, String outFile) throws IOException{

    // 获取底图  
    BufferedImage buffImg1 = ImageIO.read(new File(image1));

    // 获取层图  
    BufferedImage buffImg2 = ImageIO.read(new File(image2));

    //合并两个图像  
    int w1 = buffImg1.getWidth();
    int h1 = buffImg1.getHeight();

    int w2 = buffImg2.getWidth();
    int h2 = buffImg2.getHeight();

    BufferedImage imageSaved = new BufferedImage(w1, h1, BufferedImage.TYPE_INT_ARGB); //创建一个新的内存图像  

    Graphics2D g2d = imageSaved.createGraphics();

    g2d.drawImage(buffImg1, null, 0, 0);  //绘制背景图像  

    for (int i = 0; i < w2; i++) {
        for (int j = 0; j < h2; j++) {
            int rgb1 = buffImg1.getRGB(i + posw, j + posh);
            int rgb2 = buffImg2.getRGB(i, j);  

            /*if (rgb1 != rgb2) {  
                rgb2 = rgb1 & rgb2;  
            }*/
            imageSaved.setRGB(i + posw, j + posh, rgb2); //修改像素值  
        }
    }

    ImageIO.write(imageSaved, "png", new File(outFile));

    System.out.println(String.format("图片合成成功,合成图片文件为: %s", outFile));

}
 public static void main(String[] args) throws Exception{
detectFace("C:/Users/Lenovo/Desktop/89d31710d44cd15945059fe91f36cc64.jpg","C:/Users/Lenovo/Desktop/11.jpg");//人脸识别并截图
    }

效果图片
  • 2
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 4
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值