如何通过Win32 API在不使用GDI的情况下高效加载PNG图像?

2026-04-16 22:196阅读0评论SEO问题
  • 内容介绍
  • 文章标签
  • 相关推荐

本文共计322个文字,预计阅读时间需要2分钟。

如何通过Win32 API在不使用GDI的情况下高效加载PNG图像?

可以使用Win32+GDI函数将PNG从文件加载到HBITMAP中。如果没有使用外部库(如libpng),最轻量级的解决方案是使用Windows Imaging Component(WIC)来加载PNG文件。以下是使用WIC加载PNG文件的示例代码:

cpp#include #include

HBITMAP LoadPNGToHBITMAP(const wchar_t* filePath) { IStream* pStream=NULL; IWICImagingFactory* pFactory=NULL; IWICBitmapDecoder* pDecoder=NULL; IWICBitmap* pBitmap=NULL; HBITMAP hBitmap=NULL;

HRESULT hr=S_OK;

// 创建WIC工厂 hr=CoCreateInstance(CLSID_WICImagingFactory, NULL, CLSCTX_INPROC_SERVER, IID_IWICImagingFactory, (void**)&pFactory); if (FAILED(hr)) return NULL;

// 打开文件流 hr=CreateFileW(filePath, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL, &pStream); if (FAILED(hr)) { pFactory->Release(); return NULL; }

// 创建WIC流 hr=pFactory->CreateStreamFromHandle(pStream, 0, NULL, &pDecoder); pStream->Release(); if (FAILED(hr)) return NULL;

// 解码PNG文件 hr=pDecoder->GetFrame(0, &pBitmap); pDecoder->Release(); if (FAILED(hr)) return NULL;

// 创建HBITMAP BITMAP bmp; pBitmap->GetSize(&bmp); bmp.bmWidth=bmp.bmWidthMM / GetDeviceCaps(GetDC(NULL), LOGPIXELSX); bmp.bmHeight=bmp.bmHeightMM / GetDeviceCaps(GetDC(NULL), LOGPIXELSY); bmp.bmWidthBytes=(bmp.bmWidth * 32 + 31) / 32 * 4; bmp.bmPlanes=1; bmp.bmBitsPixel=32; bmp.bmBits=GlobalAlloc(GMEM_MOVEABLE, bmp.bmWidthBytes * bmp.bmHeight); HBITMAP hOldBitmap=(HBITMAP)SelectObject((HDC)GetDC(NULL), (HBITMAP)bmp.bmBits);

// 将WIC位图复制到HBITMAP pBitmap->CopyPixels(NULL, bmp.bmWidthBytes, bmp.bmHeight, (UINT*)bmp.bmBits);

hBitmap=(HBITMAP)bmp.bmBits; SelectObject((HDC)GetDC(NULL), hOldBitmap); pBitmap->Release();

pFactory->Release();

如何通过Win32 API在不使用GDI的情况下高效加载PNG图像?

return hBitmap;}

是否可以使用Win32 GDI函数将PNG从文件加载到HBITMAP中?如果没有,没有使用外部库(如libpng),最轻的解决方案是什么? 您可以使用 Windows Imaging Component加载PNG文件(在Windows XP SP2及更高版本上).有关如何使用API​​和 my blog post的介绍,请参阅 MSDN Magazine,以获取从IStream加载PNG并将其转换为HBITMAP的代码示例.

本文共计322个文字,预计阅读时间需要2分钟。

如何通过Win32 API在不使用GDI的情况下高效加载PNG图像?

可以使用Win32+GDI函数将PNG从文件加载到HBITMAP中。如果没有使用外部库(如libpng),最轻量级的解决方案是使用Windows Imaging Component(WIC)来加载PNG文件。以下是使用WIC加载PNG文件的示例代码:

cpp#include #include

HBITMAP LoadPNGToHBITMAP(const wchar_t* filePath) { IStream* pStream=NULL; IWICImagingFactory* pFactory=NULL; IWICBitmapDecoder* pDecoder=NULL; IWICBitmap* pBitmap=NULL; HBITMAP hBitmap=NULL;

HRESULT hr=S_OK;

// 创建WIC工厂 hr=CoCreateInstance(CLSID_WICImagingFactory, NULL, CLSCTX_INPROC_SERVER, IID_IWICImagingFactory, (void**)&pFactory); if (FAILED(hr)) return NULL;

// 打开文件流 hr=CreateFileW(filePath, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL, &pStream); if (FAILED(hr)) { pFactory->Release(); return NULL; }

// 创建WIC流 hr=pFactory->CreateStreamFromHandle(pStream, 0, NULL, &pDecoder); pStream->Release(); if (FAILED(hr)) return NULL;

// 解码PNG文件 hr=pDecoder->GetFrame(0, &pBitmap); pDecoder->Release(); if (FAILED(hr)) return NULL;

// 创建HBITMAP BITMAP bmp; pBitmap->GetSize(&bmp); bmp.bmWidth=bmp.bmWidthMM / GetDeviceCaps(GetDC(NULL), LOGPIXELSX); bmp.bmHeight=bmp.bmHeightMM / GetDeviceCaps(GetDC(NULL), LOGPIXELSY); bmp.bmWidthBytes=(bmp.bmWidth * 32 + 31) / 32 * 4; bmp.bmPlanes=1; bmp.bmBitsPixel=32; bmp.bmBits=GlobalAlloc(GMEM_MOVEABLE, bmp.bmWidthBytes * bmp.bmHeight); HBITMAP hOldBitmap=(HBITMAP)SelectObject((HDC)GetDC(NULL), (HBITMAP)bmp.bmBits);

// 将WIC位图复制到HBITMAP pBitmap->CopyPixels(NULL, bmp.bmWidthBytes, bmp.bmHeight, (UINT*)bmp.bmBits);

hBitmap=(HBITMAP)bmp.bmBits; SelectObject((HDC)GetDC(NULL), hOldBitmap); pBitmap->Release();

pFactory->Release();

如何通过Win32 API在不使用GDI的情况下高效加载PNG图像?

return hBitmap;}

是否可以使用Win32 GDI函数将PNG从文件加载到HBITMAP中?如果没有,没有使用外部库(如libpng),最轻的解决方案是什么? 您可以使用 Windows Imaging Component加载PNG文件(在Windows XP SP2及更高版本上).有关如何使用API​​和 my blog post的介绍,请参阅 MSDN Magazine,以获取从IStream加载PNG并将其转换为HBITMAP的代码示例.