gpt4 book ai didi

C: WinAPI CreateDIBitmap() 来自 byte[] 问题

转载 作者:行者123 更新时间:2023-11-30 18:09:19 25 4
gpt4 key购买 nike

我已经研究这个问题有一段时间了。
我正在尝试使用 libjpeg 将 JPEG 支持添加到程序中。
在大多数情况下,它运行得相当好,但对于某些 JPEG,它们显示如左图。

(与 original image 比较。)

这可能不明显,但背景显示为交替的红绿蓝行。如果有人以前见过这种行为并知道可能的原因,我将不胜感激。

我已将行填充为四个字节的倍数,但这对解决问题仅略有帮助。

代码:

  rowSize = cinfo.output_width * cinfo.num_components;
/* Windows needs bitmaps to be defined on Four Byte Boundaries */
winRowSize = (rowSize + 3) & -4;
imgSize = (cinfo.output_height * winRowSize + 3) & -4;
while(cinfo.output_scanline < cinfo.output_height){
jpeg_read_scanlines(&cinfo, &row_pointer, 1);

/* stagger read to get lines Bottom->Top (As BMP Requires) */
location = (imgSize) - (cinfo.output_scanline * winRowSize);
rowsRead++;

for(i = 0; i < winRowSize; i++){
rawImage[location++] = row_pointer[i];
}
}

/* Convert BGR to RGB */
if(cinfo.num_components == 3){
for(i = 0; i < imgSize; i += 3){
tmp = rawImage[i+2];
rawImage[i+2] = rawImage[i];
rawImage[i] = tmp;
}
}

biSize = sizeof(BITMAPINFOHEADER);
if(cinfo.num_components == 1){ /* Greyscale */
biPallete = 32 * 256;
biSize += biPallete;
}

bitInf = (BITMAPINFO *)malloc(biSize);

bitInf->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
bitInf->bmiHeader.biWidth = cinfo.output_width;
bitInf->bmiHeader.biHeight = cinfo.output_height;
bitInf->bmiHeader.biPlanes = 1;
bitInf->bmiHeader.biBitCount = 8*cinfo.num_components;
bitInf->bmiHeader.biCompression = BI_RGB;
bitInf->bmiHeader.biSizeImage = 0;
bitInf->bmiHeader.biXPelsPerMeter = 0;
bitInf->bmiHeader.biYPelsPerMeter = 0;
bitInf->bmiHeader.biClrUsed = 0;
bitInf->bmiHeader.biClrImportant = 0;

if(cinfo.num_components == 1){
for(i = 0; i < 256; i++){
bitInf->bmiColors[i].rgbBlue = i;
bitInf->bmiColors[i].rgbGreen = i;
bitInf->bmiColors[i].rgbRed = i;
bitInf->bmiColors[i].rgbReserved = 0;
}
}

/* Loads rawImage into an HBITMAP */
/* retval = CreateDIBitmap(inDC, &bitInf->bmiHeader, CBM_INIT, rawImage, bitInf, DIB_RGB_COLORS); */
retval = CreateCompatibleBitmap(inDC, cinfo.output_width, cinfo.output_height);
errorCode = SetDIBits(inDC, retval, 0, cinfo.output_height, rawImage, bitInf, DIB_RGB_COLORS);

解决方案:我将 RGB/BGR 转换器更改为:

if(cinfo.num_components == 3){
for(i = 0; i < cinfo.output_height; i++){
location = (i * winRowSize);
for(j = 0; j < rowSize; j += 3){
tmp = rawImage[location+2];
rawImage[location+2] = rawImage[location];
rawImage[location] = tmp;
location += 3;
}
}
}

它就像一个魅力。感谢roygbiv .

最佳答案

造成左图像的最常见原因之一是缓冲区未正确对齐。

我相信 Windows 需要 DWORD 对齐的缓冲区。

我在上面的代码中看到的一个问题是您不想使用 winRowSize 来复制实际像素,您想使用具有(图像宽度 * 每像素字节数)的变量。 winRowSize 复制 DWORD 对齐大小,该大小可能太大(尽管某些图像可能会工作,因为它们默认处于 DWORD 对齐。)

更改 for 循环:

        for(i = 0; i < (width of the image * bytes per pixel); i++){ 
rawImage[location++] = row_pointer[i];
}

(您可能还需要调整 rgb 到 bgr 代码。)

关于C: WinAPI CreateDIBitmap() 来自 byte[] 问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2520682/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com