Bug 1303570 - Part 1: Support Subpixel AA drawing of DWrite fonts to transparent GDI surfaces. r=jrmuizel
MozReview-Commit-ID: JzkE1s9A0UI
--- a/gfx/cairo/cairo/src/cairo-dwrite-font.cpp
+++ b/gfx/cairo/cairo/src/cairo-dwrite-font.cpp
@@ -1136,18 +1136,27 @@ cairo_int_status_t
cairo_dwrite_scaled_font_t *scaled_font,
const RECT &area)
{
IDWriteGdiInterop *gdiInterop;
DWriteFactory::Instance()->GetGdiInterop(&gdiInterop);
IDWriteBitmapRenderTarget *rt;
HRESULT rv;
+ cairo_d2d_surface_t::TextRenderingState renderingState =
+ scaled_font->rendering_mode;
+
+ if ((renderingState == cairo_d2d_surface_t::TEXT_RENDERING_NORMAL ||
+ renderingState == cairo_d2d_surface_t::TEXT_RENDERING_GDI_CLASSIC) &&
+ !surface->base.permit_subpixel_antialiasing) {
+ renderingState = cairo_d2d_surface_t::TEXT_RENDERING_NO_CLEARTYPE;
+ }
+
IDWriteRenderingParams *params =
- DWriteFactory::RenderingParams(scaled_font->rendering_mode);
+ DWriteFactory::RenderingParams(renderingState);
rv = gdiInterop->CreateBitmapRenderTarget(surface->dc,
area.right - area.left,
area.bottom - area.top,
&rt);
if (FAILED(rv)) {
if (rv == E_OUTOFMEMORY) {
return (cairo_int_status_t)CAIRO_STATUS_NO_MEMORY;
@@ -1169,17 +1178,17 @@ cairo_int_status_t
}
BitBlt(rt->GetMemoryDC(),
0, 0,
area.right - area.left, area.bottom - area.top,
surface->dc,
area.left, area.top,
SRCCOPY | NOMIRRORBITMAP);
DWRITE_MEASURING_MODE measureMode;
- switch (scaled_font->rendering_mode) {
+ switch (renderingState) {
case cairo_d2d_surface_t::TEXT_RENDERING_GDI_CLASSIC:
case cairo_d2d_surface_t::TEXT_RENDERING_NO_CLEARTYPE:
measureMode = DWRITE_MEASURING_MODE_GDI_CLASSIC;
break;
default:
measureMode = DWRITE_MEASURING_MODE_NATURAL;
break;
}
@@ -1272,18 +1281,17 @@ cairo_int_status_t
return CAIRO_INT_STATUS_UNSUPPORTED;
/* We can only handle opaque solid color sources */
if (!_cairo_pattern_is_opaque_solid(source))
return CAIRO_INT_STATUS_UNSUPPORTED;
/* We can only handle operator SOURCE or OVER with the destination
* having no alpha */
- if ((op != CAIRO_OPERATOR_SOURCE && op != CAIRO_OPERATOR_OVER) ||
- (dst->format != CAIRO_FORMAT_RGB24))
+ if (op != CAIRO_OPERATOR_SOURCE && op != CAIRO_OPERATOR_OVER)
return CAIRO_INT_STATUS_UNSUPPORTED;
/* If we have a fallback mask clip set on the dst, we have
* to go through the fallback path */
if (clip != NULL) {
if ((dst->flags & CAIRO_WIN32_SURFACE_FOR_PRINTING) == 0) {
cairo_region_t *clip_region;
cairo_int_status_t status;