因为在介绍这部分系列的内容时,默认是对Android开发有一点基础的,所以这样的话,Bitmap可能就相对很熟悉了,相较陌生的是Mat,那我们就首先来看看Mat是什么。
1,Mat
1.1 Mat基本介绍
Mat是OpenCV中用于存储图像信息的类,它在OpenCV中作为一个很重要的信息载体,下面看一下文档中的介绍的关于其方法的部分:
构造方法:
Mat() |
Mat(int rows, int cols, int type) |
Mat(int rows, int cols, int type, java.nio.ByteBuffer data) |
Mat(int rows, int cols, int type, Scalar s) |
Mat(long addr) |
Mat(Mat m, Range rowRange) |
Mat(Mat m, Range rowRange, Range colRange) |
Mat(Mat m, Rect roi) |
Mat(Size size, int type) |
Mat(Size size, int type, Scalar s) |
成员方法:
Mat |
adjustROI(int dtop, int dbottom, int dleft, int dright) |
void |
assignTo(Mat m) |
void |
assignTo(Mat m, int type) |
int |
channels() |
int |
checkVector(int elemChannels) |
int |
checkVector(int elemChannels, int depth) |
int |
checkVector(int elemChannels, int depth, boolean requireContinuous) |
Mat |
clone() |
Mat |
col(int x) |
Mat |
colRange(int startcol, int endcol) |
Mat |
colRange(Range r) |
int |
cols() |
void |
convertTo(Mat m, int rtype) |
void |
convertTo(Mat m, int rtype, double alpha) |
void |
convertTo(Mat m, int rtype, double alpha, double beta) |
void |
copyTo(Mat m) |
void |
copyTo(Mat m, Mat mask) |
void |
create(int rows, int cols, int type) |
void |
create(Size size, int type) |
Mat |
cross(Mat m) |
long |
dataAddr() |
int |
depth() |
Mat |
diag() |
Mat |
diag(int d) |
static Mat |
diag(Mat d) |
int |
dims() |
double |
dot(Mat m) |
java.lang.String |
dump() |
long |
elemSize() |
long |
elemSize1() |
boolean |
empty() |
static Mat |
eye(int rows, int cols, int type) |
static Mat |
eye(Size size, int type) |
double[] |
get(int row, int col) |
int |
get(int row, int col, byte[] data) |
int |
get(int row, int col, double[] data) |
int |
get(int row, int col, float[] data) |
int |
get(int row, int col, int[] data) |
int |
get(int row, int col, short[] data) |
long |
getNativeObjAddr() |
int |
height() |
Mat |
inv() |
Mat |
inv(int method) |
boolean |
isContinuous() |
boolean |
isSubmatrix() |
void |
locateROI(Size wholeSize, Point ofs) |
Mat |
mul(Mat m) |
Mat |
mul(Mat m, double scale) |
static Mat |
ones(int rows, int cols, int type) |
static Mat |
ones(Size size, int type) |
void |
push_back(Mat m) |
int |
put(int row, int col, byte[] data) |
int |
put(int row, int col, byte[] data, int offset, int length) |
int |
put(int row, int col, double... data) |
int |
put(int row, int col, float[] data) |
int |
put(int row, int col, int[] data) |
int |
put(int row, int col, short[] data) |
void |
release() |
Mat |
reshape(int cn) |
Mat |
reshape(int cn, int rows) |
Mat |
reshape(int cn, int[] newshape) |
Mat |
row(int y) |
Mat |
rowRange(int startrow, int endrow) |
Mat |
rowRange(Range r) |
int |
rows() |
Mat |
setTo(Mat value) |
Mat |
setTo(Mat value, Mat mask) |
Mat |
setTo(Scalar s) |
Mat |
setTo(Scalar value, Mat mask) |
Size |
size() |
int |
size(int i) |
long |
step1() |
long |
step1(int i) |
Mat |
submat(int rowStart, int rowEnd, int colStart, int colEnd) |
Mat |
submat(Range rowRange, Range colRange) |
Mat |
submat(Rect roi) |
Mat |
t() |
java.lang.String |
toString() |
long |
total() |
int |
type() |
int |
width() |
static Mat |
zeros(int rows, int cols, int type) |
static Mat |
zeros(Size size, int type) |
这里也只是列举一下这个类的方法而已,看着非常之多,但是不难看出其实主要就是几类,一类是创建Mat或者修改已有Mat到指定属性值Mat对象的方法,一类是以获取Mat对象属性值的方法;其实就这两类,比我们常常用于存储信息的Bean对象多了一些第一类的方法而已,至少概念上可以这么理解。
1.2 Mat创建方式
我对于上面关于Mat的API没有过多介绍,因为本身没有什么难度,下面就结合创建Mat对象简单说明一下,关于创建一个Mat对象有两大类,一个是从无到有,一个是从有到有,从有到有又分为两类,一个是复制,一个修改已有Mat对象的属性,可以简单用下图表示一下:
package com.hfut.operationopencvmain.Mat_Test;
import org.opencv.core.CvType;
import org.opencv.core.Mat;
import org.opencv.core.Scalar;
import org.opencv.core.Size;
/**
* author:why
* created on: 2018/11/27 19:30
* description:
*/
public class MatUtils {
/**
* create a Mat Object by it's create() method;the parameters can be different ,both
* by Size and cows number and rows number
*
* @return
*/
public static Mat method1() {
Mat mat = new Mat();
mat.create(new Size(10, 10), CvType.CV_16UC3);
//mat.create(10,10,CvType.CV_16UC3);
return mat;
}
/**
* create a Mat object by it's static methods like eye(),ones() and zeros()
* it's just like the usage of Matlab
*
* @return
*/
public static Mat method2() {
Mat mat = new Mat();
mat = Mat.eye(new Size(10, 10), CvType.CV_16UC3);
// mat=Mat.ones(new Size(10,10),CvType.CV_16UC3);
// mat=Mat.zeros(new Size(10,10),CvType.CV_16UC3);
return mat;
}
/**
* create a Mat object by it's setTo() method ,this is similar to the first method
*
* @return
*/
public static Mat method3() {
Mat mat = new Mat(new Size(10, 10), CvType.CV_16UC3);
mat = mat.setTo(new Scalar(0, 0, 0));
return mat;
}
/**
* create a Mat object by it's clone() and copyTo() method,this is similar to the Object's clone()
* actually,if you want a self define Object can be clone,you must implement the Cloneable interface
* @return
*/
public static Mat method4() {
Mat mat = new Mat(new Size(10, 10), CvType.CV_16UC3);
Mat mat1 = mat.clone();
//Mat mat2=new Mat();
// mat.copyTo(mat2);
return mat1;
}
}
1.3 几个概念
1.3.1 图像深度和图像通道数
这里借用《OpenCV Android开发实战》书中的表格释义一下:
图像深度 | Java中对应的数据类型 |
CV_8U=0 | 8位byte |
CV_8S=1 | 8位byte |
CV_16U=2 | 16位char |
CV_16S=3 | 16位char |
CV_32S=4 | 32位整形 -int |
CV_32F=5 | 32位-float |
CV_64F=6 | 64位-double |
其中U表示无符号,S表示符号整形,F表示浮点型;还有就是一个图像通道的概念,在Android当中,我们在使用Bitmap时,Bitmap.Config API中有几个类型常量:
ALPHA_8 |
ARGB_4444 |
ARGB_8888 |
RGB_565 |
其中RGB_565就表示RGB三通道16位的含义,其他类似,所以在OpenCV中把图片加载成Mat对象时也有通道的概念,也是对应的1,3,4通道。这样通道和图像深度组合在一起就构成了Mat对象的加载类型,这个主要可在CvType中能查看,下面就是CvType中所有的类型了:
static int |
CV_16S |
static int |
CV_16SC1 |
static int |
CV_16SC2 |
static int |
CV_16SC3 |
static int |
CV_16SC4 |
static int |
CV_16U |
static int |
CV_16UC1 |
static int |
CV_16UC2 |
static int |
CV_16UC3 |
static int |
CV_16UC4 |
static int |
CV_32F |
static int |
CV_32FC1 |
static int |
CV_32FC2 |
static int |
CV_32FC3 |
static int |
CV_32FC4 |
static int |
CV_32S |
static int |
CV_32SC1 |
static int |
CV_32SC2 |
static int |
CV_32SC3 |
static int |
CV_32SC4 |
static int |
CV_64F |
static int |
CV_64FC1 |
static int |
CV_64FC2 |
static int |
CV_64FC3 |
static int |
CV_64FC4 |
static int |
CV_8S |
static int |
CV_8SC1 |
static int |
CV_8SC2 |
static int |
CV_8SC3 |
static int |
CV_8SC4 |
static int |
CV_8U |
static int |
CV_8UC1 |
static int |
CV_8UC2 |
static int |
CV_8UC3 |
static int |
CV_8UC4 |
static int |
CV_USRTYPE1 |
其实它们的组成也很简单,就拿后面经常使用的一种类型来说CV_8UC3(inread方法默认使用类型),其中CV表示计算机视觉,8UC表示8位无符号char,3表示3通道(在OpenCv中3通道的顺序是GBR);其他类似。
2,Android中的Bitmap
关于这部分的类容我不想多做介绍,因为在Android开发过程中,我们对其使用应该是比较熟悉了的。
2.1 创建方式
其创建的方式主要有两类,一类是通过Bitmap工厂,一个是自身的静态方法;但更一层的可以知道,它也是存储图像信息的对象,创建其对象一个是根据已有的图像资源或者Bitmap对象创建,一个是构建信息填充到将要创建的Bitmap对象中,分别举例如下:
(1)根据已有的图像资源或者Bitmap对象创建
BitmapFactory静态方法
decodeFile(String pathName) |
Bitmap静态方法
createScaledBitmap(Bitmap src, int dstWidth, int dstHeight, boolean filter) |
(2)构建信息填充到将要创建的Bitmap对象中
Bitmap静态方法
createBitmap(int[] colors, int width, int height, Bitmap.Config config) |
2.2 Bitmap像素存储类型
这个在上面其实已经介绍过了,就是我们的Bitmap.Config中的枚举常量:
ALPHA_8 |
ARGB_4444 |
ARGB_8888 |
RGB_565 |
拿其中一个举例,ARGB_4444表示4通道,每一个通道4位,共两个字节,表示一个像素。
3 两者资源管理
(1)Mat对象在确定后续不使用时,需主动调用release()方法释放资源
(2)Bitmap在现有设备使用的OS版本里面是不需要主动释放资源(也可以保证资源的及时释放主动调用recycle()方法),已经被加入了垃圾回收(gc)机制里面
好了,本篇关于Mat和Bitmap的介绍到这里结束了。作为图像信息的载体,它们API本身逻辑非常之简单,总结好就行了。更多类容请往下看: