GDI+ DrawImage JPG с белым фоном не белый
Я отображаю JPG в C++ CWnd окне, используя GDI+. JPG имеет чистый белый фон, 0xffffff, но при отображении с использованием graphics.DrawImage фон не совсем белый со смесью пиксельных цветов, таких как 0xfff7f7, 0xf7fff7, 0xf7f7f7. Ниже приведен код, я пробовал различные настройки, такие как CompositingMode, SmoothingMode и т. Д. Изображение не масштабируется.
Странно то, что цвет фона отличается в зависимости от другого небелого содержимого изображения. Если я сделаю простой полностью белый JPG, то он сработает, или даже в основном белый с черным текстом. Сравнение изображений приведено ниже.
CClientDC dc(this);
Gdiplus::Graphics graphics(dc);
Gdiplus::Bitmap* bmp = Gdiplus::Bitmap::FromFile( L"c:\\test.jpg" );
graphics.SetInterpolationMode(Gdiplus::InterpolationModeHighQuality);
//graphics.SetCompositingQuality(Gdiplus::CompositingQualityHighQuality);
graphics.SetCompositingQuality(Gdiplus::CompositingQualityDefault);
graphics.SetCompositingMode(Gdiplus::CompositingModeSourceCopy);
//graphics.SetSmoothingMode( Gdiplus::SmoothingMode::SmoothingModeDefault );
graphics.DrawImage(bmp, 0, 0, bmp->GetWidth(), bmp->GetHeight() );
Здесь у меня есть текст и немного смешения только на левой стороне изображения (без альфа, это JPG) . Все справа чисто белое. Вы можете видеть, что фон весь серый.
Здесь я начал удалять внутренний контент (только с левой стороны). После определенного момента весь фон начинает отображаться белым.???
На самом деле не имеет значения, какую часть области изображения я удаляю, прежде чем она начнет отображаться белым, если я удаляю большую ее часть. То же самое происходит с PNG.
Вот оригинальное изображение test.jpg...
2 ответа
Я отвечаю на мой вопрос с решением, которое я нашел. Кажется, что использование graphics.DrawImage непосредственно на переданном HDC имеет некоторые проблемы в моем случае. Если я использую DC памяти для первоначального рисования, затем BitBlt его на HDC, тогда он работает.
У меня также были некоторые проблемы с PNG и прозрачностью. Используя приведенное ниже решение, я смог решить и эту проблему. Мой PNG был загружен из потока с помощью Bitmap::FromStream. Альфа-канал был потерян, и я пробовал разные попытки, используя LockBits и воссоздавая растровое изображение с PixelFormat32bppARGB, а также Cloning. Я смог заставить что-то работать (после долгих усилий и дополнительного кода), но у меня все еще была проблема с серым фоном, которую я задал здесь.
В моем случае у меня есть известный сплошной цвет фона для прозрачных областей. Я использовал Bitmap.GetHBITMAP и передал цвет фона. Затем растровое изображение было нарисовано в памяти DC первым. Здесь я смог решить обе мои проблемы!
Gdiplus::Bitmap* bmp = Gdiplus::Bitmap::FromFile( L"c:\test.jpg" )
Gdiplus::Color backColor( 0xff, 0xff, 0xff );
HBITMAP hBmp;
bmp->GetHBITMAP( backColor, &hBmp );
CDC bitmapDC;
bitmapDC.CreateCompatibleDC(hdc); // pass original HDC for drawing
HBITMAP oldBmp = bitmapDC.SelectBitmap(hBitmap);
::BitBlt( hdc, x, y, cx, cy, bitmapDC.m_hDC, 0, 0, SRCCOPY );
bitmapDC.SelectBitmap(oldBmp);
DeleteObject( hBmp );
Если кто-нибудь знает, мне было бы интересно, почему это решает проблему.
Как вы подтвердили, что фон JPG действительно белый? JPG реализует сжатие, которое может варьировать цвет пикселей. Если есть смешанные цвета, то могут быть определенные типы смешивания и смешивания, которые являются частью этого сжатия.
Можете ли вы показать нам оригинальное изображение?