gdiplus: Use StretchBlt instead of GdiAlphaBlend if device doesn't support alpha blending.

Vincent Povirk madewokherd at gmail.com
Tue Mar 13 13:43:02 CDT 2012


> I tested printing quite a bit of different documents with an application
> I have here and all of them get printed correctly with the patch. Before
> the printed pages were just blank. What do you think is better for a user?

It's not good if things work by coincidence in one case that's
important to you, and then we can't fix other cases later (or we can't
fix other cases without breaking yours).

>> If neither of those things are possible, the best we can do is to do
>> ALL of our drawing through alpha_blend_pixels (by using a GpGraphics
>> without an hdc), compose the result internally, and blit the result
>> with a mask based on the resulting alpha values when GdipFlush or
>> GdipDeleteGraphics is called.
>
> Did you test it under Windows? Does it really do it that way?

I heard a rumor that native draws by reading screen bits and writing
back modified screen bits. This is consistent with what I know about
the GDI+ API (in particular, it seems to be the only way to fully
control gamma correction, which the API allows). I have not made any
attempt to verify this.

Based on the things the GDI+ API allows and the things it doesn't, I
believe it does everything based on its own implementation of
AlphaBlend (except when drawing to a metafile Graphics created using
the GDI+ metafile API's; in those cases I believe it tries harder to
express things in terms of gdi32 operations, even to the point where
it loses things in the translation). In particular, it respects alpha
everywhere, and it doesn't allow things like SRCAND that cannot be
expressed in terms of AlphaBlend. So I believe the best implementation
would be based on AlphaBlend, with "optimizations" for the simple
cases that gdi32 can handle. That prevents us from controlling gamma
correction but otherwise allows us to do everything correctly.

I can't and won't test how native does anything. I will always look
for the most efficient way to do things as well as native can do them.
I'm willing to compromise on gamma correction because doing it
correctly would be a heavy performance hit for something people aren't
likely to notice much.

Until proven otherwise, I have to assume that native can handle the
full range of drawing operations that are possible when drawing to a
screen DC or image, such as filling paths with a partially transparent
color. If you test on Windows (not just with native gdiplus) and find
there are limitations to what GDI+ can print, then I can accept a
method of drawing that has the same limitations.

I would be interested in how rotated images, translucent images
stacked on top of each other, and translucent shapes print on Windows
with GDI+. If you can find some limitations there, then maybe I can
accept a broken alpha_blend_pixels, or some alternate paths for
printer DC's specifically.

I have a program that I use to test GDI+ drawing operations. Maybe it
can help with this.

> PNG (with transparency) and JPEG/BMP images do print with my patch same way
> as they look like under Windows. May be I'm missing something, but IMO it's
> better to print something (and fix any probable problems later) instead of
> printing empty pages.

Have you tried composing transparent PNG images on top of each other?
I don't think that will work with your patch.

Given that alpha_blend_pixels is designed to be the default way to
draw anything, it's not acceptable for it to be so severely broken.



More information about the wine-devel mailing list