【问题标题】:Reading Bitmap file读取位图文件
【发布时间】:2020-07-28 17:46:14
【问题描述】:

我尝试读取位图文件。这是我的程序:

#include<iostream>
#include<fstream>
#include <string>
#include<windows.h>
using namespace std;

#pragma pack(1)
struct header
{
    char header[2];
    int32_t filesize;
    int16_t reser;
    int16_t reser1;
    int32_t dataoffset;
};

struct infoheader
{
    int32_t headersize;
    int32_t width;
    int32_t height;
    int16_t plans;
    int16_t bpp;
    int32_t compression;
    int32_t datasize;
    int32_t re;
    int32_t ve;
    int32_t color;
    int32_t importantcolor;
};

struct  PIxel
{
    unsigned char G;
    unsigned char B;
    unsigned char R;
};

int main()
{
    header h;
    infoheader info;
    PIxel *p;
    ifstream file("bmp2.bmp", ios::binary);
    if (file.is_open())
    {
        cout << "true" << endl;
        file.read((char*)&h, sizeof(h));
        file.read((char*)&info, sizeof(info));
        cout << info.width << " " << info.height << " " << h.filesize << " " << info.bpp << endl;
        int pa = info.width % 4;
        int size = info.width * info.height * (info.bpp / 3) + pa * info.height;
        char* arr = new char[size];
        file.read(arr, size);
        char* temp = arr;
        int sizep = info.height * info.width;
        p = new PIxel[sizep];

        for (int i = 0; i < info.height; i++)
        {
            for (int j = 0; j < info.width; j++)
            {
                p[i * info.height + j].B = *(temp++);
                p[i * info.height + j].G = *(temp++);
                p[i * info.height + j].R = *(temp++);
                //p = p + 3;
            }
            p += pa;
        }

        HWND consoleWindow = GetConsoleWindow();
        HDC hdc = GetDC(consoleWindow);
        for (int i = 0; i < info.height; i++)
        {
            for (int j = 0; j < info.width; j++)
            {
                PIxel m = p[i * info.height + j];
                SetPixel(hdc, i, j, RGB(m.R, m.G, m.B));
            }
        }
        ReleaseDC(consoleWindow, hdc);
    }
}

它可以工作,但我控制台上的图像不正确...

你能帮我解决它吗?

【问题讨论】:

  • 看起来每行填充有问题。尽管您的代码似乎正在使用填充。
  • 我认为p += pa; 是错误的。您想通过填充而不是 p 推进 tempp 是目的地。源是有填充的。
  • 在控制台窗口上绘图也不是一个好主意。
  • 为什么不使用BITMAPFILEHEADERBITMAPINFOHEADERRGBTRIPLE。你硬编码24bpp bmp。您的代码不适用于另一个 bpp。为什么不使用CreateDIBSectionBitBlt
  • Windows Imaging Component 带有一个 bitmap decoder,这样我们就不必处​​理这些内部问题,也不会弄错。

标签: c++ file winapi struct bitmap


【解决方案1】:

我相信您在错误的指针上调整了填充。填充存在于源图像上。您不希望它出现在目标图像上。您正在使用 p += pa; 考虑填充,您应该将此行替换为 temp += pa 以考虑源图像的填充。

【讨论】:

    【解决方案2】:
    int size = info.width * info.height * (info.bpp / 3) + pa * info.height; 
    

    上述尺寸计算不正确。每个像素的位数应除以 8。for 循环中的索引也是错误的。它最终乘以高度 x 高度。

    还应将SetPixel(... i, j ...) 更改为SetPixel(... j, i ...),因为在您的情况下i 指的是y 轴。

    如上一个答案所述,填充也必须固定。

    请注意,您可以使用LoadImage 和其他 Windows GDI 函数来打开和绘制位图。

    int size = (info.width * (info.bpp / 8) + pa) * info.height;
    ...
    for(int i = info.height - 1; i >= 0; i--)
    {
        for(int j = 0; j < info.width; j++)
        {
            int index = i * (info.width) + j;
            p[index].B = *(temp++);
            p[index].G = *(temp++);
            p[index].R = *(temp++);
        }
        temp += pa;
    }
    
    for(int i = 0; i < info.height; i++)
    {
        for(int j = 0; j < info.width; j++)
        {
            int index = i * (info.width) + j;
            PIxel m = p[index];
            SetPixel(hdc, j, i, RGB(m.R, m.G, m.B));
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2020-03-16
      • 2012-06-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-12-13
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多