summaryrefslogtreecommitdiff
path: root/vcl
diff options
context:
space:
mode:
Diffstat (limited to 'vcl')
-rw-r--r--vcl/inc/skia/win/gdiimpl.hxx3
-rw-r--r--vcl/inc/win/wingdiimpl.hxx3
-rw-r--r--vcl/skia/win/gdiimpl.cxx55
-rw-r--r--vcl/win/gdi/winlayout.cxx6
4 files changed, 65 insertions, 2 deletions
diff --git a/vcl/inc/skia/win/gdiimpl.hxx b/vcl/inc/skia/win/gdiimpl.hxx
index 676e743151e7..3d6c680f2af4 100644
--- a/vcl/inc/skia/win/gdiimpl.hxx
+++ b/vcl/inc/skia/win/gdiimpl.hxx
@@ -73,6 +73,9 @@ public:
virtual bool RenderAndCacheNativeControl(CompatibleDC& rWhite, CompatibleDC& rBlack, int nX,
int nY, ControlCacheKey& aControlCacheKey) override;
+ virtual bool DrawTextLayout(const GenericSalLayout& layout) override;
+ // TODO This method of text drawing can probably be removed once DrawTextLayout()
+ // is fully usable.
virtual bool UseTextDraw() const override { return true; }
virtual void PreDrawText() override;
virtual void PostDrawText() override;
diff --git a/vcl/inc/win/wingdiimpl.hxx b/vcl/inc/win/wingdiimpl.hxx
index 84884220318f..e81e35201413 100644
--- a/vcl/inc/win/wingdiimpl.hxx
+++ b/vcl/inc/win/wingdiimpl.hxx
@@ -35,6 +35,9 @@ public:
abort();
};
+ // Implementation for WinSalGraphics::DrawTextLayout().
+ // Returns true if handled, if false, then WinSalGraphics will handle it itself.
+ virtual bool DrawTextLayout(const GenericSalLayout&) { return false; }
// If true is returned, the following functions are used for text rendering.
virtual bool UseTextDraw() const { return false; }
virtual void PreDrawText() {}
diff --git a/vcl/skia/win/gdiimpl.cxx b/vcl/skia/win/gdiimpl.cxx
index 84aed4f05b92..b7014ed33b48 100644
--- a/vcl/skia/win/gdiimpl.cxx
+++ b/vcl/skia/win/gdiimpl.cxx
@@ -13,12 +13,17 @@
#include <vcl/skia/SkiaHelper.hxx>
#include <skia/utils.hxx>
#include <skia/zone.hxx>
+#include <win/winlayout.hxx>
#include <SkColorFilter.h>
#include <SkPixelRef.h>
+#include <SkTypeface_win.h>
+#include <SkFont.h>
#include <tools/sk_app/win/WindowContextFactory_win.h>
#include <tools/sk_app/WindowContext.h>
+#include <windows.h>
+
WinSkiaSalGraphicsImpl::WinSkiaSalGraphicsImpl(WinSalGraphics& rGraphics,
SalGeometryProvider* mpProvider)
: SkiaSalGraphicsImpl(rGraphics, mpProvider)
@@ -104,6 +109,56 @@ bool WinSkiaSalGraphicsImpl::RenderAndCacheNativeControl(CompatibleDC& rWhite, C
return true;
}
+bool WinSkiaSalGraphicsImpl::DrawTextLayout(const GenericSalLayout& rLayout)
+{
+ const WinFontInstance& rWinFont = static_cast<const WinFontInstance&>(rLayout.GetFont());
+ float fHScale = rWinFont.getHScale();
+
+ assert(dynamic_cast<const WinFontInstance*>(&rLayout.GetFont()));
+ const WinFontInstance* pWinFont = static_cast<const WinFontInstance*>(&rLayout.GetFont());
+ const HFONT hLayoutFont = pWinFont->GetHFONT();
+ LOGFONT logFont;
+ if (::GetObjectW(hLayoutFont, sizeof(logFont), &logFont) == 0)
+ {
+ assert(false);
+ return false;
+ }
+ // Wrap the font in Skia's SkTypeFace subclass that's been patched
+ // to use it.
+ sk_sp<SkTypeface> typeface(SkCreateTypefaceFromLOGFONT(logFont, hLayoutFont));
+ // lfHeight actually depends on DPI, so it's not really font height as such,
+ // but for LOGFONT-based typefaces Skia simply sets lfHeight back to this value
+ // directly.
+ // This is probably not necessary since we pass also the HFONT itself, but better
+ // forward that information too, in case SkFont uses it somehow.
+ double fontHeight = logFont.lfHeight;
+ if (fontHeight < 0)
+ fontHeight = -fontHeight;
+ SkFont font(typeface, fontHeight, fHScale, 0);
+ // Skia needs to be explicitly told what kind of antialiasing should be used,
+ // get it from system settings. This does not actually matter for the text
+ // rendering itself, since it will use the font passed to Skia in the code above
+ // (and that one uses DEFAULT_QUALITY, so Windows will select the appropriate AA setting),
+ // but Skia internally chooses the format to which the glyphs will be rendered
+ // based on this setting (subpixel AA requires colors, others do not).
+ BOOL set;
+ if (SystemParametersInfo(SPI_GETFONTSMOOTHING, 0, &set, 0) && set)
+ {
+ UINT set2;
+ if (SystemParametersInfo(SPI_GETFONTSMOOTHINGTYPE, 0, &set2, 0)
+ && set2 == FE_FONTSMOOTHINGCLEARTYPE)
+ font.setEdging(SkFont::Edging::kSubpixelAntiAlias);
+ else
+ font.setEdging(SkFont::Edging::kAntiAlias);
+ }
+ assert(dynamic_cast<SkiaSalGraphicsImpl*>(mWinParent.GetImpl()));
+ SkiaSalGraphicsImpl* impl = static_cast<SkiaSalGraphicsImpl*>(mWinParent.GetImpl());
+ COLORREF color = ::GetTextColor(mWinParent.getHDC());
+ Color salColor(GetRValue(color), GetGValue(color), GetBValue(color));
+ impl->drawGenericLayout(rLayout, salColor, font);
+ return true;
+}
+
void WinSkiaSalGraphicsImpl::PreDrawText() { preDraw(); }
void WinSkiaSalGraphicsImpl::PostDrawText() { postDraw(); }
diff --git a/vcl/win/gdi/winlayout.cxx b/vcl/win/gdi/winlayout.cxx
index e13d6930df64..636cac595bf1 100644
--- a/vcl/win/gdi/winlayout.cxx
+++ b/vcl/win/gdi/winlayout.cxx
@@ -543,11 +543,13 @@ void WinSalGraphics::DrawTextLayout(const GenericSalLayout& rLayout, HDC hDC, bo
void WinSalGraphics::DrawTextLayout(const GenericSalLayout& rLayout)
{
- HDC hDC = getHDC();
+ WinSalGraphicsImplBase* pImpl = dynamic_cast<WinSalGraphicsImplBase*>(mpImpl.get());
+ if( !mbPrinter && pImpl->DrawTextLayout(rLayout))
+ return; // handled by pImpl
+ HDC hDC = getHDC();
const WinFontInstance* pWinFont = static_cast<const WinFontInstance*>(&rLayout.GetFont());
const HFONT hLayoutFont = pWinFont->GetHFONT();
- WinSalGraphicsImplBase* pImpl = dynamic_cast<WinSalGraphicsImplBase*>(mpImpl.get());
bool bUseClassic = !pImpl->UseTextDraw() || mbPrinter;
// Our DirectWrite renderer is incomplete, skip it for vertical text where glyphs are not