bmp图片处理

bmp图片基础

BMP格式内的数据分为三到四个部分,依次是:

  1. 文件信息头 (14字节)存储着文件类型,文件大小等信息
  2. 图片信息头 (40字节)存储着图像的尺寸,颜色索引,位平面数等信息
  3. 调色板 (由颜色索引数决定)【24位及以上可以没有此信息】
  4. 位图数据 (由图像尺寸决定)每一个像素的信息在这里存储

一般的bmp图像都是24位,也就是真彩。每8位为一字节,24位也就是使用三字节来存储每一个像素的信息,三个字节对应存放r,g,b三原色的数据,每个字节的存贮范围都是0-255。那么以此类推,32位图即每像素存储r,g,b,a(Alpha通道,存储透明度)四种数据。8位图就是只有灰度这一种信息,还有二值图,它只有两种颜色,黑或者白。

1. 计算调色板大小

位图起始位置偏移量 - 54

2. 计算每行的字节数

bmp图片每一行都是4的倍数,不足添加无效位
即一行的字节数等于图片宽度(一行像素点总数)* 像素点占的位数
行字节数 = 位图宽 + ((4 - (位图宽 * 像素点位数 / 8)%4))%4

lineByte = bmp.width_x + ((4-(bmp.width_x*bmp.deepth/8)%4))%4;

bmpFormat.h

#ifndef _BMPFORMAT_H_
#define _BMPFORMAT_H_

typedef unsigned char BYTE;  // 定义BYTE为一个字节的类型
typedef unsigned short WORD; // 定义WORD为两个字节的类型
typedef unsigned int DWORD;  // 定义DWORD为四个字节的类型

#pragma pack(2) // 按两个字节对齐
/* BMP文件头结构体,共14字节 */
typedef struct BMP_FILE_HEADER
{
    WORD bfType;      // 文件标识符,类型
    DWORD bfSize;     // 文件的大小,字节为单位
    WORD bfReserved1; // 保留值,必须设置为0
    WORD bfReserved2; // 保留值,必须设置为0
    DWORD bfOffset;   // 文件头的最后到图像数据位开始的偏移量
} BMPFILEHEADER;
//#pragma pack(pop)

/* 位图信息头,共40字节*/
typedef struct BMP_INFO_HEADER
{
    DWORD biInfoSize;      // 位图信息头的大小
    DWORD biWidth;         // 图像的宽度,像素单位
    DWORD biHeight;        // 图像的高度,像素单位
    WORD biPlanes;         // 图像的平面数,总为1
    WORD biBitCount;       // 每个像素的位数,及比特数1、4、8、16、24或32
    DWORD biCompression;   // 压缩类型
    DWORD biImageSize;     // 图像的大小,以字节为单位
    DWORD biXPelsPerMeter; // 水平分辨率
    DWORD biYPelsPerMeter; // 垂直分辨率
    DWORD biClrUsed;       // 使用的色彩数
    DWORD biClrImportant;  // 重要的颜色数
} BMPINFOHADER;

/* 自定义的存放颜色数据的结构体 */
typedef struct BMP_BASE
{
    unsigned char *buf; //用来存放颜色的数据
    int width_x;        //宽
    int height_y;       //高
    int deepth;         //像素的位数及biBitCount
} BMPBASE;

#endif

bmp.c

功能将8位bmp图片解析读取并写入到新的文件中

/*********************************************************************
*    处理8位bmp位图
*********************************************************************/
#include 
#include 
#include 
#include "bmpFormat.h"

int main()
{
    FILE *in;                    // 定义一个输入文件指针
    FILE *out;                   // 定义一个输出文件指针
    BMPFILEHEADER bmpFileHeader; // 定义一个BMP文件头
    BMPINFOHADER bmpInfoHeader;  // 定义一个BMP位图信息头
    BMPBASE bmp;                 // 定义一个存储颜色信息
    unsigned char *tmp;          // 调色板(颜色表)信息缓冲区
    int lineByte;				 // 一行字节数
    int biPaletteSize;           // 调色板信息大小    /* 打开原始图片并读取有关数据 */

    if ((in = fopen("in.bmp", "rb")) == NULL) //打开图片
    {
        printf("Cann't open the file!\n");
        return 0;
    }

    fread(&bmpFileHeader, sizeof(BMPFILEHEADER), 1, in);  //读取文件头信息

    fread(&bmpInfoHeader, sizeof(BMPINFOHADER), 1, in);  //读位图信息头信息

    //读取颜色表信息
    biPaletteSize = bmpFileHeader.bfOffset - 54;//BMP文件头信息,共14字节;位图信息头,共40字节
    tmp = (unsigned char*)malloc(biPaletteSize);
    fread(tmp, biPaletteSize, 1, in);
    
    ///将原始图片色彩信息存储到Bmpbase
    bmp.width_x = bmpInfoHeader.biWidth; //获取图片宽、高、每个像素所占位数等信息
    bmp.height_y = bmpInfoHeader.biHeight;
    bmp.deepth = bmpInfoHeader.biBitCount;
   
    lineByte = bmp.width_x + ((4-(bmp.width_x*bmp.deepth/8)%4))%4;  //定义变量,计算图像每行像素所占字节数,每行都是4的整数倍,不足使用无效字节填充
    bmp.buf = (unsigned char *)malloc(lineByte * bmp.height_y); //创建一定大小的数组空间存放颜色数据
    fread(bmp.buf, 1, lineByte * bmp.height_y, in);             //将颜色数据读入数组空间


    /* 创建新图,并写入信息*/
    if ((out = fopen("out.bmp", "wb")) == NULL) //打开新文件
    {
        printf("Cann't creat new file!\n");
        return 0;
    }
    
    //写文件头进文件
    fwrite(&bmpFileHeader, sizeof(BMPFILEHEADER), 1, out);

     //写位图信息头进文件
    fwrite(&bmpInfoHeader, sizeof(BMPINFOHADER), 1, out);

    //写调色板信息
    fwrite(tmp, biPaletteSize, 1, out);

    //写颜色数据进文件
    fwrite(bmp.buf, lineByte * bmp.height_y, 1, out);

#if 0
    printf("biPaletteSize:%d\n", biPaletteSize);//颜色表大小
    printf("width_x:%d width_y:%d\n", bmp.width_x, bmp.height_y);//图片宽高
    printf("lineByte:%d\n", lineByte); //行字节数
    printf("bmp.deepth:%d\n", bmp.deepth); //一个像素点占用的位数
#endif 

    fclose(in);
    fclose(out);
    free(tmp);
    free(bmp.buf);

    return 0;
}

你可能感兴趣的:(图像处理,图片处理,bmp)