1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/gfx/thebes/gfxWindowsPlatform.h Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,304 @@ 1.4 +/* -*- Mode: C++; tab-width: 20; indent-tabs-mode: nil; c-basic-offset: 4 -*- 1.5 + * This Source Code Form is subject to the terms of the Mozilla Public 1.6 + * License, v. 2.0. If a copy of the MPL was not distributed with this 1.7 + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 1.8 + 1.9 +#ifndef GFX_WINDOWS_PLATFORM_H 1.10 +#define GFX_WINDOWS_PLATFORM_H 1.11 + 1.12 + 1.13 +/** 1.14 + * XXX to get CAIRO_HAS_D2D_SURFACE, CAIRO_HAS_DWRITE_FONT 1.15 + * and cairo_win32_scaled_font_select_font 1.16 + */ 1.17 +#include "cairo-win32.h" 1.18 + 1.19 +#include "gfxFontUtils.h" 1.20 +#include "gfxWindowsSurface.h" 1.21 +#include "gfxFont.h" 1.22 +#ifdef CAIRO_HAS_DWRITE_FONT 1.23 +#include "gfxDWriteFonts.h" 1.24 +#endif 1.25 +#include "gfxPlatform.h" 1.26 +#include "gfxContext.h" 1.27 + 1.28 +#include "nsTArray.h" 1.29 +#include "nsDataHashtable.h" 1.30 + 1.31 +#include "mozilla/RefPtr.h" 1.32 + 1.33 +#include <windows.h> 1.34 +#include <objbase.h> 1.35 + 1.36 +#ifdef CAIRO_HAS_D2D_SURFACE 1.37 +#include <dxgi.h> 1.38 +#endif 1.39 + 1.40 +// This header is available in the June 2010 SDK and in the Win8 SDK 1.41 +#include <d3dcommon.h> 1.42 +// Win 8.0 SDK types we'll need when building using older sdks. 1.43 +#if !defined(D3D_FEATURE_LEVEL_11_1) // defined in the 8.0 SDK only 1.44 +#define D3D_FEATURE_LEVEL_11_1 static_cast<D3D_FEATURE_LEVEL>(0xb100) 1.45 +#define D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION 2048 1.46 +#define D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION 4096 1.47 +#endif 1.48 + 1.49 +namespace mozilla { 1.50 +namespace layers { 1.51 +class DeviceManagerD3D9; 1.52 +} 1.53 +} 1.54 +class IDirect3DDevice9; 1.55 +class ID3D11Device; 1.56 +class IDXGIAdapter1; 1.57 + 1.58 +class nsIMemoryReporter; 1.59 + 1.60 +// Utility to get a Windows HDC from a thebes context, 1.61 +// used by both GDI and Uniscribe font shapers 1.62 +struct DCFromContext { 1.63 + DCFromContext(gfxContext *aContext) { 1.64 + dc = nullptr; 1.65 + nsRefPtr<gfxASurface> aSurface = aContext->CurrentSurface(); 1.66 + NS_ASSERTION(aSurface || !aContext->IsCairo(), "DCFromContext: null surface"); 1.67 + if (aSurface && 1.68 + (aSurface->GetType() == gfxSurfaceType::Win32 || 1.69 + aSurface->GetType() == gfxSurfaceType::Win32Printing)) 1.70 + { 1.71 + dc = static_cast<gfxWindowsSurface*>(aSurface.get())->GetDC(); 1.72 + needsRelease = false; 1.73 + SaveDC(dc); 1.74 + cairo_scaled_font_t* scaled = 1.75 + cairo_get_scaled_font(aContext->GetCairo()); 1.76 + cairo_win32_scaled_font_select_font(scaled, dc); 1.77 + } 1.78 + if (!dc) { 1.79 + dc = GetDC(nullptr); 1.80 + SetGraphicsMode(dc, GM_ADVANCED); 1.81 + needsRelease = true; 1.82 + } 1.83 + } 1.84 + 1.85 + ~DCFromContext() { 1.86 + if (needsRelease) { 1.87 + ReleaseDC(nullptr, dc); 1.88 + } else { 1.89 + RestoreDC(dc, -1); 1.90 + } 1.91 + } 1.92 + 1.93 + operator HDC () { 1.94 + return dc; 1.95 + } 1.96 + 1.97 + HDC dc; 1.98 + bool needsRelease; 1.99 +}; 1.100 + 1.101 +// ClearType parameters set by running ClearType tuner 1.102 +struct ClearTypeParameterInfo { 1.103 + ClearTypeParameterInfo() : 1.104 + gamma(-1), pixelStructure(-1), clearTypeLevel(-1), enhancedContrast(-1) 1.105 + { } 1.106 + 1.107 + nsString displayName; // typically just 'DISPLAY1' 1.108 + int32_t gamma; 1.109 + int32_t pixelStructure; 1.110 + int32_t clearTypeLevel; 1.111 + int32_t enhancedContrast; 1.112 +}; 1.113 + 1.114 +class gfxWindowsPlatform : public gfxPlatform { 1.115 +public: 1.116 + enum TextRenderingMode { 1.117 + TEXT_RENDERING_NO_CLEARTYPE, 1.118 + TEXT_RENDERING_NORMAL, 1.119 + TEXT_RENDERING_GDI_CLASSIC, 1.120 + TEXT_RENDERING_COUNT 1.121 + }; 1.122 + 1.123 + gfxWindowsPlatform(); 1.124 + virtual ~gfxWindowsPlatform(); 1.125 + static gfxWindowsPlatform *GetPlatform() { 1.126 + return (gfxWindowsPlatform*) gfxPlatform::GetPlatform(); 1.127 + } 1.128 + 1.129 + virtual gfxPlatformFontList* CreatePlatformFontList(); 1.130 + 1.131 + virtual already_AddRefed<gfxASurface> 1.132 + CreateOffscreenSurface(const IntSize& size, 1.133 + gfxContentType contentType) MOZ_OVERRIDE; 1.134 + virtual already_AddRefed<gfxASurface> 1.135 + CreateOffscreenImageSurface(const gfxIntSize& aSize, 1.136 + gfxContentType aContentType); 1.137 + 1.138 + virtual mozilla::TemporaryRef<mozilla::gfx::ScaledFont> 1.139 + GetScaledFontForFont(mozilla::gfx::DrawTarget* aTarget, gfxFont *aFont); 1.140 + virtual already_AddRefed<gfxASurface> 1.141 + GetThebesSurfaceForDrawTarget(mozilla::gfx::DrawTarget *aTarget); 1.142 + 1.143 + enum RenderMode { 1.144 + /* Use GDI and windows surfaces */ 1.145 + RENDER_GDI = 0, 1.146 + 1.147 + /* Use 32bpp image surfaces and call StretchDIBits */ 1.148 + RENDER_IMAGE_STRETCH32, 1.149 + 1.150 + /* Use 32bpp image surfaces, and do 32->24 conversion before calling StretchDIBits */ 1.151 + RENDER_IMAGE_STRETCH24, 1.152 + 1.153 + /* Use Direct2D rendering */ 1.154 + RENDER_DIRECT2D, 1.155 + 1.156 + /* max */ 1.157 + RENDER_MODE_MAX 1.158 + }; 1.159 + 1.160 + int GetScreenDepth() const; 1.161 + 1.162 + RenderMode GetRenderMode() { return mRenderMode; } 1.163 + void SetRenderMode(RenderMode rmode) { mRenderMode = rmode; } 1.164 + 1.165 + /** 1.166 + * Updates render mode with relation to the current preferences and 1.167 + * available devices. 1.168 + */ 1.169 + void UpdateRenderMode(); 1.170 + 1.171 + /** 1.172 + * Verifies a D2D device is present and working, will attempt to create one 1.173 + * it is non-functional or non-existant. 1.174 + * 1.175 + * \param aAttemptForce Attempt to force D2D cairo device creation by using 1.176 + * cairo device creation routines. 1.177 + */ 1.178 + void VerifyD2DDevice(bool aAttemptForce); 1.179 + 1.180 +#ifdef CAIRO_HAS_D2D_SURFACE 1.181 + HRESULT CreateDevice(nsRefPtr<IDXGIAdapter1> &adapter1, int featureLevelIndex); 1.182 +#endif 1.183 + 1.184 + /** 1.185 + * Return the resolution scaling factor to convert between "logical" or 1.186 + * "screen" pixels as used by Windows (dependent on the DPI scaling option 1.187 + * in the Display control panel) and actual device pixels. 1.188 + */ 1.189 + double GetDPIScale(); 1.190 + 1.191 + nsresult GetFontList(nsIAtom *aLangGroup, 1.192 + const nsACString& aGenericFamily, 1.193 + nsTArray<nsString>& aListOfFonts); 1.194 + 1.195 + nsresult UpdateFontList(); 1.196 + 1.197 + virtual void GetCommonFallbackFonts(const uint32_t aCh, 1.198 + int32_t aRunScript, 1.199 + nsTArray<const char*>& aFontList); 1.200 + 1.201 + nsresult ResolveFontName(const nsAString& aFontName, 1.202 + FontResolverCallback aCallback, 1.203 + void *aClosure, bool& aAborted); 1.204 + 1.205 + nsresult GetStandardFamilyName(const nsAString& aFontName, nsAString& aFamilyName); 1.206 + 1.207 + gfxFontGroup *CreateFontGroup(const nsAString &aFamilies, 1.208 + const gfxFontStyle *aStyle, 1.209 + gfxUserFontSet *aUserFontSet); 1.210 + 1.211 + /** 1.212 + * Look up a local platform font using the full font face name (needed to support @font-face src local() ) 1.213 + */ 1.214 + virtual gfxFontEntry* LookupLocalFont(const gfxProxyFontEntry *aProxyEntry, 1.215 + const nsAString& aFontName); 1.216 + 1.217 + /** 1.218 + * Activate a platform font (needed to support @font-face src url() ) 1.219 + */ 1.220 + virtual gfxFontEntry* MakePlatformFont(const gfxProxyFontEntry *aProxyEntry, 1.221 + const uint8_t *aFontData, 1.222 + uint32_t aLength); 1.223 + 1.224 + /** 1.225 + * Check whether format is supported on a platform or not (if unclear, returns true) 1.226 + */ 1.227 + virtual bool IsFontFormatSupported(nsIURI *aFontURI, uint32_t aFormatFlags); 1.228 + 1.229 + /* Find a FontFamily/FontEntry object that represents a font on your system given a name */ 1.230 + gfxFontFamily *FindFontFamily(const nsAString& aName); 1.231 + gfxFontEntry *FindFontEntry(const nsAString& aName, const gfxFontStyle& aFontStyle); 1.232 + 1.233 + bool GetPrefFontEntries(const nsCString& aLangGroup, nsTArray<nsRefPtr<gfxFontEntry> > *array); 1.234 + void SetPrefFontEntries(const nsCString& aLangGroup, nsTArray<nsRefPtr<gfxFontEntry> >& array); 1.235 + 1.236 + void ClearPrefFonts() { mPrefFonts.Clear(); } 1.237 + 1.238 + // ClearType is not always enabled even when available (e.g. Windows XP) 1.239 + // if either of these prefs are enabled and apply, use ClearType rendering 1.240 + bool UseClearTypeForDownloadableFonts(); 1.241 + bool UseClearTypeAlways(); 1.242 + 1.243 + static void GetDLLVersion(char16ptr_t aDLLPath, nsAString& aVersion); 1.244 + 1.245 + // returns ClearType tuning information for each display 1.246 + static void GetCleartypeParams(nsTArray<ClearTypeParameterInfo>& aParams); 1.247 + 1.248 + virtual void FontsPrefsChanged(const char *aPref); 1.249 + 1.250 + void SetupClearTypeParams(); 1.251 + 1.252 +#ifdef CAIRO_HAS_DWRITE_FONT 1.253 + IDWriteFactory *GetDWriteFactory() { return mDWriteFactory; } 1.254 + inline bool DWriteEnabled() { return mUseDirectWrite; } 1.255 + inline DWRITE_MEASURING_MODE DWriteMeasuringMode() { return mMeasuringMode; } 1.256 + IDWriteTextAnalyzer *GetDWriteAnalyzer() { return mDWriteAnalyzer; } 1.257 + 1.258 + IDWriteRenderingParams *GetRenderingParams(TextRenderingMode aRenderMode) 1.259 + { return mRenderingParams[aRenderMode]; } 1.260 +#else 1.261 + inline bool DWriteEnabled() { return false; } 1.262 +#endif 1.263 + void OnDeviceManagerDestroy(mozilla::layers::DeviceManagerD3D9* aDeviceManager); 1.264 + mozilla::layers::DeviceManagerD3D9* GetD3D9DeviceManager(); 1.265 + IDirect3DDevice9* GetD3D9Device(); 1.266 +#ifdef CAIRO_HAS_D2D_SURFACE 1.267 + cairo_device_t *GetD2DDevice() { return mD2DDevice; } 1.268 + ID3D10Device1 *GetD3D10Device() { return mD2DDevice ? cairo_d2d_device_get_device(mD2DDevice) : nullptr; } 1.269 +#endif 1.270 + ID3D11Device *GetD3D11Device(); 1.271 + 1.272 + static bool IsOptimus(); 1.273 + 1.274 +protected: 1.275 + RenderMode mRenderMode; 1.276 + 1.277 + int8_t mUseClearTypeForDownloadableFonts; 1.278 + int8_t mUseClearTypeAlways; 1.279 + 1.280 +private: 1.281 + void Init(); 1.282 + IDXGIAdapter1 *GetDXGIAdapter(); 1.283 + 1.284 + bool mUseDirectWrite; 1.285 + bool mUsingGDIFonts; 1.286 + 1.287 +#ifdef CAIRO_HAS_DWRITE_FONT 1.288 + nsRefPtr<IDWriteFactory> mDWriteFactory; 1.289 + nsRefPtr<IDWriteTextAnalyzer> mDWriteAnalyzer; 1.290 + nsRefPtr<IDWriteRenderingParams> mRenderingParams[TEXT_RENDERING_COUNT]; 1.291 + DWRITE_MEASURING_MODE mMeasuringMode; 1.292 +#endif 1.293 +#ifdef CAIRO_HAS_D2D_SURFACE 1.294 + cairo_device_t *mD2DDevice; 1.295 +#endif 1.296 + mozilla::RefPtr<IDXGIAdapter1> mAdapter; 1.297 + nsRefPtr<mozilla::layers::DeviceManagerD3D9> mDeviceManager; 1.298 + mozilla::RefPtr<ID3D11Device> mD3D11Device; 1.299 + bool mD3D11DeviceInitialized; 1.300 + 1.301 + virtual void GetPlatformCMSOutputProfile(void* &mem, size_t &size); 1.302 + 1.303 + // TODO: unify this with mPrefFonts (NB: holds families, not fonts) in gfxPlatformFontList 1.304 + nsDataHashtable<nsCStringHashKey, nsTArray<nsRefPtr<gfxFontEntry> > > mPrefFonts; 1.305 +}; 1.306 + 1.307 +#endif /* GFX_WINDOWS_PLATFORM_H */