【问题标题】:8Bit Grayscale Bitmap to Array8Bit 灰度位图转数组
【发布时间】:2012-07-07 03:38:06
【问题描述】:

我想知道,从这里我将如何将像素值存储到矩阵中?我想打印出强度(灰度)值。

示例数组[5] = 4 或数组[3][1] = 17

我真的不知道该怎么做。我看到的所有示例似乎都很复杂,有没有简单的方法可以做到这一点?

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

struct BitMap
{
short Type;
long Size;
short Reserve1;
short Reserve2;
long OffBits;
long biSize;
long biWidth;
long biHeight;
short biPlanes;
short biBitCount;
long biCompression;
long biSizeImage;
long biXPelsPerMeter;
long biYPelsPerMeter;
long biClrUsed;
long biClrImportant;
}Header;

int main( void ){

    FILE *BMPFile = fopen ("MriHotrod.bmp", "rb");

    if(BMPFile == NULL){
        return;
    }

    unsigned char DataBuff[128*128];
    int i;
    int j;

    memset(&Header, 0, sizeof(Header));

    fread(&Header.Type, 2, 1, BMPFile);
    fread(&Header.Size, 4, 1, BMPFile);
    fread(&Header.Reserve1, 2, 1, BMPFile);
    fread(&Header.Reserve2, 2, 1, BMPFile);
    fread(&Header.OffBits, 4, 1, BMPFile);
    fread(&Header.biSize, 4, 1, BMPFile);
    fread(&Header.biWidth, 4, 1, BMPFile);
    fread(&Header.biHeight, 4, 1, BMPFile);
    fread(&Header.biPlanes, 2, 1, BMPFile);
    fread(&Header.biBitCount, 2, 1, BMPFile);
    fread(&Header.biCompression, 4, 1, BMPFile);
    fread(&Header.biSizeImage, 4, 1, BMPFile);
    fread(&Header.biXPelsPerMeter, 4, 1, BMPFile);
    fread(&Header.biYPelsPerMeter, 4, 1, BMPFile);
    fread(&Header.biClrUsed, 4, 1, BMPFile);
    fread(&Header.biClrImportant, 4, 1, BMPFile);

printf("\nType:%hd\n", Header.Type);
printf("Size:%ld\n", Header.Size);
printf("Reserve1:%hd\n", Header.Reserve1);
printf("Reserve2:%hd\n", Header.Reserve2);
printf("OffBits:%ld\n", Header.OffBits);
printf("biSize:%ld\n", Header.biSize);
printf("Width:%ld\n", Header.biWidth);
printf("Height:%ld\n", Header.biHeight);
printf("biPlanes:%hd\n", Header.biPlanes);
printf("biBitCount:%hd\n", Header.biBitCount);
printf("biCompression:%ld\n", Header.biCompression);
printf("biSizeImage:%ld\n", Header.biSizeImage);
printf("biXPelsPerMeter:%ld\n", Header.biXPelsPerMeter);
printf("biYPelsPerMeter:%ld\n", Header.biYPelsPerMeter);
printf("biClrUsed:%ld\n", Header.biClrUsed);
printf("biClrImportant:%ld\n\n", Header.biClrImportant);

fread(DataBuff, sizeof(DataBuff), 128*128, BMPFile);

for(i=0; i<20; i++){
    printf("%d\n", DataBuff[i]);
}

fclose(BMPFile);

return 0;
}

Output
Type:19778
Size:17462
Reserve1:0
Reserve2:0
OffBits:1078
biSize:40
Width:128
Height:128
biPlanes:1
biBitCount:8
biCompression:0
biSizeImage:0
biXPelsPerMeter:0
biYPelsPerMeter:0
biClrUsed:256
biClrImportant:0

0
0
0
0
1
1
1
0
2
2
2
0
3
3
3
0
4
4
4
0

我认为标题信息是正确的,并且元素的数量是正确的(16384)。我只是不确定如何打印出像素值。以上显然是不对的……

这和填充有关吗?

谢谢!

【问题讨论】:

    标签: bitmap grayscale


    【解决方案1】:

    您需要从 BMPFile.OffBits 中指定的偏移量开始读取像素。

    BMP 标头中还有一个“颜色表” - 每个像素都是其中的索引(IIRC!),因此它用作颜色查找表。维基百科建议颜色表对于 8BPP(或更少)图像是强制性的。

    另外:由于您的图像是每像素 8 位,因此您需要通过提取 RGB 分量并将它们组合来将 RGB 转换为灰度。

    另外还有:你为什么说你的结果“明显错误”?请记住,.bmp 文件是倒置存储在文件中的。

    您使用的是哪个操作系统? Windows 提供了为您执行此操作的函数。

    【讨论】:

    • 好的,现在我已经从偏移量开始,结果更有意义了。我在 Windows 上。我会看看是否可以找到有关 RGB 组件的一些信息。感谢您的帮助!
    • 另一个问题,如果我要打印出从 1074 到 1078 的值(如我的代码中所示),这不应该给我左下角像素的 B G R W 值吗?因为它肯定不会。有什么想法吗?
    • 位图是倒置存储的——所以第 0 个像素位于左下角,这与直觉相反!您的位应按蓝色、绿色、红色顺序排列。上次我这样做时,我记得我制作了一个纯红色位图并在十六进制编辑器中打开它以确保我得到了我所期望的 - 然后对左下角的像素和其他两种原色做了同样的事情。此外,您的图像报告为每像素 8 位 - 所以每像素一个字节,而不是三个!
    • 嘿 Randomdude,原来我的 BMPFile.OffBits 是 1024,但我的标题告诉我它是 1078。你知道为什么会这样吗?
    • 嗯,这很奇怪。我创建了几个测试位图(通过 MSPaint),它们似乎从 OffBits 的位置开始。你能上传你的位图让我们看看吗?
    猜你喜欢
    • 1970-01-01
    • 2013-06-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-08-11
    • 2012-04-29
    • 1970-01-01
    • 2014-09-29
    相关资源
    最近更新 更多