我无法将GDI + Graphics对象(从设备上下文HDC派生)保存到文件中。
什么有用:我我能够保存从Bitmap派生的GDI +图形。示例代码(Win32):
Color color(255, 0, 0);
Pen pen(color, 2.0f);
CLSID pngClsid;
if(GetEncoderClsid(L"image/bmp", &pngClsid) < 0) // calls GetImageEncoders()
return;
// Graphics from Bitmap - works OK
Bitmap bitmap(300, 300, PixelFormat24bppRGB); // create Bitmap first
Graphics *graphics = new Graphics(&bitmap); // create Graphics second
graphics->Clear(Color(255, 255, 255, 255));
Status stat = graphics->DrawEllipse(&pen, 50, 50, 100, 100);
assert(stat == Ok);
stat = bitmap.Save(L"C:\\temp\\test1.bmp", &pngClsid, NULL);
assert(stat == Ok);
delete graphics;
结果:
失败的原因:如果Graphics对象是从HDC派生的,我会得到一个黑色矩形。无论我是在点[1],[2]还是[3]创建位图,我总是得到一个黑色矩形。代码:
CLSID pngClsid;
if(GetEncoderClsid(L"image/bmp", &pngClsid) < 0) // calls GetImageEncoders()
return;
// Graphics from HDC - fails
HDC hdc = GetDC(NULL);
Graphics *graphicsDC = new Graphics(hdc); // create Graphics first
graphicsDC->SetPageUnit(UnitPixel);
//Bitmap bitmapDC(300, 300, graphicsDC); // [1] create Bitmap second. Black rectangle if called here
graphicsDC->Clear(Color(255, 255, 255, 255));
//Bitmap bitmapDC(300, 300, graphicsDC); // [2] black rectangle if called here
HPEN penGDI = CreatePen(PS_SOLID, 3, RGB(0, 255, 0)); // old school GDI
HPEN oldPen = (HPEN)SelectObject(hdc, penGDI);
Ellipse(hdc, 50, 50, 150, 150);
DeleteObject(SelectObject(hdc, oldPen));
Bitmap bitmapDC(300, 300, graphicsDC); // [3] black rectangle if called here
Status stat = bitmapDC.Save(L"C:\\temp\\test2.bmp", &pngClsid, NULL);
assert(stat == Ok);
delete graphicsDC;
ReleaseDC(NULL, hdc);
结果:
为什么我需要这个:我正在将包含数千次调用的代码转换为GDI API。我想逐渐开始使用GDI +,而不是立即将所有GDI调用转换为GDI +。我在其他情况下成功地混合了GDI / GDI +,例如在创建渐变时。唯一的区别是,在其他情况下,我并没有尝试保存到文件中。
我无法使用CImage
,因为它没有常规的抗锯齿功能。
那么,如何从HDC开始时将图形保存为图像?