依赖jar包:
faceRecognition.java
1 package opencv; 2 3 import java.awt.Graphics; 4 import java.awt.image.BufferedImage; 5 6 import javax.swing.JFrame; 7 import javax.swing.JPanel; 8 import javax.swing.WindowConstants; 9 10 import org.opencv.core.Core; 11 import org.opencv.core.Mat; 12 import org.opencv.core.MatOfDouble; 13 import org.opencv.core.MatOfRect; 14 import org.opencv.core.Point; 15 import org.opencv.core.Rect; 16 import org.opencv.core.Scalar; 17 import org.opencv.imgproc.Imgproc; 18 import org.opencv.objdetect.CascadeClassifier; 19 import org.opencv.objdetect.HOGDescriptor; 20 import org.opencv.videoio.VideoCapture; 21 import org.opencv.videoio.Videoio; 22 23 @SuppressWarnings("serial") 24 public class faceRecognition extends JPanel { 25 26 private BufferedImage mImg; 27 28 private BufferedImage mat2BI(Mat mat) { 29 int dataSize = mat.cols() * mat.rows() * (int) mat.elemSize(); 30 byte[] data = new byte[dataSize]; 31 mat.get(0, 0, data); 32 int type = mat.channels() == 1 ? BufferedImage.TYPE_BYTE_GRAY : BufferedImage.TYPE_3BYTE_BGR; 33 34 if (type == BufferedImage.TYPE_3BYTE_BGR) { 35 for (int i = 0; i < dataSize; i += 3) { 36 byte blue = data[i + 0]; 37 data[i + 0] = data[i + 2]; 38 data[i + 2] = blue; 39 } 40 } 41 BufferedImage image = new BufferedImage(mat.cols(), mat.rows(), type); 42 image.getRaster().setDataElements(0, 0, mat.cols(), mat.rows(), data); 43 44 return image; 45 } 46 47 public void paintComponent(Graphics g) { 48 if (mImg != null) { 49 g.drawImage(mImg, 0, 0, mImg.getWidth(), mImg.getHeight(), this); 50 } 51 } 52 53 public static void main(String[] args) { 54 try { 55 System.loadLibrary(Core.NATIVE_LIBRARY_NAME); 56 57 Mat capImg = new Mat(); 58 VideoCapture capture = new VideoCapture(0); 59 int height = (int) capture.get(Videoio.CAP_PROP_FRAME_HEIGHT); 60 int width = (int) capture.get(Videoio.CAP_PROP_FRAME_WIDTH); 61 if (height == 0 || width == 0) { 62 throw new Exception("未发现摄像头!"); 63 } 64 65 // 创建jframe 66 JFrame frame = new JFrame("摄像头"); 67 frame.setDefaultCloseOperation(WindowConstants.DISPOSE_ON_CLOSE); 68 faceRecognition panel = new faceRecognition(); 69 // 添加鼠标监听器 70 // panel.addMouseListener(new MouseAdapter() { 71 // @Override 72 // public void mouseClicked(MouseEvent arg0) { 73 // System.out.println("鼠标点击"); 74 // } 75 // 76 // @Override 77 // public void mouseMoved(MouseEvent arg0) { 78 // System.out.println("鼠标移开"); 79 // 80 // } 81 // 82 // @Override 83 // public void mouseReleased(MouseEvent arg0) { 84 // System.out.println("鼠标释放"); 85 // } 86 // 87 // @Override 88 // public void mousePressed(MouseEvent arg0) { 89 // System.out.println("鼠标按下"); 90 // } 91 // 92 // @Override 93 // public void mouseExited(MouseEvent arg0) { 94 // System.out.println("鼠标出界"); 95 // // System.out.println(arg0.toString()); 96 // } 97 // 98 // @Override 99 // public void mouseDragged(MouseEvent arg0) { 100 // System.out.println("mouseDragged"); 101 // // System.out.println(arg0.toString()); 102 // } 103 // }); 104 frame.setContentPane(panel); 105 frame.setVisible(true); 106 frame.setSize(width + frame.getInsets().left + frame.getInsets().right, 107 height + frame.getInsets().top + frame.getInsets().bottom); 108 int n = 1; 109 Mat temp = new Mat(); 110 // while (frame.isShowing() && n <= 500) { 111 while (frame.isShowing()) { 112 // System.out.println("第" + n + "张"); 113 capture.read(capImg); // 载入图片 114 Imgproc.cvtColor(capImg, temp, Imgproc.COLOR_RGB2GRAY); 115 // Imgcodecs.imwrite("E:/opencv/wzg/picture_" + n + ".png", temp); // 存储图片到本地 116 panel.mImg = panel.mat2BI(detectFace(capImg)); // 调用人脸识别方法 117 panel.repaint(); 118 // n++; 119 // break; // 识别500存入本地 120 } 121 capture.release(); 122 frame.dispose(); 123 } catch (Exception e) { 124 System.out.println("例外:" + e); 125 } finally { 126 System.out.println("--done--"); 127 } 128 129 } 130 131 /** 132 * opencv实现人脸识别 133 * 134 * @param img 135 */ 136 public static Mat detectFace(Mat img) throws Exception { 137 138 // System.out.println("开始人像识别 ... "); 139 // 从配置文件lbpcascade_frontalface.xml中创建一个人脸识别器,该文件位于opencv安装目录中 140 CascadeClassifier faceDetector = new CascadeClassifier("E:\my_dev\haarcascade_frontalface_alt.xml"); 141 142 // 在图片中检测人脸 143 MatOfRect faceDetections = new MatOfRect(); 144 145 faceDetector.detectMultiScale(img, faceDetections); 146 147 if (faceDetections.toArray().length == 0) { 148 // System.out.println("no face"); 149 } else { 150 System.out.println(String.format("检测到 %s 个人像", faceDetections.toArray().length)); 151 } 152 153 Rect[] rects = faceDetections.toArray(); 154 if (rects != null && rects.length >= 1) { 155 for (Rect rect : rects) { 156 Imgproc.rectangle(img, new Point(rect.x, rect.y), new Point(rect.x + rect.width, rect.y + rect.height), 157 new Scalar(0, 0, 255), 2); 158 } 159 } 160 return img; 161 } 162 163 /** 164 * opencv实现人型识别,hog默认的分类器。所以效果不好。 165 * 166 * @param img 167 */ 168 public static Mat detectPeople(Mat img) { 169 // System.out.println("detectPeople..."); 170 if (img.empty()) { 171 System.out.println("image is exist"); 172 } 173 HOGDescriptor hog = new HOGDescriptor(); 174 hog.setSVMDetector(HOGDescriptor.getDefaultPeopleDetector()); 175 System.out.println(HOGDescriptor.getDefaultPeopleDetector()); 176 hog.setSVMDetector(HOGDescriptor.getDaimlerPeopleDetector()); 177 MatOfRect regions = new MatOfRect(); 178 MatOfDouble foundWeights = new MatOfDouble(); 179 System.out.println(foundWeights.toString()); 180 hog.detectMultiScale(img, regions, foundWeights); 181 for (Rect rect : regions.toArray()) { 182 Imgproc.rectangle(img, new Point(rect.x, rect.y), new Point(rect.x + rect.width, rect.y + rect.height), 183 new Scalar(0, 0, 255), 2); 184 } 185 return img; 186 } 187 188 }