c语言bmp位图读入,C语言读取bmp位图文件(含bmp格式定义)

loadbmp.h

#ifndef _LOADBMP_H_

#define _LOADBMP_H_

typedef unsigned char    BYTE;

typedef unsigned short    WORD;

typedef unsigned long    DWORD;

typedef struct {

/* BITMAPFILEHEADER*/

BYTE    bfType[2];

DWORD    bfSize;

WORD    bfReserved1;

WORD    bfReserved2;

DWORD    bfOffBits;

} BMPFILEHEAD;

#define FILEHEADSIZE 14

/* windows style*/

typedef struct {

/* BITMAPINFOHEADER*/

DWORD    BiSize;

DWORD    BiWidth;

DWORD    BiHeight;

WORD    BiPlanes;

WORD    BiBitCount;

DWORD    BiCompression;

DWORD    BiSizeImage;

DWORD    BiXpelsPerMeter;

DWORD    BiYpelsPerMeter;

DWORD    BiClrUsed;

DWORD    BiClrImportant;

} BMPINFOHEAD;

#define INFOHEADSIZE 40

typedef struct _BMP {

BMPINFOHEAD info;

unsigned char *rgba;

unsigned char *yuy2;

unsigned char *yv12;

} BMP, *PBMP;

int LoadBMP(char *name, PBMP pbmp);

int ReleaseBMP(PBMP pbmp);

void rgb_to_yuv(unsigned int r, unsigned int g, unsigned int b,

unsigned int *y, unsigned int *u, unsigned int *v);

#endif/*_LOADBMP_H_*/

loadbmp.c

#include

#include

#include

#include

#include

#include

#include "loadbmp.h"

void rgb_to_yuv(unsigned int r, unsigned int g, unsigned int b,

unsigned int *y, unsigned int *u, unsigned int *v)

{

double dy, du, dv;

dy = (0.257 * (double)r) +

(0.504 * (double)g) + (0.098 * (double)b) + 16.0;

dv= (0.439 * (double)r) - (0.368 * (double)g) - (0.071 * (double)b) +

128.0;

du = -(0.148 * (double)r) - (0.291 * (double)g) +

(0.439 * (double)b) + 128.0;

*y = (unsigned int)dy & 0xff;

*v = (unsigned int)dv & 0xff;

*u = (unsigned int)du & 0xff;

}

static void

convert_to_yv12(PBMP pbmp)

{

int x, y;

unsigned char *in_ptr, *out_ptr_y, *out_ptr_u, *out_ptr_v;

unsigned int Y, U, V;

in_ptr = pbmp->rgba;

out_ptr_y = pbmp->yv12;

out_ptr_u = out_ptr_y + pbmp->info.BiWidth * pbmp->info.BiHeight;

out_ptr_v = out_ptr_u + pbmp->info.BiWidth * pbmp->info.BiHeight / 4;

for (y = 0; y < pbmp->info.BiHeight; y++) {

for (x = 0; x < pbmp->info.BiWidth; x++) {

rgb_to_yuv(in_ptr[0], in_ptr[1], in_ptr[2], &Y, &U, &V);

in_ptr += pbmp->info.BiBitCount / 8;

*out_ptr_y++ = Y;

if (x % 2 == 0 && y % 2 == 0) {

*out_ptr_u++ = V;

*out_ptr_v++ = U;

}

}

}

}

static void

convert_to_yuy2(PBMP pbmp)

{

int x, y;

unsigned char *in, *out;

unsigned int Y, U, V;

in = pbmp->rgba;

out = pbmp->yuy2;

for (y = 0; y < pbmp->info.BiHeight; y++) {

for (x = 0; x < pbmp->info.BiWidth; x++) {

static int cnt = 0;

rgb_to_yuv(in[0], in[1], in[2], &Y, &U, &V);

in += pbmp->info.BiBitCount / 8;

*(out) = Y;

if (cnt %2 == 0)

*(out+1) = V;

else

*(out+1) = U;

out+= 2;

cnt++;

}

}

}

int LoadBMP(char *name, PBMP pbmp)

{

int        fd;

int        headsize;

BMPFILEHEAD    bmpf;

unsigned char     headbuffer[INFOHEADSIZE];

fd = open(name, O_RDONLY);

if (fd < 0) {

perror("open");

return -1;

}

read(fd, &headbuffer, FILEHEADSIZE);

bmpf.bfType[0] = headbuffer[0];

bmpf.bfType[1] = headbuffer[1];

if (*(WORD*)&bmpf.bfType[0] != 0x4D42) /* 'BM' */

return -2;    /* not bmp image*/

bmpf.bfOffBits = *((DWORD*)&headbuffer[10]);

if (read(fd,&headsize,sizeof(DWORD)) != sizeof(DWORD))

return 0;    /* not bmp image*/

read(fd, &headbuffer, INFOHEADSIZE - sizeof(DWORD));

pbmp->info.BiWidth = *(DWORD*)(&headbuffer[0]);

pbmp->info.BiHeight = *(DWORD*)(&headbuffer[4]);

pbmp->info.BiBitCount = *(DWORD*)(&headbuffer[10]);

pbmp->info.BiSizeImage = *(DWORD*)(&headbuffer[16]);

pbmp->rgba = (unsigned char *)malloc(pbmp->info.BiSizeImage);

if (!pbmp->rgba) {

perror("malloc");

exit(EXIT_FAILURE);

}

//    pbmp->yuy2 = (unsigned char *)malloc(pbmp->info.BiWidth * pbmp->info.BiHeight * 2);

//    if (!pbmp->yuy2) {

//        perror("malloc");

//        exit(EXIT_FAILURE);

//    }

//    pbmp->yv12 = (unsigned char *)malloc(pbmp->info.BiWidth * pbmp->info.BiHeight * 3 / 2);

//    if (!pbmp->yv12) {

//        perror("malloc");

//        exit(EXIT_FAILURE);

//    }

lseek(fd, bmpf.bfOffBits, SEEK_SET);

if (read(fd, pbmp->rgba, pbmp->info.BiSizeImage) != pbmp->info.BiSizeImage) {

perror("read");

return -4;

}

//    convert_to_yv12(pbmp);

//    convert_to_yuy2(pbmp);

printf("LoadBMP: %s %ldx%ldx%d\n", name, pbmp->info.BiWidth, pbmp->info.BiHeight, pbmp->info.BiBitCount);

close(fd);

return 0;

}

int ReleaseBMP(PBMP pbmp)

{

if (pbmp->rgba) {

free(pbmp->rgba);

pbmp->rgba = NULL;

}

//    if (pbmp->yuy2) {

//        free(pbmp->yuy2);

//        pbmp->yuy2 = NULL;

//    }

//    if (pbmp->yv12) {

//        free(pbmp->yv12);

//        pbmp->yv12 = NULL;

//    }

return 0;

}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值