From entry to mastery of javacv - Chapter 11 In-depth understanding of JavaCV's advanced features of JavaCV

  1. Advanced Image Processing

JavaCV provides many advanced image processing functions, including image filtering, edge detection, morphological operations, image segmentation and feature extraction, etc. Following are some advanced image processing features in JavaCV:

  1. image filtering

JavaCV supports various image filtering algorithms, such as mean filtering, Gaussian filtering, median filtering, bilateral filtering, etc. These filtering algorithms can effectively reduce noise, smooth images and improve image quality.

import org.bytedeco.javacpp.opencv_core;
import org.bytedeco.javacpp.opencv_imgproc;

public class ImageFilteringExample {
    public static void main(String[] args) {
        // 加载图像
        opencv_core.Mat src = opencv_imgcodecs.imread("lena.png");
        opencv_core.Mat dst = new opencv_core.Mat();
        
        // 高斯滤波
        opencv_imgproc.GaussianBlur(src, dst, new opencv_core.Size(3, 3), 0);
        
        // 显示结果
        CanvasFrame frame = new CanvasFrame("Image Filtering Example");
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        frame.showImage(new Java2DFrameConverter().convert(dst));
    }
}
  1. edge detection

JavaCV provides a variety of edge detection algorithms, such as Sobel, Canny, Laplacian, etc. These algorithms can be used to detect edges in images for further image analysis and processing.

import org.bytedeco.javacpp.opencv_core;
import org.bytedeco.javacpp.opencv_imgproc;

public class EdgeDetectionExample {
    public static void main(String[] args) {
        // 加载图像
        opencv_core.Mat src = opencv_imgcodecs.imread("lena.png");
        opencv_core.Mat gray = new opencv_core.Mat();
        opencv_core.Mat edges = new opencv_core.Mat();
        
        // 灰度化
        opencv_imgproc.cvtColor(src, gray, opencv_imgproc.COLOR_BGR2GRAY);
        
        // Canny边缘检测
        opencv_imgproc.Canny(gray, edges, 50, 150);
        
        // 显示结果
        CanvasFrame frame = new CanvasFrame("Edge Detection Example");
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        frame.showImage(new Java2DFrameConverter().convert(edges));
    }
}
  1. Morphological operation

JavaCV supports various morphological operations, such as erosion, dilation, opening operation, closing operation, etc. These operations can be used to process binary images or grayscale images, and can be applied to image segmentation, morphological reconstruction and other fields.

import org.bytedeco.javacpp.opencv_core;
import org.bytedeco.javacpp.opencv_imgproc;

public class MorphologyExample {
    public static void main(String[] args) {
        // 加载图像
        opencv_core.Mat src = opencv_imgcodecs.imread("text.png");
        opencv_core.Mat gray = new opencv_core.Mat();
        opencv_core.Mat binary = new opencv_core.Mat();
        opencv_core.Mat closed = new opencv_core.Mat();
        
        // 灰度化
        opencv_imgproc.cvtColor(src, gray, opencv_imgproc.COLOR_BGR2GRAY);
        
        // 二值化
        opencv_imgproc.threshold(gray, binary, 0, 255, opencv_imgproc.THRESH_BINARY_INV | opencv_imgproc.THRESH_OTSU);
        
        // 闭操作
        opencv_core.Mat kernel = opencv_imgproc.getStructuringElement(opencv_imgproc.MORPH_RECT, new opencv_core.Size(5, 5));
        opencv_imgproc.morphologyEx(binary, closed, opencv_imgproc.MORPH_CLOSE, kernel);
        
        // 显示结果
        CanvasFrame frame = new CanvasFrame("Morphology Example");
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        frame.showImage(new Java2DFrameConverter().convert(closed));
    }
}
  1. Image segmentation

JavaCV supports various image segmentation algorithms, such as threshold-based segmentation, region growing, watershed algorithm, etc. These algorithms can divide an image into multiple distinct regions for further image analysis and processing.

import org.bytedeco.javacpp.opencv_core;
import org.bytedeco.javacpp.opencv_imgproc;

public class ImageSegmentationExample {
    public static void main(String[] args) {
        // 加载图像
        opencv_core.Mat src = opencv_imgcodecs.imread("coins.jpg");
        opencv_core.Mat gray = new opencv_core.Mat();
        opencv_core.Mat binary = new opencv_core.Mat();
        opencv_core.Mat labels = new opencv_core.Mat();
        opencv_core.Mat stats = new opencv_core.Mat();
        opencv_core.Mat centroids = new opencv_core.Mat();
        
        // 灰度化
        opencv_imgproc.cvtColor(src, gray, opencv_imgproc.COLOR_BGR2GRAY);
        
        // 二值化
        opencv_imgproc.threshold(gray, binary, 0, 255, opencv_imgproc.THRESH_BINARY_INV | opencv_imgproc.THRESH_OTSU);
        
        // 连通组件标记
        opencv_imgproc.connectedComponentsWithStats(binary, labels, stats, centroids);
        
        // 绘制结果
        opencv_core.Mat result = new opencv_core.Mat();
        opencv_core.cvtColor(src, result, opencv_imgproc.COLOR_BGR2GRAY);
        for (int i = 1; i < stats.rows(); i++) {
            int x = (int) stats.ptr(i, opencv_imgproc.CC_STAT_LEFT)[0];
            int y = (int) stats.ptr(i, opencv_imgproc.CC_STAT_TOP)[0];
            int w = (int) stats.ptr(i, opencv_imgproc.CC_STAT_WIDTH)[0];
            int h = (int) stats.ptr(i, opencv_imgproc.CC_STAT_HEIGHT)[0];
            opencv_core.rectangle(result, new opencv_core.Point(x, y), new opencv_core.Point(x + w, y + h), opencv_core.Scalar.RED);
        }
        
        // 显示结果
        CanvasFrame frame = new CanvasFrame("Image Segmentation Example");
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        frame.showImage(new Java2DFrameConverter().convert(result));
    }
}
  1. feature extraction

JavaCV provides various feature extraction algorithms, such as SIFT, SURF, ORB, HOG, etc. These algorithms can extract key points and feature descriptors in images for image matching, object recognition and other fields.

The ORB algorithm is a feature point detector based on the FAST algorithm. Compared with the SIFT and SURF algorithms, the ORB algorithm has the advantages of fast speed, high precision, and good robustness. The following is a code example for the ORB algorithm:

import org.bytedeco.javacpp.BytePointer;
import org.bytedeco.javacpp.opencv_core;
import org.bytedeco.javacpp.opencv_features2d;
import org.bytedeco.javacpp.opencv_imgcodecs;

public class ORBExample {
    public static void main(String[] args) {
        // 加载图像
        opencv_core.Mat src = opencv_imgcodecs.imread("lena.png");
        opencv_core.Mat gray = new opencv_core.Mat();
        
        // 灰度化
        opencv_imgproc.cvtColor(src, gray, opencv_imgproc.COLOR_BGR2GRAY);
        
        // ORB特征点检测
        opencv_features2d.ORB orb = opencv_features2d.ORB.create();
        opencv_core.MatOfKeyPoint keyPoints = new opencv_core.MatOfKeyPoint();
        opencv_core.Mat descriptors = new opencv_core.Mat();
        orb.detectAndCompute(gray, new opencv_core.Mat(), keyPoints, descriptors);
        
        // 绘制特征点
        opencv_core.Mat result = new opencv_core.Mat();
        opencv_features2d.drawKeypoints(src, keyPoints, result);
        
        // 显示结果
        CanvasFrame frame = new CanvasFrame("ORB Example");
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        frame.showImage(new Java2DFrameConverter().convert(result));
    }
}

The BRISK algorithm is a feature point detector based on the FAST algorithm. Compared with the ORB algorithm, the BRISK algorithm has faster speed and better rotation invariance, but is less robust to scale changes and viewing angle changes. Here is a code example of the BRISK algorithm:

import org.bytedeco.javacpp.BytePointer;
import org.bytedeco.javacpp.opencv_core;
import org.bytedeco.javacpp.opencv_features2d;
import org.bytedeco.javacpp.opencv_imgcodecs;

public class BRISKExample {
    public static void main(String[] args) {
        // 加载图像
        opencv_core.Mat src = opencv_imgcodecs.imread("lena.png");
        opencv_core.Mat gray = new opencv_core.Mat();
        
        // 灰度化
        opencv_imgproc.cvtColor(src, gray, opencv_imgproc.COLOR_BGR2GRAY);
        
        // BRISK特征点检测
        opencv_features2d.BRISK brisk = opencv_features2d.BRISK.create();
        opencv_core.MatOfKeyPoint keyPoints = new opencv_core.MatOfKeyPoint();
        opencv_core.Mat descriptors = new opencv_core.Mat();
        brisk.detectAndCompute(gray, new opencv_core.Mat(), keyPoints, descriptors);
        
        // 绘制特征点
        opencv_core.Mat result = new opencv_core.Mat();
        opencv_features2d.drawKeypoints(src, keyPoints, result);
    // 显示结果
        CanvasFrame frame = new CanvasFrame("BRISK Example");
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        frame.showImage(new Java2DFrameConverter().convert(result));
    }
}

The following is a code example for feature matching using feature descriptors based on the SIFT algorithm:

import org.bytedeco.javacpp.BytePointer;
import org.bytedeco.javacpp.opencv_core;
import org.bytedeco.javacpp.opencv_features2d;
import org.bytedeco.javacpp.opencv_imgcodecs;
import org.bytedeco.javacpp.opencv_nonfree.SIFT;

public class SIFTExample {
    public static void main(String[] args) {
        // 加载图像
        opencv_core.Mat src1 = opencv_imgcodecs.imread("lena.png");
        opencv_core.Mat src2 = opencv_imgcodecs.imread("lena_rotate.png");
        opencv_core.Mat gray1 = new opencv_core.Mat();
        opencv_core.Mat gray2 = new opencv_core.Mat();
        
        // 灰度化
        opencv_imgproc.cvtColor(src1, gray1, opencv_imgproc.COLOR_BGR2GRAY);
        opencv_imgproc.cvtColor(src2, gray2, opencv_imgproc.COLOR_BGR2GRAY);
        
        // SIFT特征点检测和特征描述
        SIFT sift = new SIFT();
        opencv_core.MatOfKeyPoint keyPoints1 = new opencv_core.MatOfKeyPoint();
        opencv_core.MatOfKeyPoint keyPoints2 = new opencv_core.MatOfKeyPoint();
        opencv_core.Mat descriptors1 = new opencv_core.Mat();
        opencv_core.Mat descriptors2 = new opencv_core.Mat();
        sift.detectAndCompute(gray1, new opencv_core.Mat(), keyPoints1, descriptors1);
        sift.detectAndCompute(gray2, new opencv_core.Mat(), keyPoints2, descriptors2);
        
        // 特征匹配
        opencv_features2d.BFMatcher matcher = new opencv_features2d.BFMatcher(opencv_core.NORM_L2, true);
        opencv_core.DMatchVectorVector matches = new opencv_core.DMatchVectorVector();
        matcher.knnMatch(descriptors1, descriptors2, matches, 2);
        
        // 筛选匹配结果
        opencv_core.MatOfDMatch goodMatches = new opencv_core.MatOfDMatch();
        for (int i = 0; i < matches.size(); i++) {
            opencv_core.DMatchVector match = matches.get(i);
            if (match.size() == 2 && match.get(0).distance() < 0.7 * match.get(1).distance()) {
                goodMatches.fromArray(match.get(0));
            }
        }
        
        // 绘制匹配结果
        opencv_core.Mat result = new opencv_core.Mat();
        opencv_features2d.drawMatches(src1, keyPoints1, src2, keyPoints2, goodMatches, result);
        // 显示结果
        CanvasFrame frame = new CanvasFrame("SIFT Example");
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        frame.showImage(new Java2DFrameConverter().convert(result));
    }

}

In the above code, first load two images and convert them into grayscale images, then use the SIFT algorithm for feature point detection and feature description, then use the Brute-Force matcher for feature point matching, and finally pass the filtered good Match Results draws a match line and displays the results.

The following is a code example for image fusion using SIFT algorithm-based image registration:

import org.bytedeco.javacpp.opencv_core;
import org.bytedeco.javacpp.opencv_features2d;
import org.bytedeco.javacpp.opencv_imgcodecs;
import org.bytedeco.javacpp.opencv_nonfree.SIFT;
import org.bytedeco.javacpp.opencv_stitching.DetailStitcher;

public class ImageStitchingExample {
    public static void main(String[] args) {
        // 加载图像
        opencv_core.Mat src1 = opencv_imgcodecs.imread("img1.jpg");
        opencv_core.Mat src2 = opencv_imgcodecs.imread("img2.jpg");
        opencv_core.Mat gray1 = new opencv_core.Mat();
        opencv_core.Mat gray2 = new opencv_core.Mat();
        
        // 灰度化
        opencv_imgproc.cvtColor(src1, gray1, opencv_imgproc.COLOR_BGR2GRAY);
        opencv_imgproc.cvtColor(src2, gray2, opencv_imgproc.COLOR_BGR2GRAY);
        
        // SIFT特征点检测和特征描述
        SIFT sift = new SIFT();
        opencv_core.MatOfKeyPoint keyPoints1 = new opencv_core.MatOfKeyPoint();
        opencv_core.MatOfKeyPoint keyPoints2 = new opencv_core.MatOfKeyPoint();
        opencv_core.Mat descriptors1 = new opencv_core.Mat();
        opencv_core.Mat descriptors2 = new opencv_core.Mat();
        sift.detectAndCompute(gray1, new opencv_core.Mat(), keyPoints1, descriptors1);
        sift.detectAndCompute(gray2, new opencv_core.Mat(), keyPoints2, descriptors2);
        
        // 特征点匹配
        opencv_features2d.BFMatcher matcher = new opencv_features2d.BFMatcher(opencv_core.NORM_L2, true);
        opencv_core.DMatchVectorVector matches = new opencv_core.DMatchVectorVector();
        matcher.knnMatch(descriptors1, descriptors2, matches, 2);
        
        // 筛选匹配结果
        opencv_core.MatOfDMatch goodMatches = new opencv_core.MatOfDMatch();
        for (int i = 0; i < matches.size(); i++) {
            opencv_core.DMatchVector match = matches.get(i);
            if (match.size() >= 2) {
                opencv_core.DMatch m1 = match.get(0);
                opencv_core.DMatch m2 = match.get(1);
                if (m1.distance() < 0.7 * m2.distance()) {
                    goodMatches.push_back(new opencv_core.MatOfDMatch(m1));
                }
            }
        }
        // 图像配准
        DetailStitcher stitcher = new DetailStitcher();
        opencv_core.Mat result = new opencv_core.Mat();
        opencv_core.MatVector src = new opencv_core.MatVector(2);
        src.put(0, src1);
        src.put(1, src2);
        opencv_core.MatOfInt indices = new opencv_core.MatOfInt(0, 1);
        opencv_core.MatOfIntVector matchesIndices = new opencv_core.MatOfIntVector();
        matchesIndices.push_back(goodMatches);
        stitcher.stitch(src, indices, result, matchesIndices);
        
        // 显示结果
        CanvasFrame frame = new CanvasFrame("Image Stitching Example");
        frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        frame.showImage(new Java2DFrameConverter().convert(result));
    }
}

In the above code, first load two images and convert them into grayscale images, then use the SIFT algorithm for feature point detection and feature description, then use the Brute-Force matcher for feature point matching and filter out good matching results, Finally, an image registration algorithm based on the SIFT algorithm is used for image registration and image fusion, and finally a stitched image is obtained.

  1. Advanced Video Processing

JavaCV is a computer vision library based on the Java platform, which is the encapsulation of OpenCV on the Java platform. JavaCV provides a range of advanced features, including advanced video processing. Below, I'll detail the features of JavaCV's advanced video processing.

  1. Video Capture and Video Recording

JavaCV provides two classes VideoCapture and FFmpegFrameRecorder for video capture and video recording. VideoCapture can capture video from multiple sources like webcam, video file, webcam, etc., while FFmpegFrameRecorder can record video to multiple destinations like video file, RTSP server, etc.

  1. Video codec and format conversion

JavaCV provides a series of codec and format conversion functions through FFmpeg and OpenCV libraries. You can use the FFmpegFrameGrabber and FFmpegFrameRecorder classes to codec and convert video.

  1. video stream processing

JavaCV provides FFmpegFrameGrabber and FFmpegFrameRecorder classes to handle video streams. You can grab video from streaming media sources such as webcams and RTSP servers, and you can also publish video streams to RTSP servers.

  1. Video Analysis and Processing

JavaCV provides a set of functions for image processing and analysis. Various operations on video such as image enhancement, object detection, tracking, motion estimation, etc. can be performed using the OpenCV library. In addition, JavaCV also provides a library called JavaCV FX, which is an extension of JavaFX and can be used to implement interactive user interfaces for image and video processing in Java applications.

  1. Video codec optimization

JavaCV improves the speed of video encoding and decoding by using hardware acceleration. JavaCV uses the optimized code provided by the OpenCV library, and uses SIMD instructions to accelerate video encoding and decoding. JavaCV also supports GPU-based acceleration, using the CUDA library to take advantage of the GPU's parallel computing capabilities.

Guess you like

Origin blog.csdn.net/ayou_llf/article/details/129432816