如何绘制到设备上下文中

时间:2017-02-18 13:01:52

标签: winapi device-context

我有一个32位整数数组形式的位图图像(ARGB像素:uint32 *mypixels)和int width以及int height。我需要将它们输出到打印机。

我有打印机上下文:HDC hdcPrinter;

据我所知,我首先需要创建一个兼容的上下文:

HDC hdcMem = CreateCompatibleDC(hdcPrinter);

然后我需要创建一个HBITMAP对象,将其选择到兼容的上下文中,然后渲染:

HBITMAP hBitmap = ...?
SelectObject(hdcMem, hBitmap);
BitBlt(printerContext, 0, 0, width, height, hdcMem, 0, 0, SRCCOPY);

最后清理:

DeleteObject(hBitmap);
DeleteDC(hdcMem);

我的问题是如何创建HBITMAP对象并将mypixels放入其中?

我找到了两个选项:

  1. HBITMAP hBitmap = CreateCompatibleBitmap(hdcPrinter, width, height);

    看起来不错,但mypixels如何进入此位图?

  2. HBITMAP hBitmap = CreateDIBSection(hdcPrinter /*or hdcMem?*/, ...);

    会起作用吗?它是否比选项1更好。?

1 个答案:

答案 0 :(得分:0)

此函数创建一个位图并将其设置为初始图像。 Irt有点讨厌直接访问这些位,但是可以做到。

HBITMAP MakeBitmap(unsigned char *rgba, int width, int height, VOID **buff)
{
    VOID *pvBits;          // pointer to DIB section 
    HBITMAP answer;
    BITMAPINFO bmi;
    HDC hdc;
    int x, y;
    int red, green, blue, alpha;

    // setup bitmap info   
    bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
    bmi.bmiHeader.biWidth = width;
    bmi.bmiHeader.biHeight = height;
    bmi.bmiHeader.biPlanes = 1;
    bmi.bmiHeader.biBitCount = 32;         // four 8-bit components 
    bmi.bmiHeader.biCompression = BI_RGB;
    bmi.bmiHeader.biSizeImage = width * height * 4;

    hdc = CreateCompatibleDC(GetDC(0));
    answer = CreateDIBSection(hdc, &bmi, DIB_RGB_COLORS, &pvBits, NULL, 0x0);
    for (y = 0; y < height; y++)
    {
        for (x = 0; x < width; x++)
        {
            red = rgba[(y*width + x) * 4];
            green = rgba[(y*width + x) * 4 + 1];
            blue = rgba[(y*width + x) * 4 + 2];
            alpha = rgba[(y*width + x) * 4 + 3];
            red = (red * alpha) >> 8;
            green = (green * alpha) >> 8;
            blue = (blue * alpha) >> 8;
            ((UINT32 *)pvBits)[(height - y - 1) * width + x] = (alpha << 24) | (red << 16) | (green << 8) | blue;
        }
    }
    DeleteDC(hdc);

    *buff = pvBits;

    return answer;
}