OpenCV - Hướng dẫn nhanh
OpenCV là một thư viện đa nền tảng sử dụng mà chúng tôi có thể phát triển theo thời gian thực computer vision applications. Nó chủ yếu tập trung vào xử lý hình ảnh, quay video và phân tích bao gồm các tính năng như nhận diện khuôn mặt và phát hiện đối tượng.
Hãy bắt đầu chương bằng cách định nghĩa thuật ngữ "Thị giác máy tính".
Tầm nhìn máy tính
Thị giác máy tính có thể được định nghĩa là một môn học giải thích cách tái tạo, ngắt và hiểu một cảnh 3D từ hình ảnh 2D của nó, xét về các thuộc tính của cấu trúc hiện diện trong cảnh đó. Nó đề cập đến việc mô hình hóa và tái tạo tầm nhìn của con người bằng phần mềm và phần cứng máy tính.
Thị giác Máy tính trùng lặp đáng kể với các trường sau:
Image Processing - Nó tập trung vào thao tác hình ảnh.
Pattern Recognition - Nó giải thích các kỹ thuật khác nhau để phân loại các mẫu.
Photogrammetry - Có liên quan đến việc thu được các phép đo chính xác từ hình ảnh.
Xử lý hình ảnh Computer Vision Vs
Image processinggiải quyết việc chuyển đổi hình ảnh sang hình ảnh. Đầu vào và đầu ra của quá trình xử lý hình ảnh đều là hình ảnh.
Computer visionlà việc xây dựng các mô tả rõ ràng, có ý nghĩa về các đối tượng vật chất từ hình ảnh của chúng. Đầu ra của thị giác máy tính là mô tả hoặc diễn giải các cấu trúc trong cảnh 3D.
Các ứng dụng của Thị giác máy tính
Ở đây chúng tôi đã liệt kê một số miền chính mà Computer Vision được sử dụng nhiều.
Ứng dụng người máy
Bản địa hóa - Tự động xác định vị trí rô bốt
Navigation
Tránh chướng ngại vật
Lắp ráp (chốt trong lỗ, hàn, sơn)
Thao tác (ví dụ: người điều khiển robot PUMA)
Tương tác với người máy (HRI) - Robot thông minh để tương tác và phục vụ con người
Đơn thuốc
- Phân loại và phát hiện (ví dụ như phân loại tổn thương hoặc tế bào và phát hiện khối u)
- Phân đoạn 2D / 3D
- Tái tạo nội tạng người 3D (MRI hoặc siêu âm)
- Phẫu thuật robot có hướng dẫn thị giác
Ứng dụng tự động hóa công nghiệp
- Kiểm tra công nghiệp (phát hiện khuyết tật)
- Assembly
- Đọc mã vạch và nhãn gói
- Phân loại đối tượng
- Hiểu tài liệu (ví dụ OCR)
Ứng dụng bảo mật
Sinh trắc học (mống mắt, vân tay, nhận dạng khuôn mặt)
Giám sát - Phát hiện một số hoạt động hoặc hành vi đáng ngờ
Ứng dụng Vận chuyển
- Xe tự hành
- An toàn, ví dụ, giám sát cảnh giác của người lái xe
Các tính năng của Thư viện OpenCV
Sử dụng thư viện OpenCV, bạn có thể -
Đọc và ghi hình ảnh
Chụp và lưu video
Xử lý hình ảnh (lọc, biến đổi)
Thực hiện phát hiện tính năng
Phát hiện các đối tượng cụ thể như khuôn mặt, mắt, ô tô, trong video hoặc hình ảnh.
Phân tích video, tức là ước tính chuyển động trong đó, trừ hậu cảnh và theo dõi các đối tượng trong đó.
OpenCV ban đầu được phát triển bằng C ++. Ngoài ra, các liên kết Python và Java đã được cung cấp. OpenCV chạy trên nhiều Hệ điều hành khác nhau như windows, Linux, OSx, FreeBSD, Net BSD, Open BSD, v.v.
Hướng dẫn này giải thích các khái niệm về OpenCV với các ví dụ sử dụng liên kết Java.
Mô-đun thư viện OpenCV
Sau đây là các mô-đun thư viện chính của thư viện OpenCV.
Chức năng cốt lõi
Mô-đun này bao gồm các cấu trúc dữ liệu cơ bản như Scalar, Point, Range, v.v., được sử dụng để xây dựng các ứng dụng OpenCV. Ngoài những thứ này, nó cũng bao gồm mảng đa chiềuMat, được sử dụng để lưu trữ hình ảnh. Trong thư viện Java của OpenCV, mô-đun này được bao gồm dưới dạng một gói với tênorg.opencv.core.
Đang xử lý hình ảnh
Mô-đun này bao gồm các hoạt động xử lý hình ảnh khác nhau như lọc hình ảnh, biến đổi hình ảnh hình học, chuyển đổi không gian màu, biểu đồ, v.v. Trong thư viện Java của OpenCV, mô-đun này được bao gồm dưới dạng một gói với tên org.opencv.imgproc.
Video
Mô-đun này bao gồm các khái niệm phân tích video như ước tính chuyển động, trừ nền và theo dõi đối tượng. Trong thư viện Java của OpenCV, mô-đun này được bao gồm dưới dạng một gói với tênorg.opencv.video.
I / O video
Mô-đun này giải thích codec quay video và video bằng thư viện OpenCV. Trong thư viện Java của OpenCV, mô-đun này được bao gồm dưới dạng một gói với tênorg.opencv.videoio.
hiệu chỉnh3d
Mô-đun này bao gồm các thuật toán liên quan đến thuật toán hình học nhiều chế độ xem cơ bản, hiệu chỉnh máy ảnh đơn và âm thanh nổi, ước tính tư thế đối tượng, tương ứng âm thanh nổi và các yếu tố của tái tạo 3D. Trong thư viện Java của OpenCV, mô-đun này được bao gồm dưới dạng một gói với tênorg.opencv.calib3d.
features2d
Mô-đun này bao gồm các khái niệm về phát hiện và mô tả tính năng. Trong thư viện Java của OpenCV, mô-đun này được bao gồm dưới dạng một gói với tênorg.opencv.features2d.
Objectdetect
Mô-đun này bao gồm việc phát hiện các đối tượng và cá thể của các lớp được xác định trước như khuôn mặt, mắt, cốc, người, ô tô, v.v. Trong thư viện Java của OpenCV, mô-đun này được bao gồm dưới dạng một gói với tên org.opencv.objdetect.
Highgui
Đây là một giao diện dễ sử dụng với khả năng UI đơn giản. Trong thư viện Java của OpenCV, các tính năng của mô-đun này được bao gồm trong hai gói khác nhau, cụ thể là,org.opencv.imgcodecs và org.opencv.videoio.
Lược sử về OpenCV
OpenCV ban đầu là một sáng kiến nghiên cứu của Intel nhằm tư vấn cho các ứng dụng sử dụng nhiều CPU. Nó được chính thức ra mắt vào năm 1999.
- Vào năm 2006, phiên bản chính đầu tiên của nó, OpenCV 1.0 đã được phát hành.
- Vào tháng 10 năm 2009, phiên bản chính thứ hai, OpenCV 2 được phát hành.
- Vào tháng 8 năm 2012, OpenCV đã được một tổ chức phi lợi nhuận OpenCV.org thực hiện.
Trong chương này, bạn sẽ học cách cài đặt OpenCV và thiết lập môi trường của nó trong hệ thống của bạn.
Cài đặt OpenCV
Trước hết, bạn cần tải OpenCV vào hệ thống của mình. Làm theo các bước dưới đây.
Step 1 - Mở trang chủ của OpenCV bằng cách nhấp vào liên kết sau: http://opencv.org/ Khi nhấp vào, bạn sẽ thấy trang chủ của nó như hình bên dưới.
Step 2 - Bây giờ, hãy nhấp vào Downloadsliên kết được đánh dấu trong ảnh chụp màn hình ở trên. Khi nhấp vào, bạn sẽ được dẫn đến trang tải xuống của OpenCV.
Step 3 - Khi nhấp vào liên kết được đánh dấu trong ảnh chụp màn hình ở trên, một tệp có tên opencv-3.1.0.exesẽ được tải xuống. Giải nén tệp này để tạo một thư mụcopencv trong hệ thống của bạn, như được hiển thị trong ảnh chụp màn hình sau.
Step 4 - Mở thư mục OpenCV → build → java. Ở đây bạn sẽ tìm thấy tệp jar của OpenCV có tênopencv-310.jar. Lưu tệp này vào một thư mục riêng để sử dụng thêm.
Cài đặt Eclipse
Sau khi tải xuống các tệp JAR cần thiết, bạn phải nhúng các tệp JAR này vào môi trường Eclipse của mình. Bạn có thể làm điều này bằng cách đặt Đường dẫn xây dựng cho các tệp JAR này và bằng cách sử dụngpom.xml.
Đặt đường dẫn xây dựng
Sau đây là các bước để thiết lập OpenCV trong Eclipse:
Step 1- Đảm bảo rằng bạn đã cài đặt Eclipse trong hệ thống của mình. Nếu không, hãy tải xuống và cài đặt Eclipse trong hệ thống của bạn.
Step 2 - Mở Eclipse, nhấp vào Tệp, Mới và Mở một dự án mới như thể hiện trong ảnh chụp màn hình sau.
Step 3 - Khi chọn dự án, bạn sẽ nhận được New ProjectThuật sĩ. Trong trình hướng dẫn này, hãy chọn dự án Java và tiếp tục bằng cách nhấp vàoNext , như được hiển thị trong ảnh chụp màn hình sau.
Step 4 - Khi tiếp tục về phía trước, bạn sẽ được chuyển hướng đến New Java Project wizard. Tạo một dự án mới và nhấp vàoNext, như được hiển thị trong ảnh chụp màn hình sau đây.
Step 5- Sau khi tạo một dự án mới, nhấp chuột phải vào nó. Lựa chọnBuild Path và bấm vào Configure Build Path… như thể hiện trong ảnh chụp màn hình sau đây.
Step 6 - Khi nhấp vào Build Path tùy chọn, bạn sẽ được chuyển hướng đến Java Build Path wizard. Nhấn vàoAdd External JARs , như được hiển thị trong ảnh chụp màn hình sau.
Step 7 - Chọn đường dẫn mà bạn đã lưu tệp opencv-310.jar.
Step 8 - Khi nhấp vào Open trong ảnh chụp màn hình ở trên, những tệp đó sẽ được thêm vào thư viện của bạn.
Step 9 - Khi nhấp vào OK, bạn sẽ thêm thành công các tệp JAR cần thiết vào dự án hiện tại và bạn có thể xác minh các thư viện đã thêm này bằng cách mở rộng Thư viện được tham chiếu.
Đặt đường dẫn cho thư viện gốc
Ngoài các tệp JAR, bạn cần đặt đường dẫn cho các thư viện gốc (tệp DLL) của OpenCV.
Location of DLL files - Mở thư mục cài đặt của OpenCV và đi đến thư mục con build → java. Ở đây bạn sẽ tìm thấy hai thư mụcx64 (64 bit) và x86 (32 bit) chứa dll tệp của OpenCV.
Mở thư mục tương ứng phù hợp với hệ điều hành của bạn, sau đó bạn có thể thấy dll , như được hiển thị trong ảnh chụp màn hình sau.
Bây giờ, hãy đặt cả đường dẫn cho tệp này bằng cách làm theo các bước dưới đây:
Step 1- Một lần nữa, mở cửa sổ JavaBuildPath. Tại đây, bạn có thể quan sát tệp JAR được thêm vào vàJRE System Library.
Step 2 - Khi mở rộng nó, bạn sẽ nhận được các thư viện hệ thống và Native library location, như được đánh dấu trong ảnh chụp màn hình sau.
Step 3 - Nhấp đúp vào Native library location. Tại đây, bạn có thể thấyNative Library Folder Configuration window như hình bên dưới.
Tại đây, hãy nhấp vào nút External Folder… và chọn vị trí của dll tệp trong hệ thống của bạn.
Để chụp ảnh, chúng tôi sử dụng các thiết bị như máy ảnh và máy quét. Các thiết bị này ghi lại các giá trị số của hình ảnh (Ví dụ: giá trị pixel). OpenCV là một thư viện xử lý hình ảnh kỹ thuật số, do đó chúng ta cần lưu trữ những hình ảnh này để xử lý.
Các Matlớp của thư viện OpenCV được sử dụng để lưu trữ các giá trị của một hình ảnh. Nó đại diện cho một mảng n chiều và được sử dụng để lưu trữ dữ liệu hình ảnh có thang độ xám hoặc hình ảnh màu, khối lượng voxel, trường vectơ, đám mây điểm, tensor, biểu đồ, v.v.
Lớp này bao gồm hai phần dữ liệu: header và một pointer
Header - Chứa thông tin như kích thước, phương pháp được sử dụng để lưu trữ và địa chỉ của ma trận (kích thước không đổi).
Pointer - Lưu trữ các giá trị pixel của hình ảnh (Luôn thay đổi).
Lớp Mat
Thư viện OpenCV Java cung cấp lớp này có cùng tên (Mat) trong gói org.opencv.core.
Người xây dựng
Lớp Mat của thư viện Java OpenCV có nhiều hàm tạo khác nhau, bạn có thể sử dụng nó để tạo đối tượng Mat.
S. không | Trình tạo và mô tả |
---|---|
1 | Mat() Đây là hàm tạo mặc định không có tham số trong hầu hết các trường hợp. Chúng tôi sử dụng hàm này để tạo ra một ma trận trống và chuyển nó cho các phương thức OpenCV khác. |
2 | Mat(int rows, int cols, int type) Hàm tạo này chấp nhận ba tham số kiểu số nguyên đại diện cho số hàng và cột trong một mảng 2D và kiểu của mảng (được sử dụng để lưu trữ dữ liệu). |
3 | Mat(int rows, int cols, int type, Scalar s) Bao gồm các tham số của cái trước, hàm tạo này cũng chấp nhận một đối tượng của lớp Scalar làm tham số. |
4 | Mat(Size size, int type) Hàm tạo này chấp nhận hai tham số, một đối tượng đại diện cho kích thước của ma trận và một số nguyên đại diện cho kiểu của mảng được sử dụng để lưu trữ dữ liệu. |
5 | Mat(Size size, int type, Scalar s) Bao gồm các tham số của cái trước, hàm tạo này cũng chấp nhận một đối tượng của lớp Scalar làm tham số. |
6 | Mat(long addr) |
7 | Mat(Mat m, Range rowRange) Hàm tạo này chấp nhận một đối tượng của một ma trận khác và một đối tượng của lớp Phạm vi đại diện cho phạm vi của các hàng được sử dụng để tạo một ma trận mới. |
số 8 | Mat(Mat m, Range rowRange, Range colRange) Bao gồm các tham số của cái trước, hàm tạo này chấp nhận thêm một đối tượng của lớp. Phạm vi đại diện cho phạm vi cột. |
9 | Mat(Mat m, Rect roi) Hàm tạo này chấp nhận hai đối tượng, một đối tượng đại diện cho ma trận khác và đối tượng kia đại diện cho Region Of Iquan tâm. |
Note -
Kiểu mảng. Sử dụng CV_8UC1, ..., CV_64FC4 để tạo ma trận 1-4 kênh hoặc CV_8UC (n), ..., CV_64FC (n) để tạo ma trận đa kênh (tối đa kênh CV_CN_MAX).
Loại ma trận được đại diện bởi các trường khác nhau của lớp CvType cái nào thuộc về gói org.opencv.core.
Phương pháp và Mô tả
Sau đây là một số phương thức được cung cấp bởi lớp Mat.
S. không | Phương pháp và Mô tả |
---|---|
1 | Mat col(int x) Phương thức này chấp nhận một tham số nguyên đại diện cho chỉ số của một cột và truy xuất và trả về cột đó. |
2 | Mat row(int y) Phương thức này chấp nhận một tham số nguyên đại diện cho chỉ số của một hàng và truy xuất và trả về hàng đó. |
3 | int cols() Phương thức này trả về số cột trong ma trận. |
4 | int rows() Phương thức này trả về số hàng trong ma trận. |
5 | Mat setTo(Mat value) Phương thức này chấp nhận một đối tượng của Mat gõ và đặt các phần tử mảng thành giá trị được chỉ định. |
6 | Mat setTo(Scalar s) Phương thức này chấp nhận một đối tượng của Scalar gõ và đặt các phần tử mảng thành giá trị được chỉ định. |
Tạo và hiển thị ma trận
Trong phần này, chúng ta sẽ thảo luận về ví dụ OpenCV đầu tiên của chúng ta. Chúng ta sẽ xem cách tạo và hiển thị một ma trận OpenCV đơn giản.
Dưới đây là các bước cần thực hiện để tạo và hiển thị ma trận trong OpenCV.
Bước 1: Tải thư viện gốc OpenCV
Trong khi viết mã Java bằng thư viện OpenCV, bước đầu tiên bạn cần làm là tải thư viện gốc của OpenCV bằng cách sử dụng loadLibrary(). Tải thư viện gốc OpenCV như hình dưới đây.
//Loading the core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
Bước 2: Khởi tạo lớp Mat
Khởi tạo lớp Mat bằng cách sử dụng bất kỳ hàm nào được đề cập trong chương này trước đó.
//Creating a matrix
Mat matrix = new Mat(5, 5, CvType.CV_8UC1, new Scalar(0));
Bước 3: Điền vào ma trận bằng các phương pháp
Bạn có thể truy xuất các hàng / cột cụ thể của ma trận bằng cách chuyển các giá trị chỉ mục cho các phương thức row()/col().
Và, bạn có thể đặt các giá trị cho những giá trị này bằng cách sử dụng bất kỳ biến thể nào của setTo() các phương pháp.
//Retrieving the row with index 0
Mat row0 = matrix.row(0);
//setting values of all elements in the row with index 0
row0.setTo(new Scalar(1));
//Retrieving the row with index 3
Mat col3 = matrix.col(3);
//setting values of all elements in the row with index 3
col3.setTo(new Scalar(3));
Example
Bạn có thể sử dụng mã chương trình sau để tạo và hiển thị một ma trận đơn giản trong Java bằng thư viện OpenCV.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.CvType;
import org.opencv.core.Scalar;
class DisplayingMatrix {
public static void main(String[] args) {
//Loading the core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
//Creating a matrix
Mat matrix = new Mat(5, 5, CvType.CV_8UC1, new Scalar(0));
//Retrieving the row with index 0
Mat row0 = matrix.row(0);
//setting values of all elements in the row with index 0
row0.setTo(new Scalar(1));
//Retrieving the row with index 3
Mat col3 = matrix.col(3);
//setting values of all elements in the row with index 3
col3.setTo(new Scalar(3));
//Printing the matrix
System.out.println("OpenCV Mat data:\n" + matrix.dump());
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
OpenCV Mat data:
[ 1, 1, 1, 3, 1;
0, 0, 0, 3, 0;
0, 0, 0, 3, 0;
0, 0, 0, 3, 0;
0, 0, 0, 3, 0]
Tải hình ảnh bằng API JavaSE
Các BufferedImage lớp của java.awt.image.BufferedImage gói được sử dụng để lưu trữ hình ảnh và ImageIO lớp của gói import javax.imageio cung cấp các phương pháp đọc và ghi Hình ảnh.
Example
Bạn có thể sử dụng mã chương trình sau để tải và lưu ảnh bằng thư viện JavaSE.
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
public class LoadingImage_JSE_library {
public static void main( String[] args ) throws IOException {
//Input File
File input = new File("C:/EXAMPLES/OpenCV/sample.jpg");
//Reading the image
BufferedImage image = ImageIO.read(input);
//Saving the image with a different name
File ouptut = new File("C:/OpenCV/sample.jpg");
ImageIO.write(image, "jpg", ouptut);
System.out.println("image Saved");
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
image Saved
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đã lưu như sau:
Các Imgcodecs lớp của gói org.opencv.imgcodecscung cấp các phương pháp đọc và ghi hình ảnh. Sử dụng OpenCV, bạn có thể đọc một hình ảnh và lưu trữ nó trong ma trận (thực hiện các phép biến đổi trên ma trận nếu cần). Sau đó, bạn có thể ghi ma trận đã xử lý vào một tệp.
Các read() phương pháp của Imgcodecslớp được sử dụng để đọc một hình ảnh bằng OpenCV. Sau đây là cú pháp của phương thức này.
imread(filename)
Nó chấp nhận một đối số (filename), một biến kiểu Chuỗi đại diện cho đường dẫn của tệp sẽ được đọc.
Dưới đây là các bước cần thực hiện để đọc hình ảnh trong Java bằng thư viện OpenCV.
Bước 1: Tải thư viện gốc OpenCV
Tải thư viện gốc OpenCV bằng cách sử dụng load() như hình dưới đây.
//Loading the core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
Bước 2: Khởi tạo lớp Imgcodecs
Khởi tạo Imgcodecs lớp học.
//Instantiating the Imgcodecs class
Imgcodecs imageCodecs = new Imgcodecs();
Bước 3: Đọc hình ảnh
Đọc hình ảnh bằng phương pháp imread(). Phương thức này chấp nhận một đối số chuỗi đại diện cho đường dẫn của hình ảnh và trả về hình ảnh được đọc làMat vật.
//Reading the Image from the file
Mat matrix = imageCodecs.imread(Path of the image);
Thí dụ
Mã chương trình sau đây cho biết cách bạn có thể read an image sử dụng thư viện OpenCV.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
public class ReadingImages {
public static void main(String args[]) {
//Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
//Instantiating the Imagecodecs class
Imgcodecs imageCodecs = new Imgcodecs();
//Reading the Image from the file
String file ="C:/EXAMPLES/OpenCV/sample.jpg";
Mat matrix = imageCodecs.imread(file);
System.out.println("Image Loaded");
}
}
Khi thực hiện chương trình trên, OpenCV tải hình ảnh được chỉ định và hiển thị đầu ra sau:
Image Loaded
Các write() phương pháp của Imgcodecslớp được sử dụng để viết một hình ảnh bằng OpenCV. Để viết một hình ảnh, hãy lặp lại ba bước đầu tiên từ ví dụ trước.
Để viết một hình ảnh, bạn cần gọi imwrite() phương pháp của Imgcodecs lớp học.
Sau đây là cú pháp của phương thức này.
imwrite(filename, mat)
Phương thức này chấp nhận các tham số sau:
filename - A String biến đại diện cho đường dẫn nơi lưu tệp.
mat - A Mat đối tượng đại diện cho hình ảnh được viết.
Thí dụ
Chương trình sau đây là một ví dụ để write an image bằng chương trình Java sử dụng thư viện OpenCV.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
public class WritingImages {
public static void main(String args[]) {
//Loading the OpenCV core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
//Instantiating the imagecodecs class
Imgcodecs imageCodecs = new Imgcodecs();
//Reading the Image from the file and storing it in to a Matrix object
String file ="C:/EXAMPLES/OpenCV/sample.jpg";
Mat matrix = imageCodecs.imread(file);
System.out.println("Image Loaded ..........");
String file2 = "C:/EXAMPLES/OpenCV/sample_resaved.jpg";
//Writing the image
imageCodecs.imwrite(file2, matrix);
System.out.println("Image Saved ............");
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Image Loaded ..........
Image Saved ...........
Nếu bạn mở đường dẫn đã chỉ định, bạn có thể quan sát hình ảnh đã lưu như hình dưới đây -
Trong các chương trước, chúng ta đã thảo luận về cách đọc và lưu một hình ảnh bằng thư viện OpenCV Java. Ngoài ra, chúng tôi cũng có thể hiển thị các hình ảnh đã tải trong một cửa sổ riêng biệt bằng cách sử dụng các thư viện GUI như AWT / Swings và JavaFX.
Chuyển đổi Mat thành Hình ảnh được đệm
Để đọc một hình ảnh, chúng tôi sử dụng phương pháp imread(). Phương thức này trả về hình ảnh đã đọc ở dạngMatrix. Tuy nhiên, để sử dụng hình ảnh này với các thư viện GUI (AWT / Swings và JavaFX), nó phải được chuyển đổi thành một đối tượng của lớpBufferedImage của gói java.awt.image.BufferedImage.
Sau đây là các bước để chuyển đổi một Mat đối tượng của OpenCV để BufferedImage vật.
Bước 1: Mã hóa Mat thành MatOfByte
Trước hết, bạn cần chuyển ma trận thành ma trận byte. Bạn có thể làm điều đó bằng phương phápimencode() của lớp Imgcodecs. Sau đây là cú pháp của phương thức này.
imencode(ext, image, matOfByte);
Phương thức này chấp nhận các tham số sau:
Ext - Một tham số Chuỗi chỉ định định dạng hình ảnh (.jpg, .png, v.v.)
image - Một đối tượng Mat của hình ảnh
matOfByte - Một đối tượng rỗng của lớp MatOfByte
Mã hóa hình ảnh bằng phương pháp này như hình dưới đây.
//Reading the image
Mat image = Imgcodecs.imread(file);
//instantiating an empty MatOfByte class
MatOfByte matOfByte = new MatOfByte();
//Converting the Mat object to MatOfByte
Imgcodecs.imencode(".jpg", image, matOfByte);
Bước 2: Chuyển đối tượng MatOfByte thành mảng byte
Chuyển đổi MatOfByte đối tượng vào một mảng byte bằng phương pháp toArray().
byte[] byteArray = matOfByte.toArray();
Bước 3: Chuẩn bị đối tượng InputStream
Chuẩn bị đối tượng InputStream bằng cách chuyển mảng byte đã tạo ở bước trước tới hàm tạo của ByteArrayInputStream lớp học.
//Preparing the InputStream object
InputStream in = new ByteArrayInputStream(byteArray);
Bước 4: Chuẩn bị đối tượng InputStream
Chuyển đối tượng Dòng đầu vào được tạo ở bước trước đó vào read() phương pháp của ImageIOlớp học. Điều này sẽ trả về một đối tượng BufferedImage.
//Preparing the BufferedImage
BufferedImage bufImage = ImageIO.read(in);
Hiển thị hình ảnh bằng AWT / Swings
Để hiển thị hình ảnh bằng khung AWT / Swings, trước hết, hãy đọc hình ảnh bằng cách sử dụng imread() và chuyển đổi nó thành BufferedImage theo các bước nêu trên.
Sau đó, khởi tạo JFrame và thêm hình ảnh được tạo vào bộ đệm được tạo vào ContentPane của JFrame, như hình dưới đây -
//Instantiate JFrame
JFrame frame = new JFrame();
//Set Content to the JFrame
frame.getContentPane().add(new JLabel(new ImageIcon(bufImage)));
frame.pack();
frame.setVisible(true);
Example
Mã chương trình sau đây cho biết cách bạn có thể read một hình ảnh và display nó thông qua cửa sổ xoay sử dụng thư viện OpenCV.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.imgcodecs.Imgcodecs;
public class DisplayingImagesUsingSwings {
public static void main(String args[]) throws Exception {
//Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
//Reading the Image from the file and storing it in to a Matrix object
String file = "C:/EXAMPLES/OpenCV/sample.jpg";
Mat image = Imgcodecs.imread(file);
//Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", image, matOfByte);
//Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
//Preparing the Buffered Image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
//Instantiate JFrame
JFrame frame = new JFrame();
//Set Content to the JFrame
frame.getContentPane().add(new JLabel(new ImageIcon(bufImage)));
frame.pack();
frame.setVisible(true);
System.out.println("Image Loaded");
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Image Loaded
Ngoài ra, bạn có thể thấy một cửa sổ hiển thị hình ảnh đã tải, như sau:
Hiển thị hình ảnh bằng JavaFX
Để hiển thị một hình ảnh bằng JavaFX, trước hết, hãy đọc một hình ảnh bằng cách sử dụng imread() và chuyển đổi nó thành BufferedImage. Sau đó, chuyển đổi BufferedImage thành WlikeImage, như hình dưới đây.
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
Vượt qua WritableImage phản đối hàm tạo của ImageView lớp học.
ImageView imageView = new ImageView(writableImage);
Example
Đoạn mã chương trình sau đây cho biết cách read một hình ảnh và display nó thông qua cửa sổ JavaFX sử dụng thư viện OpenCV.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import javax.imageio.ImageIO;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.imgcodecs.Imgcodecs;
public class DisplayingImagesJavaFX extends Application {
@Override
public void start(Stage stage) throws IOException {
WritableImage writableImage = loadImage();
//Setting the image view
ImageView imageView = new ImageView(writableImage);
//Setting the position of the image
imageView.setX(50);
imageView.setY(25);
//setting the fit height and width of the image view
imageView.setFitHeight(400);
imageView.setFitWidth(500);
//Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
//Creating a Group object
Group root = new Group(imageView);
//Creating a scene object
Scene scene = new Scene(root, 600, 400);
//Setting title to the Stage
stage.setTitle("Loading an image");
//Adding scene to the stage
stage.setScene(scene);
//Displaying the contents of the stage
stage.show();
}
public WritableImage loadImage() throws IOException {
//Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
//Reading the Image from the file and storing it in to a Matrix object
String file ="C:/EXAMPLES/OpenCV/sample.jpg";
Mat image = Imgcodecs.imread(file);
//Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", image, matOfByte);
//Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
//Displaying the image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
System.out.println("Image Loaded");
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
return writableImage;
}
public static void main(String args[]) {
launch(args);
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Image Loaded
Ngoài ra, bạn có thể thấy một cửa sổ hiển thị hình ảnh đã tải, như sau:
OpenCV hỗ trợ nhiều loại hình ảnh khác nhau như màu, nhị phân, thang độ xám, v.v. Sử dụng imread() phương pháp và các trường xác định trước của Imgcodecs lớp, bạn có thể đọc một hình ảnh đã cho dưới dạng một kiểu khác.
Tham số cờ của phương thức imread () (IMREAD_XXX)
Trong các chương trước, chúng ta đã thấy cú pháp của imread() phương pháp của Imgcodecslớp học. Nó chấp nhận một đối số chuỗi đại diện cho vị trí của hình ảnh sẽ được đọc.
imread(filename)
Các imread() phương thức có cú pháp khác.
imread(filename, int flags)
Cú pháp này chấp nhận hai tham số -
filename - Nó chấp nhận một đối số (filename), một biến kiểu Chuỗi đại diện cho đường dẫn của tệp sẽ được đọc.
flags- Một giá trị số nguyên đại diện cho một giá trị cờ được xác định trước. Đối với mỗi giá trị, điều này đọc hình ảnh đã cho dưới dạng một loại cụ thể (màu thang xám, v.v.)
Sau đây là bảng liệt kê các trường khác nhau được cung cấp trong Imgproc lớp dưới dạng các giá trị cho tham số này.
S. không | Các lĩnh vực và mô tả |
---|---|
1 | IMREAD_COLOR Nếu cờ được đặt thành giá trị này, hình ảnh được tải sẽ được chuyển đổi thành hình ảnh màu BGR (Xanh lục Đỏ) 3 kênh. |
2 | IMREAD_GRAYSCALE Nếu cờ được đặt thành giá trị này, hình ảnh đã tải sẽ được chuyển đổi thành hình ảnh thang độ xám đơn kênh. |
3 | IMREAD_LOAD_GDAL Nếu cờ được đặt thành giá trị này, bạn có thể tải hình ảnh bằng cách sử dụng gdal người lái xe. |
4 | IMREAD_ANYCOLOR Nếu cờ được đặt thành giá trị này, hình ảnh sẽ được đọc ở bất kỳ định dạng màu nào có thể. |
5 | IMREAD_REDUCED_COLOR_2 IMREAD_REDUCED_COLOR_4 IMREAD_REDUCED_COLOR_8 Nếu cờ được thiết lập giá trị này, hình ảnh được đọc như ba kênh BGR, và kích thước của hình ảnh được giảm xuống còn ½, ¼ thứ hoặc ⅛ thứ của kích thước ban đầu của hình ảnh liên quan đến lĩnh vực sử dụng với. |
6 | IMREAD_REDUCED_GRAYSCALE_2 IMREAD_REDUCED_GRAYSCALE_4 IMREAD_REDUCED_GRAYSCALE_8 Nếu cờ được thiết lập giá trị này, hình ảnh được đọc như một hình ảnh màu xám kênh đơn, và kích thước của hình ảnh được giảm xuống còn ½, ¼ thứ hoặc ⅛ thứ của kích thước ban đầu của hình ảnh liên quan đến lĩnh vực này sử dụng . |
7 | IMREAD_UNCHANGED Nếu cờ được đặt thành giá trị này, hình ảnh được tải sẽ được trả về như ban đầu. |
Chương trình sau đây trình bày cách đọc một hình ảnh có màu dưới dạng thang độ xám và hiển thị nó bằng cửa sổ JavaFX. Ở đây, chúng tôi đã đọc hình ảnh bằng cách chuyền cờIMREAD_GRAYSCALE cùng với Chuỗi giữ đường dẫn của một hình ảnh có màu.
import java.awt.image.BufferedImage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
public class ReadingAsGrayscale extends Application {
@Override
public void start(Stage stage) throws Exception {
WritableImage writableImage = loadAndConvert();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// Setting the position of the image
imageView.setX(10);
imageView.setY(10);
// setting the fit height and width of the image view
imageView.setFitHeight(400);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Reading image as grayscale");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage loadAndConvert() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Instantiating the imagecodecs class
Imgcodecs imageCodecs = new Imgcodecs();
String input = "C:/EXAMPLES/OpenCV/sample.jpg";
// Reading the image
Mat src = imageCodecs.imread(input, Imgcodecs.IMREAD_GRAYSCALE);
byte[] data1 = new byte[src.rows() * src.cols() * (int)(src.elemSize())];
src.get(0, 0, data1);
// Creating the buffered image
BufferedImage bufImage = new BufferedImage(src.cols(),src.rows(),
BufferedImage.TYPE_BYTE_GRAY);
// Setting the data elements to the image
bufImage.getRaster().setDataElements(0, 0, src.cols(), src.rows(), data1);
// Creating a WritableImage
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
System.out.println("Image Read");
return writableImage;
}
public static void main(String args[]) throws Exception {
launch(args);
}
}
Hình ảnh đầu vào
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Hình ảnh đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau.
Chương trình sau đây trình bày cách đọc một hình ảnh có màu dưới dạng hình ảnh kiểu BGR và hiển thị nó bằng cửa sổ JavaFX. Ở đây, chúng tôi đã đọc hình ảnh bằng cách chuyền cờIMREAD_COLOR phương pháp imread() cùng với Chuỗi giữ đường dẫn của một hình ảnh có màu.
import java.awt.image.BufferedImage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
public class ReadingAsColored extends Application {
@Override
public void start(Stage stage) throws Exception {
WritableImage writableImage = loadAndConvert();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// Setting the position of the image
imageView.setX(10);
imageView.setY(10);
// setting the fit height and width of the image view
imageView.setFitHeight(400);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Reading as colored image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage loadAndConvert() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
String input = "C:/EXAMPLES/OpenCV/sample.jpg";
Mat dst = new Mat();
// Reading the image
Mat src = Imgcodecs.imread(input, Imgcodecs.IMREAD_COLOR);
byte[] data1 = new byte[src.rows() * src.cols() * (int)(src.elemSize())];
src.get(0, 0, data1);
// Creating the buffered image
BufferedImage bufImage = new BufferedImage(src.cols(),src.rows(),
BufferedImage.TYPE_3BYTE_BGR);
// Setting the data elements to the image
bufImage.getRaster().setDataElements(0, 0, src.cols(), src.rows(), data1);
// Creating a WritableImage
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
System.out.println("Image read");
return writableImage;
}
public static void main(String args[]) throws Exception {
launch(args);
}
}
Hình ảnh đầu vào
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Hình ảnh đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau.
Trong các chương trước, chúng ta đã thảo luận về cách đọc hình ảnh đầu vào dưới dạng các kiểu khác nhau (nhị phân, thang độ xám, BGR, v.v.). Trong chương này, chúng ta sẽ học cách chuyển đổi loại ảnh này sang loại ảnh khác.
Lớp có tên Imgproc của gói org.opencv.imgproc cung cấp các phương pháp để chuyển đổi một hình ảnh từ màu này sang màu khác.
Chuyển đổi hình ảnh màu sang thang độ xám
Một phương pháp có tên cvtColor()được sử dụng để chuyển đổi hình ảnh màu sang thang độ xám. Sau đây là cú pháp của phương thức này.
cvtColor(Mat src, Mat dst, int code)
Phương thức này chấp nhận các tham số sau:
src - Một ma trận biểu diễn nguồn.
dst - Một ma trận đại diện cho điểm đến.
code - Một mã số nguyên đại diện cho kiểu chuyển đổi, ví dụ: RGB sang Thang độ xám.
Bạn có thể chuyển đổi hình ảnh màu sang thang màu xám bằng cách chuyển mã Imgproc.COLOR_RGB2GRAY cùng với ma trận nguồn và đích như một tham số cho cvtColor() phương pháp.
Thí dụ
Chương trình sau đây trình bày cách đọc một hình ảnh màu dưới dạng hình ảnh thang độ xám và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
public class ColorToGrayscale extends Application {
@Override
public void start(Stage stage) throws Exception {
WritableImage writableImage = loadAndConvert();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// Setting the position of the image
imageView.setX(10);
imageView.setY(10);
// setting the fit height and width of the image view
imageView.setFitHeight(400);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Colored to grayscale image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage loadAndConvert() throws Exception {
//Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
String input = "C:/EXAMPLES/OpenCV/sample.jpg";
//Reading the image
Mat src = Imgcodecs.imread(input);
//Creating the empty destination matrix
Mat dst = new Mat();
//Converting the image to gray sacle and saving it in the dst matrix
Imgproc.cvtColor(src, dst, Imgproc.COLOR_RGB2GRAY);
//Extracting data from the transformed image (dst)
byte[] data1 = new byte[dst.rows() * dst.cols() * (int)(dst.elemSize())];
dst.get(0, 0, data1);
//Creating Buffered image using the data
BufferedImage bufImage = new BufferedImage(dst.cols(),dst.rows(),
BufferedImage.TYPE_BYTE_GRAY);
//Setting the data elements to the image
bufImage.getRaster().setDataElements(0, 0, dst.cols(), dst.rows(), data1);
//Creating a WritableImage
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
System.out.println("Converted to Grayscale");
return writableImage;
}
public static void main(String args[]) throws Exception {
launch(args);
}
}
Hình ảnh đầu vào
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Hình ảnh đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau.
Một phương pháp được gọi là threshold()được sử dụng để chuyển đổi ảnh thang độ xám sang ảnh nhị phân. Sau đây là cú pháp của phương thức này.
threshold(Mat src, Mat dst, double thresh, double maxval, int type)
Phương thức này chấp nhận các tham số sau:
mat - A Mat đối tượng đại diện cho hình ảnh đầu vào.
dst - A Mat đối tượng đại diện cho hình ảnh đầu ra.
thresh - Một số nguyên đại diện cho giá trị ngưỡng.
maxval - Một số nguyên đại diện cho giá trị lớn nhất để sử dụng với các loại ngưỡng THRESH_BINARY và THRESH_BINARY_INV.
type - Một mã số nguyên đại diện cho kiểu chuyển đổi, ví dụ: RGB sang Thang độ xám.
Bạn có thể chuyển đổi hình ảnh thang độ xám sang hình ảnh nhị phân bằng cách chuyển mã Imgproc.THRESH_BINARY cùng với các giá trị của các tham số còn lại.
Thí dụ
Chương trình sau đây trình bày cách đọc ảnh màu dưới dạng ảnh nhị phân và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
public class ColorToBinary extends Application {
@Override
public void start(Stage stage) throws Exception {
WritableImage writableImage = loadAndConvert();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// Setting the position of the image
imageView.setX(10);
imageView.setY(10);
// setting the fit height and width of the image view
imageView.setFitHeight(400);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Loading an image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage loadAndConvert() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Instantiating the Imgcodecs class
Imgcodecs imageCodecs = new Imgcodecs();
// File input = new File("C:/EXAMPLES/OpenCV/sample.jpg");
String input = "C:/EXAMPLES/OpenCV/sample.jpg";
// Reading the image
Mat src = imageCodecs.imread(input);
// Creating the destination matrix
Mat dst = new Mat();
// Converting to binary image...
Imgproc.threshold(src, dst, 200, 500, Imgproc.THRESH_BINARY);
// Extracting data from the transformed image (dst)
byte[] data1 = new byte[dst.rows() * dst.cols() * (int)(dst.elemSize())];
dst.get(0, 0, data1);
// Creating Buffered image using the data
BufferedImage bufImage = new BufferedImage(dst.cols(),dst.rows(),
BufferedImage.TYPE_BYTE_GRAY);
// Setting the data elements to the image
bufImage.getRaster().setDataElements(0, 0, dst.cols(), dst.rows(), data1);
// Creating a Writable image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
System.out.println("Converted to binary");
return writableImage;
}
public static void main(String args[]) throws Exception {
launch(args);
}
}
Hình ảnh đầu vào
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Hình ảnh đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau.
Bạn có thể sử dụng phương pháp tương tự được đề cập trong chương trước để chuyển đổi hình ảnh thang độ xám thành hình ảnh nhị phân. Chỉ cần chuyển đường dẫn cho hình ảnh thang độ xám làm đầu vào cho chương trình này.
Thí dụ
Chương trình sau đây trình bày cách đọc ảnh thang độ xám dưới dạng ảnh nhị phân và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
public class GrayScaleToBinary extends Application {
@Override
public void start(Stage stage) throws Exception {
WritableImage writableImage = loadAndConvert();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// Setting the position of the image
imageView.setX(10);
imageView.setY(10);
// Setting the fit height and width of the image view
imageView.setFitHeight(400);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Grayscale to binary image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage loadAndConvert() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Instantiating the imagecodecs class
Imgcodecs imageCodecs = new Imgcodecs();
String input = "E:/OpenCV/chap7/grayscale.jpg";
// Reading the image
Mat src = imageCodecs.imread(input);
// Creating the destination matrix
Mat dst = new Mat();
// Converting to binary image...
Imgproc.threshold(src, dst, 200, 500, Imgproc.THRESH_BINARY);
// Extracting data from the transformed image (dst)
byte[] data1 = new byte[dst.rows() * dst.cols() * (int)(dst.elemSize())];
dst.get(0, 0, data1);
// Creating Buffered image using the data
BufferedImage bufImage = new BufferedImage(dst.cols(),dst.rows(),
BufferedImage.TYPE_BYTE_BINARY);
// Setting the data elements to the image
bufImage.getRaster().setDataElements(0, 0, dst.cols(), dst.rows(), data1);
// Creating a Writable image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
System.out.println("Converted to binary");
return writableImage;
}
public static void main(String args[]) throws Exception {
launch(args);
}
}
Hình ảnh đầu vào
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Hình ảnh đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau.
Bạn có thể vẽ các hình dạng khác nhau như Hình tròn, Hình chữ nhật, Đường thẳng, Hình elip, Đường đa giác, Mặt lồi, Đường đa giác, Đường đa giác trên một hình ảnh bằng các phương pháp tương ứng của org.opencv.imgproc gói hàng.
Bạn có thể vẽ một vòng tròn trên một hình ảnh bằng phương pháp circle() sau đó imgproclớp học. Sau đây là cú pháp của phương thức này:
circle(img, center, radius, color, thickness)
Phương thức này chấp nhận các tham số sau:
mat - A Mat đối tượng đại diện cho hình ảnh mà vòng tròn sẽ được vẽ.
point - A Point đối tượng biểu diễn tâm của hình tròn.
radius - Một biến kiểu integer biểu diễn bán kính của hình tròn.
scalar - A Scalarđối tượng đại diện cho màu sắc của hình tròn. (BGR)
thickness - An integerbiểu diễn độ dày của hình tròn; theo mặc định, giá trị của độ dày là 1.
Thí dụ
Chương trình sau đây trình bày cách vẽ một hình tròn trên một hình ảnh và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import javax.imageio.ImageIO;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.core.Point;
import org.opencv.core.Scalar;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class DrawingCircle extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws Exception {
// Capturing the snapshot from the camera
DrawingCircle obj = new DrawingCircle();
WritableImage writableImage = obj.LoadImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(600);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Drawing Circle on the image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage LoadImage() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap8/input.jpg";
Mat matrix = Imgcodecs.imread(file);
//Drawing a Circle Imgproc.circle ( matrix, //Matrix obj of the image new Point(230, 160), //Center of the circle 100, //Radius new Scalar(0, 0, 255), //Scalar object for color 10 //Thickness of the circle );
// Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", matrix, matOfByte);
// Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
// Displaying the image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
this.matrix = matrix;
// Creating the Writable Image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
return writableImage;
}
public static void main(String args[]) {
launch(args);
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Bạn có thể vẽ một đường thẳng trên hình ảnh bằng phương pháp line() sau đó imgproclớp học. Sau đây là cú pháp của phương thức này.
line(img, pt1, pt2, color, thickness)
Phương thức này chấp nhận các tham số sau:
mat - A Mat đối tượng đại diện cho hình ảnh mà đường sẽ được vẽ.
pt1 and pt2 - Hai Point các đối tượng đại diện cho các điểm mà đường thẳng sẽ được vẽ.
scalar - A Scalarđối tượng đại diện cho màu sắc của hình tròn. (BGR)
thickness- Một số nguyên đại diện cho độ dày của đường; theo mặc định, giá trị của độ dày là 1.
Thí dụ
Chương trình sau đây trình bày cách vẽ một đường thẳng trên một hình ảnh và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import javax.imageio.ImageIO;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.core.Point;
import org.opencv.core.Scalar;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class DrawingLine extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws Exception {
// Capturing the snapshot from the camera
DrawingLine obj = new DrawingLine();
WritableImage writableImage = obj.LoadImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(600);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Drawing a line on the image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage LoadImage() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap8/input.jpg";
Mat matrix = Imgcodecs.imread(file);
// Drawing a line Imgproc.line ( matrix, //Matrix obj of the image new Point(10, 200), //p1 new Point(300, 200), //p2 new Scalar(0, 0, 255), //Scalar object for color 5 //Thickness of the line );
// Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", matrix, matOfByte);
// Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
// Displaying the image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
this.matrix = matrix;
// Creating the Writable Image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
return writableImage;
}
public static void main(String args[]) {
launch(args);
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Bạn có thể vẽ một hình chữ nhật trên một hình ảnh bằng phương pháp rectangle() sau đó imgproclớp học. Sau đây là cú pháp của phương thức này:
rectangle(img, pt1, pt2, color, thickness)
Phương thức này chấp nhận các tham số sau:
mat - A Mat đối tượng đại diện cho hình ảnh mà hình chữ nhật sẽ được vẽ.
pt1 and pt2 - Hai Point các đối tượng đại diện cho các đỉnh của hình chữ nhật sẽ được vẽ.
scalar - A Scalarđối tượng đại diện cho màu sắc của hình chữ nhật. (BGR)
thickness- Một số nguyên thể hiện độ dày của hình chữ nhật; theo mặc định, giá trị của độ dày là 1.
Thí dụ
Ví dụ sau minh họa cách vẽ một hình chữ nhật trên một hình ảnh và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import javax.imageio.ImageIO;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.core.Point;
import org.opencv.core.Scalar;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class DrawingRectangle extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws Exception {
// Capturing the snapshot from the camera
DrawingRectangle obj = new DrawingRectangle();
WritableImage writableImage = obj.LoadImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(600);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Drawing Rectangle on the image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage LoadImage() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap8/input.jpg";
Mat matrix = Imgcodecs.imread(file);
// Drawing a Rectangle Imgproc.rectangle ( matrix, //Matrix obj of the image new Point(130, 50), //p1 new Point(300, 280), //p2 new Scalar(0, 0, 255), //Scalar object for color 5 //Thickness of the line );
// Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", matrix, matOfByte);
// Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
// Displaying the image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
this.matrix = matrix;
// Creating the Writable Image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
return writableImage;
}
public static void main(String args[]) {
launch(args);
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Bạn có thể vẽ một hình elip trên một hình ảnh bằng phương pháp rectangle() sau đó imgproclớp học. Sau đây là cú pháp của phương thức này:
ellipse(img, box, color, thickness)
Phương thức này chấp nhận các tham số sau:
mat - A Mat đối tượng đại diện cho hình ảnh mà Hình chữ nhật sẽ được vẽ.
box - Một đối tượng RotatedRect (Hình elip được vẽ bên trong hình chữ nhật này.)
scalar - A Scalarđối tượng đại diện cho màu sắc của Hình chữ nhật. (BGR)
thickness- Một số nguyên đại diện cho độ dày của Hình chữ nhật; theo mặc định, giá trị của độ dày là 1.
Hàm tạo của RotatedRect lớp chấp nhận một đối tượng của lớp Point, một đối tượng của lớp Size và một biến có kiểu double, như hình dưới đây.
RotatedRect(Point c, Size s, double a)
Thí dụ
Chương trình sau đây trình bày cách vẽ một hình elip trên một hình ảnh và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import javax.imageio.ImageIO;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.core.Point;
import org.opencv.core.RotatedRect;
import org.opencv.core.Scalar;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class DrawingEllipse extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws Exception {
// Capturing the snapshot from the camera
DrawingEllipse obj = new DrawingEllipse();
WritableImage writableImage = obj.LoadImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(600);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Drawing Ellipse on the image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage LoadImage() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap8/input.jpg";
Mat matrix = Imgcodecs.imread(file);
// Drawing an Ellipse Imgproc.ellipse ( matrix, //Matrix obj of the image new RotatedRect ( // RotatedRect(Point c, Size s, double a) new Point(200, 150), new Size(260, 180), 180 ), new Scalar(0, 0, 255), //Scalar object for color 10 //Thickness of the line );
// Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", matrix, matOfByte);
// Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
// Displaying the image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
this.matrix = matrix;
// Creating the Writable Image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
return writableImage;
}
public static void main(String args[]) {
launch(args);
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Bạn có thể vẽ Polylines trên hình ảnh bằng phương pháp polylines() sau đó imgproclớp học. Sau đây là cú pháp của phương thức này.
polylines(img, pts, isClosed, color, thickness)
Phương thức này chấp nhận các tham số sau:
mat - A Mat đối tượng đại diện cho hình ảnh mà Polylines sẽ được vẽ.
pts - A List đối tượng giữ các đối tượng của loại MatOfPoint.
isClosed - Một tham số của kiểu boolean chỉ định thời tiết mà các đường đa tuyến được đóng lại.
scalar - A Scalarđối tượng đại diện cho màu của Polylines. (BGR)
thickness- Một số nguyên đại diện cho độ dày của Polylines; theo mặc định, giá trị của độ dày là 1.
Hàm tạo của MatOfPoint lớp chấp nhận các đối tượng của lớp Point.
MatOfPoint(Point... a)
Thí dụ
Chương trình sau đây trình bày cách vẽ polylines trên một hình ảnh và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import javax.imageio.ImageIO;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.core.MatOfPoint;
import org.opencv.core.Point;
import org.opencv.core.Scalar;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class DrawingPolyLines extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws Exception {
// Capturing the snapshot from the camera
DrawingPolyLines obj = new DrawingPolyLines();
WritableImage writableImage = obj.LoadImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(600);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Drawing Polylines on the image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage LoadImage() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap8/input.jpg";
Mat matrix = Imgcodecs.imread(file);
List<MatOfPoint> list = new ArrayList();
list.add(
new MatOfPoint (
new Point(75, 100), new Point(350, 100),
new Point(75, 150), new Point(350, 150),
new Point(75, 200), new Point(350, 200),
new Point(75, 250), new Point(350, 250)
)
);
// Drawing polylines Imgproc.polylines ( matrix, // Matrix obj of the image list, // java.util.List<MatOfPoint> pts false, // isClosed new Scalar(0, 0, 255), // Scalar object for color 2 // Thickness of the line );
// Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", matrix, matOfByte);
// Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
// Displaying the image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
this.matrix = matrix;
// Creating the Writable Image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
return writableImage;
}
public static void main(String args[]) {
launch(args);
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Bạn có thể vẽ các đường đa giác lồi trên hình ảnh bằng phương pháp fillconvexPoly() sau đó imgproclớp học. Sau đây là cú pháp của phương thức này.
fillConvexPoly(Mat img, MatOfPoint points, Scalar color)
Phương thức này chấp nhận các tham số sau:
mat - A Mat đối tượng đại diện cho hình ảnh mà Polylines lồi sẽ được vẽ trên đó.
points - A MatOfPoint đối tượng đại diện cho các điểm mà giữa các đường đa giác lồi sẽ được vẽ.
scalar - A Scalarđối tượng đại diện cho màu của Polylines lồi. (BGR)
Hàm tạo của MatOfPoint lớp chấp nhận các đối tượng của lớp Point.
MatOfPoint(Point... a)
Thí dụ
Chương trình sau đây trình bày cách vẽ các đường đa giác lồi trên một hình ảnh và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import javax.imageio.ImageIO;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.core.MatOfPoint;
import org.opencv.core.Point;
import org.opencv.core.Scalar;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class FillConvexPoly extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws Exception {
// Capturing the snapshot from the camera
FillConvexPoly obj = new FillConvexPoly();
WritableImage writableImage = obj.LoadImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(600);
imageView.setFitWidth(600);
//Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Drawing convex Polylines (fill) on the image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage LoadImage() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap8/input.jpg";
Mat matrix = Imgcodecs.imread(file);
MatOfPoint matOfPoint = new MatOfPoint (
new Point(75, 100), new Point(350, 100),
new Point(75, 150), new Point(350, 150),
new Point(75, 200), new Point(350, 200),
new Point(75, 250), new Point(350, 250)
);
// Drawing polylines Imgproc.fillConvexPoly ( matrix, // Matrix obj of the image matOfPoint, // java.util.List<MatOfPoint> pts new Scalar(0, 0, 255) // Scalar object for color );
// Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", matrix, matOfByte);
// Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
// Displaying the image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
this.matrix = matrix;
// Creating the Writable Image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
return writableImage;
}
public static void main(String args[]) {
launch(args);
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Bạn có thể vẽ một đường có mũi tên trên hình ảnh bằng phương pháp arrowedLine() sau đó imgproclớp học. Sau đây là cú pháp của phương thức này:
arrowedLine(Mat img, Point pt1, Point pt2, Scalar color)
Phương thức này chấp nhận các tham số sau:
mat - A Mat đối tượng đại diện cho hình ảnh mà đường mũi tên sẽ được vẽ.
pt1 and pt2 - Hai Point các đối tượng đại diện cho các điểm mà đường mũi tên sẽ được vẽ.
scalar - A Scalarđối tượng đại diện cho màu của đường mũi tên. (BGR)
Thí dụ
Chương trình sau đây trình bày cách vẽ đường có mũi tên trên hình ảnh và hiển thị hình ảnh đó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import javax.imageio.ImageIO;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.core.Point;
import org.opencv.core.Scalar;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class DrawingArrowedLine extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws Exception {
// Capturing the snapshot from the camera
DrawingArrowedLine obj = new DrawingArrowedLine();
WritableImage writableImage = obj.LoadImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(600);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Drawing a line on the image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage LoadImage() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="C:/EXAMPLES/OpenCV/Aish.jpg";
Mat matrix = Imgcodecs.imread(file);
//Drawing a line Imgproc.arrowedLine( matrix, // Matrix obj of the image new Point(10, 200), // p1 new Point(590, 200), // p2 new Scalar(0, 100, 255) // Scalar object for color );
// arrowedLine(Mat img, Point pt1, Point pt2, Scalar color)
// Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", matrix, matOfByte);
// Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
// Displaying the image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
this.matrix = matrix;
// Creating the Writable Image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
return writableImage;
}
public static void main(String args[]) {
launch(args);
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Bạn có thể thêm văn bản vào hình ảnh bằng phương pháp arrowedLine() sau đó imgproclớp học. Sau đây là cú pháp của phương thức này.
putText(img, text, org, fontFace, fontScale, Scalar color, int thickness)
Phương thức này chấp nhận các tham số sau:
mat - A Mat đối tượng đại diện cho hình ảnh mà văn bản sẽ được thêm vào.
text - A string biến đại diện cho văn bản sẽ được thêm vào.
org - A Point đối tượng đại diện cho chuỗi văn bản góc dưới cùng bên trái trong hình ảnh.
fontFace - Một biến kiểu số nguyên đại diện cho kiểu phông chữ.
fontScale - Một biến kiểu double đại diện cho hệ số tỷ lệ được nhân với kích thước cơ sở dành riêng cho phông chữ.
scalar - A Scalarđối tượng đại diện cho màu của văn bản sẽ được thêm vào. (BGR)
thickness - Một số nguyên đại diện cho độ dày của đường theo mặc định, giá trị của độ dày là 1.
Thí dụ
Chương trình sau đây trình bày cách thêm văn bản vào hình ảnh và hiển thị nó bằng cửa sổ JavaFX.
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import javax.imageio.ImageIO;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfByte;
import org.opencv.core.Point;
import org.opencv.core.Scalar;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class AddingTextToImage extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws Exception {
// Capturing the snapshot from the camera
AddingTextToImage obj = new AddingTextToImage();
WritableImage writableImage = obj.LoadImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(600);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Adding text to an image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage LoadImage() throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap8/input.jpg";
Mat matrix = Imgcodecs.imread(file);
// Adding Text Imgproc.putText ( matrix, // Matrix obj of the image "Ravivarma's Painting", // Text to be added new Point(10, 50), // point Core.FONT_HERSHEY_SIMPLEX , // front face 1, // front scale new Scalar(0, 0, 0), // Scalar object for color 4 // Thickness );
// Encoding the image
MatOfByte matOfByte = new MatOfByte();
Imgcodecs.imencode(".jpg", matrix, matOfByte);
// Storing the encoded Mat in a byte array
byte[] byteArray = matOfByte.toArray();
// Displaying the image
InputStream in = new ByteArrayInputStream(byteArray);
BufferedImage bufImage = ImageIO.read(in);
this.matrix = matrix;
//Creating the Writable Image
WritableImage writableImage = SwingFXUtils.toFXImage(bufImage, null);
return writableImage;
}
public static void main(String args[]) {
launch(args);
}
}
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Làm mờ (làm mịn) là thao tác xử lý hình ảnh thường được sử dụng để giảm nhiễu hình ảnh. Quá trình loại bỏ nội dung tần số cao, như các cạnh, khỏi hình ảnh và làm cho hình ảnh trở nên mượt mà.
Nói chung, hiện tượng nhòe được thực hiện bằng cách xoay vòng (mỗi phần tử của hình ảnh được thêm vào các vùng lân cận cục bộ của nó, được tính trọng số bởi nhân) hình ảnh thông qua một nhân bộ lọc thông thấp.
Làm mờ (Trung bình)
Trong thao tác này, hình ảnh được đối chiếu với một bộ lọc hộp (chuẩn hóa). Trong quá trình này, phần tử trung tâm của hình ảnh được thay thế bằng giá trị trung bình của tất cả các pixel trong vùng nhân.
Bạn có thể thực hiện thao tác này trên hình ảnh bằng phương pháp blur() sau đó imgproclớp học. Sau đây là cú pháp của phương thức này:
blur(src, dst, ksize, anchor, borderType)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
ksize - A Size đối tượng đại diện cho kích thước của hạt nhân.
anchor - Một biến kiểu số nguyên đại diện cho điểm neo.
borderType - Một biến kiểu số nguyên đại diện cho kiểu đường viền được sử dụng cho đầu ra.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác lấy trung bình (làm mờ) trên ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Point;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class BlurTest {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="C:/EXAMPLES/OpenCV/sample.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Creating the Size and Point objects
Size size = new Size(45, 45);
Point point = new Point(20, 30);
// Applying Blur effect on the Image
Imgproc.blur(src, dst, size, point, Core.BORDER_DEFAULT);
// blur(Mat src, Mat dst, Size ksize, Point anchor, int borderType)
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap9/blur.jpg", dst);
System.out.println("Image processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Trong hoạt động Gaussian Blur, hình ảnh được đối chiếu với bộ lọc Gaussian thay vì bộ lọc hộp. Bộ lọc Gaussian là bộ lọc thông thấp loại bỏ các thành phần tần số cao bị giảm.
Bạn có thể thực hiện thao tác này trên một hình ảnh bằng cách sử dụng Gaussianblur() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này:
GaussianBlur(src, dst, ksize, sigmaX)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
ksize - A Size đối tượng đại diện cho kích thước của hạt nhân.
sigmaX - Một biến kiểu double đại diện cho độ lệch chuẩn của hạt nhân Gaussian theo hướng X.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác làm mờ Gaussian trên ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class GaussianTest {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
// Reading the Image from the file and storing it in to a Matrix object
String file ="C:/EXAMPLES/OpenCV/sample.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying GaussianBlur on the Image
Imgproc.GaussianBlur(src, dst, new Size(45, 45), 0);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap9/Gaussian.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Thao tác làm mờ trung bình tương tự như các phương pháp tính trung bình khác. Ở đây, phần tử trung tâm của hình ảnh được thay thế bằng phần trung bình của tất cả các pixel trong vùng nhân. Thao tác này xử lý các cạnh đồng thời loại bỏ tiếng ồn.
Bạn có thể thực hiện thao tác này trên một hình ảnh bằng cách sử dụng medianBlur() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này:
medianBlur(src, dst, ksize)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
ksize - A Size đối tượng đại diện cho kích thước của hạt nhân.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác làm mờ trung bình trên ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class MedianBlurTest {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="C:/EXAMPLES/OpenCV/sample.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying MedianBlur on the Image
Imgproc.medianBlur(src, dst, 15);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap9/median.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Lọc hình ảnh cho phép bạn áp dụng các hiệu ứng khác nhau cho hình ảnh. Trong chương này và ba chương tiếp theo, chúng ta sẽ thảo luận về các hoạt động lọc khác nhau như Bộ lọc song phương, Bộ lọc hộp, Bộ lọc hộp SQR và Bộ lọc2D.
Bộ lọc song phương
Thao tác Bộ lọc song phương áp dụng hình ảnh song phương cho một bộ lọc. Bạn có thể thực hiện thao tác này trên một hình ảnh bằng cách sử dụngmedianBlur() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này.
bilateralFilter(src, dst, d, sigmaColor, sigmaSpace, borderType)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
d - Một biến kiểu số nguyên đại diện cho đường kính của vùng lân cận pixel.
sigmaColor - Một biến kiểu số nguyên đại diện cho sigma bộ lọc trong không gian màu.
sigmaSpace - Một biến kiểu số nguyên đại diện cho bộ lọc sigma trong không gian tọa độ.
borderType - Một đối tượng số nguyên đại diện cho kiểu đường viền được sử dụng.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác Bộ lọc song phương trên ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class BilateralFilter {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap11/filter_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying Bilateral filter on the Image
Imgproc.bilateralFilter(src, dst, 15, 80, 80, Core.BORDER_DEFAULT);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap11/bilateralfilter.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào filter_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Hoạt động của Bộ lọc Hộp tương tự như hoạt động làm mờ trung bình; nó áp dụng hình ảnh hai bên cho một bộ lọc. Tại đây, bạn có thể chọn hộp có nên được chuẩn hóa hay không.
Bạn có thể thực hiện thao tác này trên một hình ảnh bằng cách sử dụng boxFilter() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này:
boxFilter(src, dst, ddepth, ksize, anchor, normalize, borderType)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
ddepth - Một biến kiểu số nguyên đại diện cho độ sâu của hình ảnh đầu ra.
ksize - A Size đối tượng đại diện cho kích thước của hạt nhân làm mờ.
anchor - Một biến kiểu số nguyên đại diện cho điểm neo.
Normalize - Một biến kiểu boolean chỉ định thời tiết hạt nhân sẽ được chuẩn hóa.
borderType - Một đối tượng số nguyên đại diện cho kiểu đường viền được sử dụng.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác Bộ lọc Hộp trên ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Point;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class BoxFilterTest {
public static void main( String[] args ) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file = "E:/OpenCV/chap11/filter_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Creating the objects for Size and Point
Size size = new Size(45, 45);
Point point = Point(-1, -1);
// Applying Box Filter effect on the Image
Imgproc.boxFilter(src, dst, 50, size, point, true, Core.BORDER_DEFAULT);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap11/boxfilterjpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào filter_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Bạn có thể thực hiện thao tác Bộ lọc SQRBox trên hình ảnh bằng cách sử dụng boxFilter() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này:
sqrBoxFilter(src, dst, ddepth, ksize)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
ddepth - Một biến kiểu số nguyên đại diện cho độ sâu của hình ảnh đầu ra.
ksize - A Size đối tượng đại diện cho kích thước của hạt nhân làm mờ.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác lọc Sqrbox trên một hình ảnh nhất định.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class SqrBoxFilterTest {
public static void main( String[] args ) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap11/filter_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying Box Filter effect on the Image
Imgproc.sqrBoxFilter(src, dst, -1, new Size(1, 1));
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap11/sqrboxfilter.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào filter_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Phép toán Filter2D chuyển đổi một hình ảnh với hạt nhân. Bạn có thể thực hiện thao tác này trên một hình ảnh bằng cách sử dụngFilter2D() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này:
filter2D(src, dst, ddepth, kernel)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
ddepth - Một biến kiểu số nguyên đại diện cho độ sâu của hình ảnh đầu ra.
kernel - A Mat đối tượng đại diện cho nhân tích chập.
Thí dụ
Chương trình sau đây trình bày cách thực hiện hoạt động Filter2D trên một hình ảnh.
import org.opencv.core.Core;
import org.opencv.core.CvType;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class Filter2D {
public static void main( String[] args ) {
//Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
//Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap11/filter_input.jpg";
Mat src = Imgcodecs.imread(file);
//Creating an empty matrix to store the result
Mat dst = new Mat();
// Creating kernel matrix
Mat kernel = Mat.ones(2,2, CvType.CV_32F);
for(int i = 0; i<kernel.rows(); i++) {
for(int j = 0; j<kernel.cols(); j++) {
double[] m = kernel.get(i, j);
for(int k = 1; k<m.length; k++) {
m[k] = m[k]/(2 * 2);
}
kernel.put(i,j, m);
}
}
Imgproc.filter2D(src, dst, -1, kernel);
Imgcodecs.imwrite("E:/OpenCV/chap11/filter2d.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào filter_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Xói mòn và giãn nở là hai loại hoạt động hình thái học. Như tên của nó, các phép toán hình thái là một tập hợp các phép toán xử lý hình ảnh theo hình dạng của chúng.
Dựa trên hình ảnh đầu vào đã cho, một "phần tử cấu trúc" được phát triển. Điều này có thể được thực hiện trong bất kỳ quy trình nào trong hai quy trình. Chúng nhằm mục đích loại bỏ nhiễu và giải quyết các khuyết điểm, để làm cho hình ảnh rõ ràng.
Sự giãn nở
Quy trình này tuân theo phép tích chập với một số hạt nhân có hình dạng cụ thể như hình vuông hoặc hình tròn. Hạt nhân này có một điểm neo, biểu thị trung tâm của nó.
Kernel này được phủ lên hình ảnh để tính giá trị pixel tối đa. Sau khi tính toán, bức tranh được thay thế bằng mỏ neo ở tâm. Với quy trình này, các vùng sáng tăng kích thước và do đó kích thước hình ảnh tăng lên.
Ví dụ: kích thước của một đối tượng trong bóng râm trắng hoặc bóng sáng tăng lên, trong khi kích thước của một đối tượng trong bóng đen hoặc bóng tối giảm.
Bạn có thể thực hiện thao tác giãn nở trên hình ảnh bằng cách sử dụng dilate() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này.
dilate(src, dst, kernel)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
kernel - A Mat đối tượng đại diện cho hạt nhân.
Thí dụ
Bạn có thể chuẩn bị ma trận hạt nhân bằng cách sử dụng getStructuringElement()phương pháp. Phương thức này chấp nhận một số nguyên đại diện chomorph_rect loại và một đối tượng của loại Size.
Imgproc.getStructuringElement(int shape, Size ksize);
Chương trình sau đây trình bày cách thực hiện phép toán giãn nở trên một hình ảnh nhất định.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class DilateTest {
public static void main( String[] args ) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="C:/EXAMPLES/OpenCV/sample.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Preparing the kernel matrix object
Mat kernel = Imgproc.getStructuringElement(Imgproc.MORPH_RECT,
new Size((2*2) + 1, (2*2)+1));
// Applying dilate on the Image
Imgproc.dilate(src, dst, kernel);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap10/Dilation.jpg", dst);
System.out.println("Image Processed");
}
}
Đầu vào
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Xói mòn là một quá trình tương tự như sự giãn nở. Nhưng giá trị pixel được tính ở đây là tối thiểu chứ không phải tối đa khi giãn nở. Hình ảnh được thay thế dưới điểm neo bằng giá trị pixel tối thiểu đó.
Với quy trình này, kích thước vùng tối phát triển và vùng sáng giảm. Ví dụ, kích thước của một đối tượng trong bóng tối hoặc bóng đen tăng lên, trong khi nó giảm ở bóng trắng hoặc bóng sáng.
Thí dụ
Bạn có thể thực hiện thao tác này trên một hình ảnh bằng cách sử dụng erode() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này:
erode(src, dst, kernel)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
kernel - A Mat đối tượng đại diện cho hạt nhân.
Bạn có thể chuẩn bị ma trận hạt nhân bằng cách sử dụng getStructuringElement()phương pháp. Phương thức này chấp nhận một số nguyên đại diện chomorph_rect loại và một đối tượng của loại Size.
Imgproc.getStructuringElement(int shape, Size ksize);
Chương trình sau đây trình bày cách thực hiện thao tác xói mòn trên một hình ảnh nhất định.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class ErodeTest {
public static void main( String[] args ) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="C:/EXAMPLES/OpenCV/sample.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Preparing the kernel matrix object
Mat kernel = Imgproc.getStructuringElement(Imgproc.MORPH_RECT,
new Size((2*2) + 1, (2*2)+1));
// Applying erode on the Image
Imgproc.erode(src, dst, kernel);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap10/Erosion.jpg", dst);
System.out.println("Image processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào sample.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Loaded
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Trong các chương trước, chúng ta đã thảo luận về quá trình erosion và dilation. Ngoài hai điều này, OpenCV có nhiều biến đổi hình thái hơn. CácmorphologyEx() của phương thức của lớp Imgproc được sử dụng để thực hiện các thao tác này trên một hình ảnh nhất định.
Sau đây là cú pháp của phương thức này:
morphologyEx(src, dst, op, kernel)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
dst - đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
op - Một số nguyên đại diện cho kiểu hoạt động Hình thái.
kernel - Một ma trận nhân.
Thí dụ
Chương trình sau đây trình bày cách áp dụng phép toán hình thái "top-hat" trên một hình ảnh sử dụng thư viện OpenCV.
import org.opencv.core.Core;
import org.opencv.core.CvType;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class MorphologyExTest {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap12/morph_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Creating kernel matrix
Mat kernel = Mat.ones(5,5, CvType.CV_32F);
// Applying Blur effect on the Image
Imgproc.morphologyEx(src, dst, Imgproc.MORPH_TOPHAT, kernel);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap12/morph_tophat.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào morph_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Hoạt động khác
Ngoài các hoạt động hình thái TOPHAT, đã chứng minh trong phần trước example, OpenCV phục vụ nhiều loại hình thái khác nhau. Tất cả các loại này được đại diện bởi các trường tĩnh được xác định trước (giá trị cố định) củaImgproc lớp học.
Bạn có thể chọn loại hình thái mình cần bằng cách chuyển giá trị xác định trước tương ứng của chúng vào tham số op sau đó morphologyEx() phương pháp.
// Applying Blur effect on the Image
Imgproc.morphologyEx(src, dst, Imgproc.MORPH_TOPHAT, kernel);
Sau đây là các giá trị đại diện cho kiểu hoạt động hình thái và đầu ra tương ứng của chúng.
Hoạt động và mô tả | Đầu ra |
---|---|
MORPH_BLACKHAT |
|
MORPH_CLOSE |
|
MORPH_CROSS |
|
MORPH_DILATE |
|
MORPH_ELLIPSE |
|
MORPH_ERODE |
|
MORPH_GRADIENT |
|
MORPH_OPEN |
|
MORPH_RECT |
|
MORPH_TOPHAT |
|
Kim tự tháp là một phép toán trên một hình ảnh trong đó,
Hình ảnh đầu vào ban đầu được làm mịn bằng cách sử dụng một bộ lọc làm mịn cụ thể (ví dụ: Gaussian, Laplacian) và sau đó hình ảnh được làm mịn được lấy mẫu con.
Quá trình này được lặp lại nhiều lần.
Trong quá trình vận hành kim tự tháp, độ mịn của hình ảnh được tăng lên và giảm độ phân giải (kích thước).
Kim tự tháp lên
Trong Pyramid Up, hình ảnh ban đầu được lấy mẫu lên và sau đó được làm mờ. Bạn có thể thực hiện thao tác Pyramid Up trên một hình ảnh bằng cách sử dụngpyrUP() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này:
pyrUp(src, dst, dstsize, borderType)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
mat - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
size - Một đối tượng của lớp Size đại diện cho kích thước mà hình ảnh sẽ được tăng hoặc giảm.
borderType - Một biến kiểu số nguyên đại diện cho kiểu đường viền sẽ được sử dụng.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác Pyramid Up trên một hình ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class PyramidUp {
public static void main( String[] args ) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap13/pyramid_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying pyrUp on the Image
Imgproc.pyrUp(src, dst, new Size(src.cols()*2, src.rows()*2), Core.BORDER_DEFAULT);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap13/pyrUp_output.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào pyramid_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Kim tự tháp xuống
Trong Pyramid Down, hình ảnh ban đầu bị mờ và sau đó được lấy mẫu xuống. Bạn có thể thực hiện thao tác Pyramid Down trên một hình ảnh bằng cách sử dụngpyrDown() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này:
pyrDown(src, dst, dstsize, borderType)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
mat - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
size - Một đối tượng của lớp Size đại diện cho kích thước mà hình ảnh sẽ được tăng hoặc giảm.
borderType - Một biến kiểu số nguyên đại diện cho kiểu đường viền sẽ được sử dụng.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác Pyramid Down trên hình ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class PyramidDown {
public static void main( String[] args ) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap13/pyramid_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying pyrDown on the Image
Imgproc.pyrDown(src, dst, new Size(src.cols()/2, src.rows()/2),
Core.BORDER_DEFAULT);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap13/pyrDown_output.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào pyramid_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Lọc dịch chuyển trung bình
Trong hoạt động Kim tự tháp Dịch chuyển Trung bình, bước đầu tiên của việc phân đoạn dịch chuyển trung bình của một hình ảnh được thực hiện.
Bạn có thể thực hiện thao tác Lọc Dịch chuyển Trung bình theo hình kim tự tháp trên một hình ảnh bằng cách sử dụng pyrDown() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này.
pyrMeanShiftFiltering(src, dst, sp, sr)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
mat - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
sp - Một biến kiểu double đại diện cho bán kính cửa sổ không gian.
sr - Một biến kiểu double đại diện cho bán kính cửa sổ màu.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác Lọc Dịch chuyển Trung bình trên một hình ảnh nhất định.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class PyramidMeanShift {
public static void main( String[] args ) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap13/pyramid_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying meanShifting on the Image
Imgproc.pyrMeanShiftFiltering(src, dst, 200, 300);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap13/meanShift_output.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào pyramid_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Thresholding là một phương pháp phân đoạn ảnh, nói chung nó được sử dụng để tạo ảnh nhị phân. Ngưỡng có hai loại cụ thể là ngưỡng đơn giản và ngưỡng thích ứng.
Ngưỡng đơn giản
Trong thao tác tạo ngưỡng đơn giản, các pixel có giá trị lớn hơn giá trị ngưỡng được chỉ định sẽ được gán với giá trị chuẩn.
Bạn có thể thực hiện thao tác ngưỡng đơn giản trên hình ảnh bằng phương pháp threshold() sau đó Imgproc class, Sau đây là cú pháp của phương thức này.
threshold(src, dst, thresh, maxval, type)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
dst - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
thresh - Một biến kiểu kép đại diện cho giá trị ngưỡng.
maxval - Một biến kiểu kép đại diện cho giá trị sẽ được cung cấp nếu giá trị pixel lớn hơn giá trị ngưỡng.
type - Một biến kiểu số nguyên đại diện cho kiểu ngưỡng sẽ được sử dụng.
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác ngưỡng đơn giản trên một hình ảnh trong OpenCV.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class Thresh {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap14/thresh_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
Imgproc.threshold(src, dst, 50, 255, Imgproc.THRESH_BINARY);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap14/thresh_trunc.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào thresh_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Các loại ngưỡng đơn giản khác
Ngoài các THRESH_BINARYhoạt động được trình bày trong ví dụ trước, OpenCV phục vụ nhiều loại hoạt động ngưỡng khác nhau. Tất cả các loại này được đại diện bởi các trường tĩnh được xác định trước (giá trị cố định) củaImgproc lớp học.
Bạn có thể chọn loại hoạt động ngưỡng bạn cần, bằng cách chuyển giá trị được xác định trước tương ứng của nó cho tham số có tên type sau đó threshold() phương pháp.
Imgproc.threshold(src, dst, 50, 255, Imgproc.THRESH_BINARY);
Sau đây là các giá trị đại diện cho các loại hoạt động ngưỡng khác nhau và đầu ra tương ứng của chúng.
Hoạt động và mô tả | Đầu ra |
---|---|
THRESH_BINARY |
|
THRESH_BINARY_INV |
|
THRESH_TRUNC |
|
THRESH_TOZERO |
|
THRESH_TOZERO_INV |
|
Trong simple thresholding, giá trị ngưỡng là toàn cục, tức là nó giống nhau đối với tất cả các pixel trong hình ảnh. Adaptive thresholding là phương pháp mà giá trị ngưỡng được tính cho các vùng nhỏ hơn và do đó, sẽ có các giá trị ngưỡng khác nhau cho các vùng khác nhau.
Trong OpenCV, bạn có thể thực hiện thao tác ngưỡng Thích ứng trên hình ảnh bằng phương pháp adaptiveThreshold() sau đó Imgproclớp học. Sau đây là cú pháp của phương thức này.
adaptiveThreshold(src, dst, maxValue, adaptiveMethod, thresholdType, blockSize, C)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
dst - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
maxValue - Một biến kiểu kép đại diện cho giá trị sẽ được cung cấp nếu giá trị pixel lớn hơn giá trị ngưỡng.
adaptiveMethod- Một biến kiểu số nguyên đại diện cho phương thức thích ứng sẽ được sử dụng. Đây sẽ là một trong hai giá trị sau
ADAPTIVE_THRESH_MEAN_C - giá trị ngưỡng là giá trị trung bình của khu vực lân cận.
ADAPTIVE_THRESH_GAUSSIAN_C - giá trị ngưỡng là tổng trọng số của các giá trị lân cận trong đó trọng số là một cửa sổ Gaussian.
thresholdType - Một biến kiểu số nguyên đại diện cho kiểu ngưỡng sẽ được sử dụng.
blockSize - Một biến kiểu số nguyên đại diện cho kích thước của pixelneighborhood được sử dụng để tính toán giá trị ngưỡng.
C - Một biến kiểu kép đại diện cho hằng số được sử dụng trong cả hai phương pháp (đã trừ giá trị trung bình hoặc giá trị trung bình có trọng số).
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác ngưỡng Thích ứng trên hình ảnh trong OpenCV. Ở đây, chúng tôi đang chọn ngưỡng thích ứng của loạibinary và ADAPTIVE_THRESH_MEAN_C đối với phương pháp ngưỡng.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class AdaptiveThresh {
public static void main(String args[]) throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap14/thresh_input.jpg";
// Reading the image
Mat src = Imgcodecs.imread(file,0);
// Creating an empty matrix to store the result
Mat dst = new Mat();
Imgproc.adaptiveThreshold(src, dst, 125, Imgproc.ADAPTIVE_THRESH_MEAN_C,
Imgproc.THRESH_BINARY, 11, 12);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap14/Adaptivemean_thresh_binary.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào thresh_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Các loại ngưỡng thích ứng khác
Ngoài các ADAPTIVE_THRESH_MEAN_C là phương pháp thích ứng và THRESH_BINARY là loại ngưỡng như đã trình bày trong ví dụ trước, chúng ta có thể chọn nhiều kết hợp hơn của hai giá trị này.
Imgproc.adaptiveThreshold(src, dst, 125, Imgproc.ADAPTIVE_THRESH_MEAN_C, Imgproc.THRESH_BINARY, 11, 12);
Sau đây là các giá trị đại diện cho các tổ hợp giá trị khác nhau cho các tham số adaptiveMethod và thresholdType và kết quả đầu ra tương ứng của chúng.
adaptiveMethod / ngưỡngType | ADAPTIVE_THRESH_MEAN_C | ADAPTIVE_THRESH_GAUSSIAN_C: |
---|---|---|
THRESH_BINARY |
|
|
THRESH_BINARY_INV |
|
|
Chương này hướng dẫn bạn cách con cóc viền vào một hình ảnh.
Phương thức copyMakeBorder ()
Bạn có thể thêm các đường viền khác nhau vào hình ảnh bằng cách sử dụng phương pháp copyMakeBorder() của lớp có tên Core, thuộc về gói org.opencv.core. sau đây là cú pháp của phương thức này.
copyMakeBorder(src, dst, top, bottom, left, right, borderType)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
dst - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
top - Một biến số nguyên kiểu số nguyên đại diện cho độ dài của đường viền ở trên cùng của hình ảnh.
bottom - Một biến số nguyên kiểu số nguyên đại diện cho độ dài của đường viền ở dưới cùng của hình ảnh.
left - Một biến số nguyên, kiểu số nguyên đại diện cho độ dài của đường viền ở bên trái của hình ảnh.
right - Một biến số nguyên kiểu số nguyên đại diện cho độ dài của đường viền ở bên phải của hình ảnh.
borderType - Một biến kiểu số nguyên đại diện cho kiểu đường viền sẽ được sử dụng.
Thí dụ
Chương trình sau đây là một ví dụ minh họa, cách thêm đường viền vào một hình ảnh nhất định.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
public class AddingBorder {
public static void main( String[] args ) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap15/input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
Core.copyMakeBorder(src, dst, 20, 20, 20, 20, Core.BORDER_CONSTANT);
Imgcodecs.imwrite("E:/OpenCV/chap15/border_constant.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào thresh_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Các loại biên giới khác
Ngoài kiểu viền, BORDER_CONSTANTđã trình bày trong ví dụ trước, OpenCV phục vụ nhiều loại đường viền khác nhau. Tất cả các kiểu này được đại diện bởi các trường tĩnh được xác định trước (giá trị cố định) của lớp Core.
Bạn có thể chọn loại hoạt động ngưỡng bạn cần, bằng cách chuyển giá trị được xác định trước tương ứng của nó cho tham số có tên borderType sau đó copyMakeBorder() phương pháp.
Core.copyMakeBorder(src, dst, 20, 20, 20, 20, Core.BORDER_CONSTANT);
Sau đây là các giá trị đại diện cho các loại hoạt động biên giới khác nhau và kết quả đầu ra tương ứng của chúng.
Hoạt động và mô tả | Đầu ra |
---|---|
BORDER_CONSTANT |
|
BORDER_ISOLATED |
|
BORDER_DEFAULT |
|
BORDER_REFLECT |
|
BORDER_REFLECT_101 |
|
BORDER_REFLECT101 |
|
BORDER_REPLICATE |
|
BORDER_WRAP |
|
Sử dụng sobel operation, bạn có thể phát hiện các cạnh của hình ảnh theo cả hướng ngang và dọc. Bạn có thể áp dụng thao tác sobel trên hình ảnh bằng phương phápsobel(). Sau đây là cú pháp của phương thức này:
Sobel(src, dst, ddepth, dx, dy)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
dst - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
ddepth - Một biến số nguyên đại diện cho độ sâu của hình ảnh (-1)
dx- Một biến số nguyên biểu diễn đạo hàm x. (0 hoặc 1)
dy- Một biến số nguyên biểu diễn đạo hàm y. (0 hoặc 1)
Thí dụ
Chương trình sau đây trình bày cách thực hiện thao tác Sobel trên một hình ảnh nhất định.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class SobelTest {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap16/sobel_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying sobel on the Image
Imgproc.Sobel(src, dst, -1, 1, 1);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap16/sobel_output.jpg", dst);
System.out.println("Image processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào sobel_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
biến thể sobel
Khi chuyển các giá trị khác nhau đến tham số cuối cùng (dx và dy) (trong số 0 và 1), bạn sẽ nhận được các đầu ra khác nhau -
// Applying sobel on the Image
Imgproc.Sobel(src, dst, -1, 1, 1);
Bảng sau liệt kê các giá trị khác nhau cho các biến dx và dy của phương pháp Sobel() và kết quả đầu ra tương ứng của chúng.
Dẫn xuất X | Dẫn xuất Y | Đầu ra |
---|---|---|
0 | 1 |
|
1 | 0 |
|
1 | 1 |
|
Scharr cũng được sử dụng để phát hiện các dẫn xuất thứ hai của một hình ảnh theo hướng ngang và dọc. Bạn có thể thực hiện thao tác scharr trên một hình ảnh bằng phương phápscharr(). Sau đây là cú pháp của phương thức này:
Scharr(src, dst, ddepth, dx, dy)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
dst - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
ddepth - Một biến số nguyên đại diện cho độ sâu của hình ảnh (-1)
dx- Một biến số nguyên biểu diễn đạo hàm x. (0 hoặc 1)
dy- Một biến số nguyên biểu diễn đạo hàm y. (0 hoặc 1)
Thí dụ
Chương trình sau đây trình bày cách áp dụng scharr cho một hình ảnh nhất định.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class ScharrTest {
public static void main( String[] args ) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap16/sobel_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying Box Filter effect on the Image
Imgproc.Scharr(src, dst, Imgproc.CV_SCHARR, 0, 1);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap16/scharr_output.jpg", dst);
System.out.println("Image processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào scharr_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện nó, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Thêm các phái sinh scharr
Khi chuyển các giá trị khác nhau đến tham số cuối cùng (dx và dy) (trong số 0 và 1), bạn sẽ nhận được các đầu ra khác nhau -
// Applying scharr on the Image
Imgproc.Scharr(src, dst, -1, 1, 1);
Sau đây là bảng liệt kê các giá trị khác nhau cho các biến dx và dy của phương pháp scharr() và kết quả đầu ra tương ứng của chúng.
Dẫn xuất X | Dẫn xuất Y | Đầu ra |
---|---|---|
0 | 1 |
|
1 | 0 |
|
Toán tử Laplacian cũng là một toán tử đạo hàm được sử dụng để tìm các cạnh trong một hình ảnh. Nó là một mặt nạ phái sinh bậc hai. Trong mặt nạ này, chúng ta có hai phân loại khác, một là Toán tử Laplacian dương và toán tử khác là Toán tử Laplacian âm.
Không giống như các toán tử khác, Laplacian không loại bỏ các cạnh theo bất kỳ hướng cụ thể nào mà nó loại bỏ các cạnh theo phân loại sau.
- Cạnh trong
- Cạnh bên ngoài
Bạn có thể thực hiện Laplacian Transform hoạt động trên một hình ảnh bằng cách sử dụng Laplacian() phương pháp của imgproc , sau đây là cú pháp của phương thức này.
Laplacian(src, dst, ddepth)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
ddepth - Một biến kiểu số nguyên đại diện cho độ sâu của hình ảnh đích.
Thí dụ
Chương trình sau đây trình bày cách thực hiện phép toán biến đổi Laplace trên một hình ảnh đã cho.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class LaplacianTest {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
//Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap18/laplacian_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying GaussianBlur on the Image
Imgproc.Laplacian(src, dst, 10);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap18/laplacian.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào laplacian_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Các distance transformtoán tử thường lấy hình ảnh nhị phân làm đầu vào. Trong thao tác này, cường độ mức xám của các điểm bên trong vùng tiền cảnh được thay đổi để tạo khoảng cách tương ứng của chúng từ giá trị 0 gần nhất (ranh giới).
Bạn có thể áp dụng biến đổi khoảng cách trong OpenCV bằng phương pháp distanceTransform(). Sau đây là cú pháp của phương thức này.
distanceTransform(src, dst, distanceType, maskSize)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
dst - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
distanceType - Một biến kiểu số nguyên đại diện cho kiểu biến đổi khoảng cách được áp dụng.
maskSize - Một biến kiểu số nguyên đại diện cho kích thước mặt nạ sẽ được sử dụng.
Thí dụ
Chương trình sau đây trình bày cách thực hiện phép toán biến đổi khoảng cách trên một hình ảnh cho trước.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class DistanceTransform {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap19/input.jpg";
Mat src = Imgcodecs.imread(file,0);
// Creating an empty matrix to store the results
Mat dst = new Mat();
Mat binary = new Mat();
// Converting the grayscale image to binary image
Imgproc.threshold(src, binary, 100, 255, Imgproc.THRESH_BINARY);
// Applying distance transform
Imgproc.distanceTransform(mat, dst, Imgproc.DIST_C, 3);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap19/distnceTransform.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Các loại hoạt động biến đổi khoảng cách
Ngoài loại hoạt động khoảng cách DIST_Cđã trình bày trong ví dụ trước, OpenCV phục vụ nhiều loại hoạt động biến đổi khoảng cách khác nhau. Tất cả các kiểu này được đại diện bởi các trường tĩnh được xác định trước (giá trị cố định) của lớp Imgproc.
Bạn có thể chọn loại hoạt động biến đổi khoảng cách mà bạn cần, bằng cách chuyển giá trị được xác định trước tương ứng của nó cho tham số có tên distanceType sau đó distanceTransform() phương pháp.
// Applying distance transform
Imgproc.distanceTransform(mat, dst, Imgproc.DIST_C, 3);
Sau đây là các giá trị đại diện cho các loại distanceTransform hoạt động và kết quả đầu ra tương ứng của chúng.
Hoạt động và mô tả | Đầu ra |
---|---|
DIST_C |
|
DIST_L1 |
|
DIST_L2 |
|
DIST_LABEL_PIXEL |
|
DIST_MASK_3 |
|
Trong chương này, chúng ta sẽ học cách sử dụng OpenCV để chụp các khung hình bằng camera hệ thống. CácVideoCapture lớp của org.opencv.videoiogói chứa các lớp và phương thức để quay video bằng máy ảnh. Hãy đi từng bước và tìm hiểu cách chụp khung hình -
Bước 1: Tải thư viện gốc OpenCV
Trong khi viết mã Java bằng thư viện OpenCV, bước đầu tiên bạn cần làm là tải thư viện gốc của OpenCV bằng cách sử dụng loadLibrary(). Tải thư viện gốc OpenCV như hình dưới đây.
// Loading the core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
Bước 2: Khởi tạo lớp quay video
Khởi tạo lớp Mat bằng cách sử dụng bất kỳ hàm nào được đề cập trong hướng dẫn này trước đó.
// Instantiating the VideoCapture class (camera:: 0)
VideoCapture capture = new VideoCapture(0);
Bước 3: Đọc các khung
Bạn có thể đọc các khung hình từ máy ảnh bằng cách sử dụng read() phương pháp của VideoCapturelớp học. Phương thức này chấp nhận một đối tượng của lớpMat để lưu trữ khung đã đọc.
// Reading the next video frame from the camera
Mat matrix = new Mat();
capture.read(matrix);
Thí dụ
Chương trình sau đây trình bày cách chụp một khung hình bằng máy ảnh và hiển thị nó bằng cửa sổ JavaFX. Nó cũng lưu khung hình đã chụp.
import java.awt.image.BufferedImage;
import java.awt.image.DataBufferByte;
import java.awt.image.WritableRaster;
import java.io.FileNotFoundException;
import java.io.IOException;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.videoio.VideoCapture;
public class CameraSnapshotJavaFX extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws FileNotFoundException, IOException {
// Capturing the snapshot from the camera
CameraSnapshotJavaFX obj = new CameraSnapshotJavaFX();
WritableImage writableImage = obj.capureSnapShot();
// Saving the image
obj.saveImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(400);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Capturing an image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage capureSnapShot() {
WritableImage WritableImage = null;
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Instantiating the VideoCapture class (camera:: 0)
VideoCapture capture = new VideoCapture(0);
// Reading the next video frame from the camera
Mat matrix = new Mat();
capture.read(matrix);
// If camera is opened
if( capture.isOpened()) {
// If there is next video frame
if (capture.read(matrix)) {
// Creating BuffredImage from the matrix
BufferedImage image = new BufferedImage(matrix.width(),
matrix.height(), BufferedImage.TYPE_3BYTE_BGR);
WritableRaster raster = image.getRaster();
DataBufferByte dataBuffer = (DataBufferByte) raster.getDataBuffer();
byte[] data = dataBuffer.getData();
matrix.get(0, 0, data);
this.matrix = matrix;
// Creating the Writable Image
WritableImage = SwingFXUtils.toFXImage(image, null);
}
}
return WritableImage;
}
public void saveImage() {
// Saving the Image
String file = "E:/OpenCV/chap22/sanpshot.jpg";
// Instantiating the imgcodecs class
Imgcodecs imageCodecs = new Imgcodecs();
// Saving it again
imageCodecs.imwrite(file, matrix);
}
public static void main(String args[]) {
launch(args);
}
}
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau.
Nếu bạn mở đường dẫn đã chỉ định, bạn có thể quan sát cùng một khung được lưu dưới dạng tệp jpg.
Các VideoCapture lớp của org.opencv.videoiogói chứa các lớp và phương thức để quay video bằng camera hệ thống. Chúng ta hãy đi từng bước và tìm hiểu cách thực hiện.
Bước 1: Tải thư viện gốc OpenCV
Trong khi viết mã Java bằng thư viện OpenCV, bước đầu tiên bạn cần làm là tải thư viện gốc của OpenCV bằng cách sử dụng loadLibrary(). Tải thư viện gốc OpenCV như hình dưới đây.
// Loading the core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
Bước 2: Khởi tạo lớp CascadeClassifier
Các CascadeClassifier lớp của gói org.opencv.objdetectđược sử dụng để tải tệp phân loại. Khởi tạo lớp này bằng cách chuyểnxml tập tin lbpcascade_frontalface.xml như hình bên dưới.
// Instantiating the CascadeClassifier
String xmlFile = "E:/OpenCV/facedetect/lbpcascade_frontalface.xml";
CascadeClassifier classifier = new CascadeClassifier(xmlFile);
Bước 3: Phát hiện khuôn mặt
Bạn có thể phát hiện các khuôn mặt trong ảnh bằng phương pháp detectMultiScale() của lớp có tên CascadeClassifier. Phương thức này chấp nhận một đối tượng của lớpMat giữ hình ảnh đầu vào và một đối tượng của lớp MatOfRect để lưu trữ các khuôn mặt được phát hiện.
// Detecting the face in the snap
MatOfRect faceDetections = new MatOfRect();
classifier.detectMultiScale(src, faceDetections);
Thí dụ
Chương trình sau đây trình bày cách phát hiện khuôn mặt trong ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
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.objdetect.CascadeClassifier;
public class FaceDetectionImage {
public static void main (String[] args) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap23/facedetection_input.jpg";
Mat src = Imgcodecs.imread(file);
// Instantiating the CascadeClassifier
String xmlFile = "E:/OpenCV/facedetect/lbpcascade_frontalface.xml";
CascadeClassifier classifier = new CascadeClassifier(xmlFile);
// Detecting the face in the snap
MatOfRect faceDetections = new MatOfRect();
classifier.detectMultiScale(src, faceDetections);
System.out.println(String.format("Detected %s faces",
faceDetections.toArray().length));
// Drawing boxes for (Rect rect : faceDetections.toArray()) { Imgproc.rectangle( src, // where to draw the box new Point(rect.x, rect.y), // bottom left new Point(rect.x + rect.width, rect.y + rect.height), // top right new Scalar(0, 0, 255), 3 // RGB colour );
}
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap23/facedetect_output1.jpg", src);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào facedetection_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Detected 3 faces
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Chương trình sau đây trình bày cách phát hiện khuôn mặt bằng camera hệ thống và hiển thị nó bằng cửa sổ JavaFX.
Thí dụ
import java.awt.image.BufferedImage;
import java.awt.image.DataBufferByte;
import java.awt.image.WritableRaster;
import java.io.FileNotFoundException;
import java.io.IOException;
import javafx.application.Application;
import javafx.embed.swing.SwingFXUtils;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.ImageView;
import javafx.scene.image.WritableImage;
import javafx.stage.Stage;
import org.opencv.core.Core;
import org.opencv.core.Mat;
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.objdetect.CascadeClassifier;
import org.opencv.videoio.VideoCapture;
public class faceDetectionJavaFXX extends Application {
Mat matrix = null;
@Override
public void start(Stage stage) throws FileNotFoundException, IOException {
// Capturing the snapshot from the camera
faceDetectionJavaFXX obj = new faceDetectionJavaFXX();
WritableImage writableImage = obj.capureFrame();
// Saving the image
obj.saveImage();
// Setting the image view
ImageView imageView = new ImageView(writableImage);
// setting the fit height and width of the image view
imageView.setFitHeight(400);
imageView.setFitWidth(600);
// Setting the preserve ratio of the image view
imageView.setPreserveRatio(true);
// Creating a Group object
Group root = new Group(imageView);
// Creating a scene object
Scene scene = new Scene(root, 600, 400);
// Setting title to the Stage
stage.setTitle("Capturing an image");
// Adding scene to the stage
stage.setScene(scene);
// Displaying the contents of the stage
stage.show();
}
public WritableImage capureFrame() {
WritableImage writableImage = null;
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Instantiating the VideoCapture class (camera:: 0)
VideoCapture capture = new VideoCapture(0);
// Reading the next video frame from the camera
Mat matrix = new Mat();
capture.read(matrix);
// If camera is opened
if(!capture.isOpened()) {
System.out.println("camera not detected");
} else
System.out.println("Camera detected ");
// If there is next video frame
if (capture.read(matrix)) {
/////// Detecting the face in the snap /////
String file = "E:/OpenCV/facedetect/lbpcascade_frontalface.xml";
CascadeClassifier classifier = new CascadeClassifier(file);
MatOfRect faceDetections = new MatOfRect();
classifier.detectMultiScale(matrix, faceDetections);
System.out.println(String.format("Detected %s faces",
faceDetections.toArray().length));
// Drawing boxes for (Rect rect : faceDetections.toArray()) { Imgproc.rectangle( matrix, //where to draw the box new Point(rect.x, rect.y), //bottom left new Point(rect.x + rect.width, rect.y + rect.height), //top right new Scalar(0, 0, 255) //RGB colour );
}
// Creating BuffredImage from the matrix
BufferedImage image = new BufferedImage(matrix.width(), matrix.height(),
BufferedImage.TYPE_3BYTE_BGR);
WritableRaster raster = image.getRaster();
DataBufferByte dataBuffer = (DataBufferByte) raster.getDataBuffer();
byte[] data = dataBuffer.getData();
matrix.get(0, 0, data);
this.matrix = matrix;
// Creating the Writable Image
writableImage = SwingFXUtils.toFXImage(image, null);
}
return writableImage;
}
public void saveImage() {
// Saving the Image
String file = "E:/OpenCV/chap23/facedetected.jpg";
// Instantiating the imagecodecs class
Imgcodecs imageCodecs = new Imgcodecs();
// Saving it again
imageCodecs.imwrite(file, matrix);
}
public static void main(String args[]) {
launch(args);
}
}
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau.
Nếu bạn mở đường dẫn đã chỉ định, bạn có thể thấy cùng một ảnh chụp nhanh được lưu dưới dạng jpg hình ảnh.
Bạn có thể thực hiện affine translation trên một hình ảnh bằng cách sử dụng warpAffine()phương thức của lớp imgproc. Sau đây là cú pháp của phương thức này:
Imgproc.warpAffine(src, dst, tranformMatrix, size);
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
tranformMatrix - A Mat đối tượng biểu diễn ma trận biến đổi.
size - Một biến kiểu số nguyên đại diện cho kích thước của hình ảnh đầu ra.
Thí dụ
Chương trình sau đây trình bày cách áp dụng phép toán affine trên một hình ảnh đã cho.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.MatOfPoint2f;
import org.opencv.core.Point;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class AffineTranslation {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap24/transform_input.jpg";
Mat src = Imgcodecs.imread(file);
//Creating an empty matrix to store the result
Mat dst = new Mat();
Point p1 = new Point( 0,0 );
Point p2 = new Point( src.cols() - 1, 0 );
Point p3 = new Point( 0, src.rows() - 1 );
Point p4 = new Point( src.cols()*0.0, src.rows()*0.33 );
Point p5 = new Point( src.cols()*0.85, src.rows()*0.25 );
Point p6 = new Point( src.cols()*0.15, src.rows()*0.7 );
MatOfPoint2f ma1 = new MatOfPoint2f(p1,p2,p3);
MatOfPoint2f ma2 = new MatOfPoint2f(p4,p5,p6);
// Creating the transformation matrix
Mat tranformMatrix = Imgproc.getAffineTransform(ma1,ma2);
// Creating object of the class Size
Size size = new Size(src.cols(), src.cols());
// Applying Wrap Affine
Imgproc.warpAffine(src, dst, tranformMatrix, size);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap24/Affinetranslate.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào transform_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện nó, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Bạn có thể perform rotation hoạt động trên một hình ảnh bằng cách sử dụng warpAffine() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này:
Imgproc.warpAffine(src, dst, rotationMatrix, size);
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
rotationMatrix - A Mat đối tượng biểu diễn ma trận xoay.
size - Một biến kiểu số nguyên đại diện cho kích thước của hình ảnh đầu ra.
Thí dụ
Chương trình sau đây trình bày cách xoay một hình ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Point;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class Rotation {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap24/transform_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Creating a Point object
Point point = new Point(300, 200)
// Creating the transformation matrix M
Mat rotationMatrix = Imgproc.getRotationMatrix2D(point, 30, 1);
// Creating the object of the class Size
Size size = new Size(src.cols(), src.cols());
// Rotating the given image
Imgproc.warpAffine(src, dst, rotationMatrix, size);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap24/rotate_output.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào transform_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Bạn có thể thực hiện scaling trên một hình ảnh bằng cách sử dụng resize() phương pháp của imgproclớp học. Sau đây là cú pháp của phương thức này.
resize(Mat src, Mat dst, Size dsize, double fx, double fy, int interpolation)
Phương thức này chấp nhận các tham số sau:
src - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
dst - A Mat đối tượng đại diện cho đích (hình ảnh đầu ra) cho hoạt động này.
dsize - A Size đối tượng đại diện cho kích thước của hình ảnh đầu ra.
fx - Một biến kiểu double đại diện cho hệ số tỷ lệ dọc theo trục hoành.
fy - Một biến kiểu double đại diện cho hệ số tỷ lệ dọc theo trục tung.
Interpolation - Một biến số nguyên đại diện cho phương pháp nội suy.
Thí dụ
Chương trình sau đây trình bày cách đăng ký scale transformation vào một hình ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class Scaling {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap24/transform_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Creating the Size object
Size size = new Size(src.rows()*2, src.rows()*2);
// Scaling the Image
Imgproc.resize(src, dst, size, 0, 0, Imgproc.INTER_AREA);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap24/scale_output.jpg", dst);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào transform_input.jpg được chỉ định trong chương trình trên (kích thước - Chiều rộng: 300px và chiều cao: 300px).
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau (kích thước - Chiều rộng: 600px và chiều cao: 600px) -
Trong OpenCV, bạn có thể áp dụng các bản đồ màu khác nhau cho hình ảnh bằng phương pháp applyColorMap() của lớp Imgproc. Sau đây là cú pháp của phương thức này:
applyColorMap(Mat src, Mat dst, int colormap)
Nó chấp nhận ba tham số -
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
dst - Một đối tượng của lớp Mat đại diện cho hình ảnh đích (đầu ra).
colormap - Một biến kiểu số nguyên đại diện cho kiểu bản đồ màu sẽ được áp dụng.
Thí dụ
Chương trình sau đây trình bày cách đăng ký color map vào một hình ảnh.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class ColorMapTest {
public static void main(String args[]) {
// Loading the OpenCV core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap25/color_input.jpg";
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat dst = new Mat();
// Applying color map to an image
Imgproc.applyColorMap(src, dst, Imgproc.COLORMAP_HOT);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap25/colormap_hot.jpg", dst);
System.out.println("Image processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào color_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Hoạt động khác
Ngoài COLORMAP_HOTđược minh họa trong ví dụ trước, OpenCV phục vụ nhiều loại bản đồ màu khác nhau. Tất cả các kiểu này được đại diện bởi các trường tĩnh được xác định trước (giá trị cố định) của lớp Imgproc.
Bạn có thể chọn loại bản đồ màu mà bạn cần, bằng cách chuyển giá trị được xác định trước tương ứng của nó cho tham số có tên colormap sau đó applyColorMap() phương pháp.
Imgproc.applyColorMap(src, dst, Imgproc.COLORMAP_HOT);
Sau đây là các giá trị đại diện cho các loại bản đồ màu khác nhau và kết quả đầu ra tương ứng của chúng.
Hoạt động và mô tả | Đầu ra |
---|---|
COLORMAP_AUTUMN |
|
COLORMAP_BONE |
|
COLORMAP_COOL |
|
COLORMAP_HOT |
|
COLORMAP_HSV |
|
COLORMAP_JET |
|
COLORMAP_OCEAN |
|
COLORMAP_PARULA |
|
COLORMAP_PINK |
|
COLORMAP_RAINBOW |
|
COLORMAP_SPRING |
|
COLORMAP_SUMMER |
|
COLORMAP_WINTER |
|
Canny Edge Detection được sử dụng để phát hiện các cạnh trong hình ảnh. Nó chấp nhận một hình ảnh tỷ lệ xám làm đầu vào và nó sử dụng một thuật toán nhiều tầng.
Bạn có thể thực hiện thao tác này trên một hình ảnh bằng cách sử dụng Canny() phương pháp của imgproc , sau đây là cú pháp của phương thức này.
Canny(image, edges, threshold1, threshold2)
Phương thức này chấp nhận các tham số sau:
image - A Mat đối tượng đại diện cho nguồn (hình ảnh đầu vào) cho hoạt động này.
edges - A Mat đối tượng đại diện cho đích (các cạnh) cho thao tác này.
threshold1 - Một biến kiểu double đại diện cho ngưỡng đầu tiên cho quy trình trễ.
threshold2 - Một biến kiểu double đại diện cho ngưỡng thứ hai cho thủ tục trễ.
Thí dụ
Chương trình sau đây là một ví dụ minh họa, cách thực hiện thao tác Phát hiện cạnh Canny trên một hình ảnh nhất định.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class CannyEdgeDetection {
public static void main(String args[]) throws Exception {
// Loading the OpenCV core library
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
// Reading the Image from the file and storing it in to a Matrix object
String file = "E:/OpenCV/chap17/canny_input.jpg";
// Reading the image
Mat src = Imgcodecs.imread(file);
// Creating an empty matrix to store the result
Mat gray = new Mat();
// Converting the image from color to Gray
Imgproc.cvtColor(src, gray, Imgproc.COLOR_BGR2GRAY);
Mat edges = new Mat();
// Detecting the edges
Imgproc.Canny(gray, edges, 60, 60*3);
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap17/canny_output.jpg", edges);
System.out.println("Image Loaded");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào canny_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình trên, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Bạn có thể phát hiện hình dạng của một hình ảnh nhất định bằng cách áp dụng Hough Transform technique sử dụng phương pháp HoughLines() sau đó Imgproclớp học. Sau đây là cú pháp của phương thức này.
HoughLines(image, lines, rho, theta, threshold)
Phương thức này chấp nhận các tham số sau:
image - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
lines - Một đối tượng của lớp Mat lưu vectơ lưu các tham số (r, Φ) của các dòng.
rho - Một biến kiểu double đại diện cho độ phân giải của tham số r tính bằng pixel.
theta - Một biến kiểu double đại diện cho độ phân giải của tham số Φ tính bằng radian.
threshold - Một biến kiểu số nguyên đại diện cho số giao điểm tối thiểu để "phát hiện" một đường.
Thí dụ
Chương trình sau đây trình bày cách phát hiện các đường Hough trong một hình ảnh nhất định.
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Point;
import org.opencv.core.Scalar;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class HoughlinesTest {
public static void main(String args[]) throws Exception {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file = "E:/OpenCV/chap21/hough_input.jpg";
// Reading the image
Mat src = Imgcodecs.imread(file,0);
// Detecting edges of it
Mat canny = new Mat();
Imgproc.Canny(src, canny, 50, 200, 3, false);
// Changing the color of the canny
Mat cannyColor = new Mat();
Imgproc.cvtColor(canny, cannyColor, Imgproc.COLOR_GRAY2BGR);
// Detecting the hough lines from (canny)
Mat lines = new Mat();
Imgproc.HoughLines(canny, lines, 1, Math.PI/180, 100);
System.out.println(lines.rows());
System.out.println(lines.cols());
// Drawing lines on the image
double[] data;
double rho, theta;
Point pt1 = new Point();
Point pt2 = new Point();
double a, b;
double x0, y0;
for (int i = 0; i < lines.cols(); i++) {
data = lines.get(0, i);
rho = data[0];
theta = data[1];
a = Math.cos(theta);
b = Math.sin(theta);
x0 = a*rho;
y0 = b*rho;
pt1.x = Math.round(x0 + 1000*(-b));
pt1.y = Math.round(y0 + 1000*(a));
pt2.x = Math.round(x0 - 1000*(-b));
pt2.y = Math.round(y0 - 1000 *(a));
Imgproc.line(cannyColor, pt1, pt2, new Scalar(0, 0, 255), 6);
}
// Writing the image
Imgcodecs.imwrite("E:/OpenCV/chap21/hough_output.jpg", cannyColor);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào hough_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
143
1
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau:
Các histogramcủa một hình ảnh cho biết tần số của các giá trị cường độ pixel. Trong biểu đồ hình ảnh, trục X hiển thị các cường độ màu xám và trục Y hiển thị tần suất của các cường độ này.
Histogram equalizationcải thiện độ tương phản của hình ảnh, để mở rộng phạm vi cường độ. Bạn có thể cân bằng biểu đồ của một hình ảnh nhất định bằng phương phápequalizeHist() sau đó Imgproclớp học. Sau đây là cú pháp của phương thức này.
equalizeHist(src, dst)
Phương thức này chấp nhận các tham số sau:
src - Một đối tượng của lớp Mat đại diện cho hình ảnh nguồn (đầu vào).
dst - Một đối tượng của lớp Matđại diện cho đầu ra. (Hình ảnh thu được sau khi cân bằng biểu đồ)
Thí dụ
Chương trình sau đây trình bày cách cân bằng biểu đồ của một hình ảnh nhất định.
import java.util.ArrayList;
import java.util.List;
import org.opencv.core.Core;
import org.opencv.core.Mat;
import org.opencv.core.Size;
import org.opencv.imgcodecs.Imgcodecs;
import org.opencv.imgproc.Imgproc;
public class HistoTest {
public static void main (String[] args) {
// Loading the OpenCV core library
System.loadLibrary( Core.NATIVE_LIBRARY_NAME );
// Reading the Image from the file and storing it in to a Matrix object
String file ="E:/OpenCV/chap20/histo_input.jpg";
// Load the image
Mat img = Imgcodecs.imread(file);
// Creating an empty matrix
Mat equ = new Mat();
img.copyTo(equ);
// Applying blur
Imgproc.blur(equ, equ, new Size(3, 3));
// Applying color
Imgproc.cvtColor(equ, equ, Imgproc.COLOR_BGR2YCrCb);
List<Mat> channels = new ArrayList<Mat>();
// Splitting the channels
Core.split(equ, channels);
// Equalizing the histogram of the image
Imgproc.equalizeHist(channels.get(0), channels.get(0));
Core.merge(channels, equ);
Imgproc.cvtColor(equ, equ, Imgproc.COLOR_YCrCb2BGR);
Mat gray = new Mat();
Imgproc.cvtColor(equ, gray, Imgproc.COLOR_BGR2GRAY);
Mat grayOrig = new Mat();
Imgproc.cvtColor(img, grayOrig, Imgproc.COLOR_BGR2GRAY);
Imgcodecs.imwrite("E:/OpenCV/chap20/histo_output.jpg", equ);
System.out.println("Image Processed");
}
}
Giả sử rằng sau đây là hình ảnh đầu vào histo_input.jpg được chỉ định trong chương trình trên.
Đầu ra
Khi thực hiện chương trình, bạn sẽ nhận được kết quả sau:
Image Processed
Nếu bạn mở đường dẫn được chỉ định, bạn có thể quan sát hình ảnh đầu ra như sau: