Java 调用 OpenCV (可获取到图像)
前言
感谢 年轻的老魏 Java实现opencv 调用本地摄像头,实现人脸识别、人形识别、人眼识别,在此基础上做的一点点优化
1.首先下载opencv
2.没有用System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
配置比较繁琐,采用了System.load(ClassLoader.getSystemResource("lib/opencv_java440.dll").getPath());
这种方式不用那么多配置,简单实用
简化版
package com.callOpencv; import org.opencv.core.*; import org.opencv.imgcodecs.Imgcodecs; import org.opencv.imgproc.Imgproc; import org.opencv.videoio.VideoCapture; import org.opencv.videoio.Videoio; import java.text.SimpleDateFormat; import java.util.Arrays; import java.util.Date; public class CallOpenCv { private static String rtsp_64 = "rtsp://账号:密码@192.168.0.64:554/stream0"; private static SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmssSSS"); private static String dir = "D:/VideoRec/Img"; private static Integer sleepCount = 0; public static void main(String[] args) { openVideo(); } private static void openVideo() { VideoCapture capture = null; try { System.load("D:/Program/opencv/build/java/x64/opencv_java440.dll"); capture = new VideoCapture(); capture.open(rtsp_64); int height = (int) capture.get(Videoio.CAP_PROP_FRAME_HEIGHT); int width = (int) capture.get(Videoio.CAP_PROP_FRAME_WIDTH); if (height == 0 || width == 0) { throw new Exception("camera not found!"); } Mat capImg = new Mat(); Mat temp = new Mat(); while (true) { capture.read(capImg); //opencv是1s读取24张图片(大概),想要1s处理一次,【先读取再扔掉】 if (++sleepCount <= 25) { continue; } sleepCount = 0; Imgproc.cvtColor(capImg, temp, Imgproc.COLOR_RGB2GRAY); Imgcodecs.imwrite(dir + "/" + sdf.format(new Date()) + ".jpg", temp); } } catch (Exception e) { System.out.println("异常:" + e.getMessage() + " --- " + Arrays.toString(e.getStackTrace())); } finally { if (capture != null && capture.isOpened()) { System.out.println("-----capture--done--"); capture.release(); } } } }
package com; import java.awt.Graphics; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent; import java.awt.event.MouseWheelEvent; import java.awt.image.BufferedImage; import java.net.URL; import java.util.Arrays; import javax.swing.JFrame; import javax.swing.JPanel; import javax.swing.WindowConstants; import org.opencv.core.Core; import org.opencv.core.Mat; import org.opencv.core.MatOfDouble; import org.opencv.core.MatOfRect; import org.opencv.core.Point; import org.opencv.core.Rect; import org.opencv.core.Scalar; import org.opencv.imgcodecs.Imgcodecs; import org.opencv.imgproc.Imgproc; import org.opencv.ml.SVM; import org.opencv.objdetect.CascadeClassifier; import org.opencv.objdetect.HOGDescriptor; import org.opencv.videoio.VideoCapture; import org.opencv.videoio.Videoio; public class CaptureBasic extends JPanel { private BufferedImage mImg; public static void main(String[] args) { try { //加载本地native库 配置较繁琐,不用 // System.loadLibrary(Core.NATIVE_LIBRARY_NAME); //获取opencv.dll绝对路径 推荐 URL url = ClassLoader.getSystemResource("lib/opencv_java440.dll"); System.load(url.getPath()); //获取本地摄像头 // VideoCapture capture = new VideoCapture(0); //获取网络摄像头 VideoCapture capture = new VideoCapture(); capture.open("rtsp://账号:密码@192.168.0.64:554/stream0"); int height = (int) capture.get(Videoio.CAP_PROP_FRAME_HEIGHT); int width = (int) capture.get(Videoio.CAP_PROP_FRAME_WIDTH); if (height == 0 || width == 0) { throw new Exception("camera not found!"); } //Java窗口容器 JFrame frame = new JFrame("camera"); frame.setDefaultCloseOperation(WindowConstants.DISPOSE_ON_CLOSE); //Java画板容器 CaptureBasic panel = new CaptureBasic(); addMouseListener(panel); //配置关系 frame.setContentPane(panel); frame.setVisible(true); frame.setSize(width + frame.getInsets().left + frame.getInsets().right, height + frame.getInsets().top + frame.getInsets().bottom); int n = 0; Mat capImg = new Mat(); Mat temp = new Mat(); while (frame.isShowing() && ++n < 500) { //把摄像头数据读到Mat capture.read(capImg); //彩色空间转换,把图像转换为灰度的、占用空间小的 Imgproc.cvtColor(capImg, temp, Imgproc.COLOR_RGB2GRAY); // temp = capImg.clone(); //保存 Imgcodecs.imwrite("D:/VideoRec/Img/back" + n + ".png", temp); //进行人脸识别 Mat mat = detectFace(capImg); //把识别画框图像放在画板上 panel.mImg = panel.mat2BI(mat); //绘制 panel.repaint(); } capture.release(); frame.dispose(); } catch (Exception e) { System.out.println("异常:" + e.getMessage() + " --- " + Arrays.toString(e.getStackTrace())); } finally { System.out.println("--done--"); } } private BufferedImage mat2BI(Mat mat) { int dataSize = mat.cols() * mat.rows() * (int) mat.elemSize(); byte[] data = new byte[dataSize]; mat.get(0, 0, data); int type = mat.channels() == 1 ? BufferedImage.TYPE_BYTE_GRAY : BufferedImage.TYPE_3BYTE_BGR; if (type == BufferedImage.TYPE_3BYTE_BGR) { for (int i = 0; i < dataSize; i += 3) { byte blue = data[i + 0]; data[i + 0] = data[i + 2]; data[i + 2] = blue; } } BufferedImage image = new BufferedImage(mat.cols(), mat.rows(), type); image.getRaster().setDataElements(0, 0, mat.cols(), mat.rows(), data); return image; } /** * opencv实现人脸识别 * * @param img */ public static Mat detectFace(Mat img) throws Exception { System.out.println("Running DetectFace ... "); // 从配置文件lbpcascade_frontalface.xml中创建一个人脸识别器,该文件位于opencv安装目录中 // CascadeClassifier faceDetector = new CascadeClassifier("D:\\TDDOWNLOAD\\opencv\\sources\\data\\haarcascades\\haarcascade_frontalface_alt.xml"); CascadeClassifier faceDetector = new CascadeClassifier("D:/Program/opencv/sources/data/haarcascades/haarcascade_frontalface_alt.xml"); // 在图片中检测人脸 MatOfRect faceDetections = new MatOfRect(); faceDetector.detectMultiScale(img, faceDetections); //System.out.println(String.format("Detected %s faces", faceDetections.toArray().length)); Rect[] rects = faceDetections.toArray(); if (rects != null && rects.length >= 1) { for (Rect rect : rects) { Imgproc.rectangle(img, new Point(rect.x, rect.y), new Point(rect.x + rect.width, rect.y + rect.height), new Scalar(0, 0, 255), 2); } } return img; } /** * opencv实现人型识别,hog默认的分类器。所以效果不好。 * * @param img */ public static Mat detectPeople(Mat img) { //System.out.println("detectPeople..."); if (img.empty()) { System.out.println("image is exist"); } HOGDescriptor hog = new HOGDescriptor(); hog.setSVMDetector(HOGDescriptor.getDefaultPeopleDetector()); System.out.println(HOGDescriptor.getDefaultPeopleDetector()); //hog.setSVMDetector(HOGDescriptor.getDaimlerPeopleDetector()); MatOfRect regions = new MatOfRect(); MatOfDouble foundWeights = new MatOfDouble(); //System.out.println(foundWeights.toString()); hog.detectMultiScale(img, regions, foundWeights); for (Rect rect : regions.toArray()) { Imgproc.rectangle(img, new Point(rect.x, rect.y), new Point(rect.x + rect.width, rect.y + rect.height), new Scalar(0, 0, 255), 2); } return img; } /** * 画到容器 * * @param g */ public void paintComponent(Graphics g) { if (mImg != null) { g.drawImage(mImg, 0, 0, mImg.getWidth(), mImg.getHeight(), this); } } /** * 添加鼠标监听 * * @param panel */ private static void addMouseListener(CaptureBasic panel) { panel.addMouseListener(new MouseAdapter() { @Override public void mouseClicked(MouseEvent e) { System.out.println("click"); } @Override public void mousePressed(MouseEvent e) { System.out.println("mousePressed"); } @Override public void mouseReleased(MouseEvent e) { System.out.println("mouseReleased"); } @Override public void mouseEntered(MouseEvent e) { System.out.println("mouseEntered"); } @Override public void mouseExited(MouseEvent e) { System.out.println("mouseExited"); } @Override public void mouseWheelMoved(MouseWheelEvent e) { System.out.println("mouseWheelMoved"); } @Override public void mouseDragged(MouseEvent e) { System.out.println("mouseDragged"); } @Override public void mouseMoved(MouseEvent e) { System.out.println("mouseMoved"); } }); } }
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· [.NET]调用本地 Deepseek 模型
· 一个费力不讨好的项目,让我损失了近一半的绩效!
· .NET Core 托管堆内存泄露/CPU异常的常见思路
· PostgreSQL 和 SQL Server 在统计信息维护中的关键差异
· C++代码改造为UTF-8编码问题的总结
· 【.NET】调用本地 Deepseek 模型
· CSnakes vs Python.NET:高效嵌入与灵活互通的跨语言方案对比
· DeepSeek “源神”启动!「GitHub 热点速览」
· 我与微信审核的“相爱相杀”看个人小程序副业
· Plotly.NET 一个为 .NET 打造的强大开源交互式图表库
2018-12-04 11.【Linq】