Opencv study notes - C++ reads the bmp image data, converts it to a mat-type matrix, and displays the output

Before we start, let's introduce the usage of the mat class:

1. The mat class stores images

The Mat class is a widely used class in OpenCV, and one of the most important functions is as a data structure for storing images. So how does the Mat class store images?

       We all know that images are divided into color images and grayscale images. I have a misunderstanding here. I always think that a color image is a three-dimensional matrix, which is the structure of a cube. An image is divided into three layers. But this understanding is wrong. In fact, the stored image, whether it is a color or grayscale image, is a two-dimensional matrix. The specific storage format is as follows:
(1) The format of the grayscale image:

(2) The color image Format:


Although the color image has three channels of BGR, it is stored in the same plane, but OpenCV treats three columns as one column here, so img.cols is equal to the number of columns in the image.

Generally, the data type of the grayscale image we read with Opencv is of type uchar , while the data type of one pixel of the color image is of type <Vec3b> . One pixel of the grayscale image occupies 1 byte, and one pixel of the color image 3 bytes.

2. Convert the array to mat class and display the output

This program succeeds the previous C++ image reading program. In the previous program, the bmp image data has been read out and stored in the matrix. What we need to achieve here is to store the three-channel image data in the mat matrix and display the output. code show as below:

rgb2opencvshow.cpp

#include<cstdlib>
#include<cstdio>
#include<cmath>
#include<iomanip>
#include <opencv2/opencv.hpp>
#include "opencv2/highgui/highgui.hpp"
#include "opencv2/core/core.hpp"
#include"readbmp.h"
#include"savebmp.h"

using namespace std;
using namespace cv;

unsigned int **out_r;
unsigned int **out_g;
unsigned int **out_b;

void doIt()
{

	char readPath[] = "D:\\C++_file\\image_deal_C++\\read_BMP\\lunpan.bmp";
	readBmp(readPath);
	// output the overall image information
	cout << "\nwidth=" << bmpWidth << "\nheight=" << bmpHeight << "\nbiBitCount=" << biBitCount << endl;
	// number of bytes of the image
	int linebyte1 = (bmpWidth*biBitCount / 8 + 3) / 4 * 4;
	int n = 0, m = 0, count_xiang_su = 0;

	out_r = new unsigned int *[bmpHeight]; //Create an array of pointers
	for (int i = 0; i<bmpHeight; i++)
		out_r[i] = new unsigned int[bmpWidth];

	out_g = new unsigned int *[bmpHeight]; //Open an array of pointers
	for (int i = 0; i<bmpHeight; i++)
		out_g[i] = new unsigned int[bmpWidth];

	out_b = new unsigned int *[bmpHeight]; //Create an array of pointers
	for (int i = 0; i<bmpHeight; i++)
		out_b[i] = new unsigned int[bmpWidth];

	//Initialize an array of raw pixels.

	if (biBitCount == 8)
	{
		for (int i = 0; i<bmpHeight / 2; i++)
		{
			for (int j = 0; j<bmpWidth / 2; i++)
				*(pBmpBuf + i*linebyte1 + j) = 0;
		}
	}

	if (biBitCount == 24)
	{
		for (int i = 0; i<bmpHeight; i++)
		{
			for (int j = 0; j<bmpWidth; j++)
			{
				for (int k = 0; k<3; k++)//The three RGB components of each pixel are set to 0 to turn black
				{
					m = *(pBmpBuf + i*linebyte1 + j * 3 + k);
					count_xiang_su++;
				}
				n++;
			}
		}
		cout << "The total number of pixels is:" << n << endl;
		cout << "----------------------------------------------------" << endl;
	}


	if (biBitCount == 24)
	{
		for (int i = 0; i<bmpHeight; i++)
		{
			for (int j = 0; j<bmpWidth; j++)
			{
				out_r[bmpHeight - 1 - i][j] = pBmpBuf[j * 3 + 2 + bmpWidth*i * 3];
				out_g[bmpHeight - 1 - i][j] = pBmpBuf[j * 3 + 1 + bmpWidth *i * 3];
				out_b[bmpHeight - 1 - i][j] = pBmpBuf[j * 3 + bmpWidth *i * 3];
			}
		}
		Mat img_data(bmpHeight, bmpWidth, CV_8UC3);
		for (int i = 0; i<bmpHeight; i++){
			for (int j = 0; j<bmpWidth; j++){
				img_data.at<Vec3b>(i, j)[0] = out_b[i][j];
				img_data.at<Vec3b>(i, j) [1]= out_g[i][j];
				img_data.at<Vec3b>(i, j) [2]= out_r[i][j];
			}
		}
		
		namedWindow("lunpan");
		imshow("lunpan",img_data);
		waitKey(0);
		imwrite("D:\\C++_file\\image_deal_C++\\11.bmp",img_data);
	
	}

	//Clear the buffer, pBmpBuf and pColorTable are global variables, the space allocated when the file is read in
	delete[]pBmpBuf;
	if (biBitCount == 8)
		delete[]pColorTable;

}


intmain()
{
	must();
	system("pause");
	return 0;
}
Testing the program shows that the output result is the same as the original image, and the data conversion is successfully achieved.









Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325792041&siteId=291194637