Bug 764125; sort out preferred and fallback Azure backends for all platforms (gfxPlatform). r=Bas

This commit is contained in:
Nicholas Cameron 2012-07-25 12:45:58 +12:00
parent 8cef9af43a
commit 97d6423dfa
13 changed files with 136 additions and 78 deletions

View File

@ -38,7 +38,7 @@ enum SurfaceFormat
enum BackendType
{
BACKEND_NONE,
BACKEND_NONE = 0,
BACKEND_DIRECT2D,
BACKEND_COREGRAPHICS,
BACKEND_CAIRO,

View File

@ -484,8 +484,11 @@ TemporaryRef<DrawTarget>
LayerManagerD3D10::CreateDrawTarget(const IntSize &aSize,
SurfaceFormat aFormat)
{
BackendType backend;
if ((aFormat != FORMAT_B8G8R8A8 &&
aFormat != FORMAT_B8G8R8X8)) {
aFormat != FORMAT_B8G8R8X8) ||
!gfxPlatform::GetPlatform()->SupportsAzure(backend) ||
backend != BACKEND_DIRECT2D) {
return LayerManager::CreateDrawTarget(aSize, aFormat);
}

View File

@ -33,8 +33,6 @@ public:
CreateOffscreenSurface(const gfxIntSize& size,
gfxASurface::gfxContentType contentType);
virtual bool SupportsAzure(mozilla::gfx::BackendType& aBackend) { aBackend = mozilla::gfx::BACKEND_SKIA; return true; }
virtual gfxImageFormat GetOffscreenFormat() { return mOffscreenFormat; }
mozilla::RefPtr<mozilla::gfx::ScaledFont>

View File

@ -48,6 +48,7 @@
#include "nsTArray.h"
#include "nsUnicharUtilCIID.h"
#include "nsILocaleService.h"
#include "nsReadableUtils.h"
#include "nsWeakReference.h"
@ -75,6 +76,7 @@ using namespace mozilla::layers;
gfxPlatform *gPlatform = nsnull;
static bool gEverInitialized = false;
static nsTArray<nsCString>* gBackendList = nsnull;
// These two may point to the same profile
static qcms_profile *gCMSOutputProfile = nsnull;
@ -223,11 +225,8 @@ gfxPlatform::gfxPlatform()
#endif
mBidiNumeralOption = UNINITIALIZED_VALUE;
if (Preferences::GetBool("gfx.canvas.azure.prefer-skia", false)) {
mPreferredDrawTargetBackend = BACKEND_SKIA;
} else {
mPreferredDrawTargetBackend = BACKEND_NONE;
}
PRUint32 backendMask = (1 << BACKEND_CAIRO) | (1 << BACKEND_SKIA);
InitCanvasBackend(backendMask);
}
gfxPlatform*
@ -407,6 +406,9 @@ gfxPlatform::Shutdown()
CompositorParent::ShutDown();
delete gBackendList;
gBackendList = nsnull;
delete gPlatform;
gPlatform = nsnull;
}
@ -669,7 +671,7 @@ gfxPlatform::GetThebesSurfaceForDrawTarget(DrawTarget *aTarget)
}
RefPtr<DrawTarget>
gfxPlatform::CreateOffscreenDrawTarget(const IntSize& aSize, SurfaceFormat aFormat)
gfxPlatform::CreateDrawTargetForBackend(BackendType aBackend, const IntSize& aSize, SurfaceFormat aFormat)
{
BackendType backend;
if (!SupportsAzure(backend)) {
@ -684,7 +686,7 @@ gfxPlatform::CreateOffscreenDrawTarget(const IntSize& aSize, SurfaceFormat aForm
// now, but this might need to change in the future (using
// CreateOffscreenSurface() and CreateDrawTargetForSurface() for all
// backends).
if (backend == BACKEND_CAIRO) {
if (aBackend == BACKEND_CAIRO) {
nsRefPtr<gfxASurface> surf = CreateOffscreenSurface(ThebesIntSize(aSize),
ContentForFormat(aFormat));
if (!surf) {
@ -693,10 +695,28 @@ gfxPlatform::CreateOffscreenDrawTarget(const IntSize& aSize, SurfaceFormat aForm
return CreateDrawTargetForSurface(surf, aSize);
} else {
return Factory::CreateDrawTarget(backend, aSize, aFormat);
return Factory::CreateDrawTarget(aBackend, aSize, aFormat);
}
}
RefPtr<DrawTarget>
gfxPlatform::CreateOffscreenDrawTarget(const IntSize& aSize, SurfaceFormat aFormat)
{
BackendType backend;
if (!SupportsAzure(backend)) {
return NULL;
}
RefPtr<DrawTarget> target = CreateDrawTargetForBackend(backend, aSize, aFormat);
if (target ||
mFallbackCanvasBackend == BACKEND_NONE) {
return target;
}
return CreateDrawTargetForBackend(mFallbackCanvasBackend, aSize, aFormat);
}
RefPtr<DrawTarget>
gfxPlatform::CreateDrawTargetForData(unsigned char* aData, const IntSize& aSize, int32_t aStride, SurfaceFormat aFormat)
{
@ -707,6 +727,31 @@ gfxPlatform::CreateDrawTargetForData(unsigned char* aData, const IntSize& aSize,
return Factory::CreateDrawTargetForData(backend, aData, aSize, aStride, aFormat);
}
bool
gfxPlatform::SupportsAzure(BackendType& aBackend)
{
if (mPreferredCanvasBackend != BACKEND_NONE) {
aBackend = mPreferredCanvasBackend;
return true;
}
return false;
}
/* static */ BackendType
gfxPlatform::BackendTypeForName(const nsCString& aName)
{
if (aName.EqualsLiteral("cairo"))
return BACKEND_CAIRO;
if (aName.EqualsLiteral("skia"))
return BACKEND_SKIA;
if (aName.EqualsLiteral("direct2d"))
return BACKEND_DIRECT2D;
if (aName.EqualsLiteral("cg"))
return BACKEND_COREGRAPHICS;
return BACKEND_NONE;
}
nsresult
gfxPlatform::GetFontList(nsIAtom *aLangGroup,
const nsACString& aGenericFamily,
@ -1127,20 +1172,47 @@ gfxPlatform::AppendPrefLang(eFontPrefLang aPrefLangs[], PRUint32& aLen, eFontPre
}
}
void
gfxPlatform::InitCanvasBackend(PRUint32 aBackendBitmask)
{
mPreferredCanvasBackend = GetCanvasBackendPref(aBackendBitmask);
mFallbackCanvasBackend = GetCanvasBackendPref(aBackendBitmask & ~(1 << mPreferredCanvasBackend));
}
/* static */ BackendType
gfxPlatform::GetCanvasBackendPref(PRUint32 aBackendBitmask)
{
if (!gBackendList) {
gBackendList = new nsTArray<nsCString>();
nsCString prefString;
if (NS_SUCCEEDED(Preferences::GetCString("gfx.canvas.azure.backends", &prefString))) {
ParseString(prefString, ',', *gBackendList);
}
}
for (PRUint32 i = 0; i < gBackendList->Length(); ++i) {
BackendType result = BackendTypeForName((*gBackendList)[i]);
if ((1 << result) & aBackendBitmask) {
return result;
}
}
return BACKEND_NONE;
}
bool
gfxPlatform::UseProgressiveTilePainting()
{
static bool sUseProgressiveTilePainting;
static bool sUseProgressiveTilePaintingPrefCached = false;
static bool sUseProgressiveTilePainting;
static bool sUseProgressiveTilePaintingPrefCached = false;
if (!sUseProgressiveTilePaintingPrefCached) {
sUseProgressiveTilePaintingPrefCached = true;
mozilla::Preferences::AddBoolVarCache(&sUseProgressiveTilePainting,
"layers.progressive-paint",
false);
}
if (!sUseProgressiveTilePaintingPrefCached) {
sUseProgressiveTilePaintingPrefCached = true;
mozilla::Preferences::AddBoolVarCache(&sUseProgressiveTilePainting,
"layers.progressive-paint",
false);
}
return sUseProgressiveTilePainting;
return sUseProgressiveTilePainting;
}
bool

View File

@ -195,8 +195,10 @@ public:
CreateDrawTargetForData(unsigned char* aData, const mozilla::gfx::IntSize& aSize,
int32_t aStride, mozilla::gfx::SurfaceFormat aFormat);
virtual bool SupportsAzure(mozilla::gfx::BackendType& aBackend) { return false; }
// aBackend will be set to the preferred backend for Azure canvas
bool SupportsAzure(mozilla::gfx::BackendType& aBackend);
// aObj will contain the preferred backend for Azure canvas
void GetAzureBackendInfo(mozilla::widget::InfoObject &aObj) {
mozilla::gfx::BackendType backend;
if (SupportsAzure(backend)) {
@ -455,7 +457,30 @@ protected:
void AppendCJKPrefLangs(eFontPrefLang aPrefLangs[], PRUint32 &aLen,
eFontPrefLang aCharLang, eFontPrefLang aPageLang);
/**
* Helper method, creates a draw target for a specific Azure backend.
* Used by CreateOffscreenDrawTarget.
*/
mozilla::RefPtr<mozilla::gfx::DrawTarget>
CreateDrawTargetForBackend(mozilla::gfx::BackendType aBackend,
const mozilla::gfx::IntSize& aSize,
mozilla::gfx::SurfaceFormat aFormat);
/**
* Initialise the preferred and fallback canvas backends
* aBackendBitmask specifies the backends which are acceptable to the caller.
* The backend used is determined by aBackendBitmask and the order specified
* by the gfx.canvas.azure.backends pref.
*/
void InitCanvasBackend(PRUint32 aBackendBitmask);
/**
* returns the first backend named in the pref gfx.canvas.azure.backends
* which is a component of aBackendBitmask, a bitmask of backend types
*/
static mozilla::gfx::BackendType GetCanvasBackendPref(PRUint32 aBackendBitmask);
static mozilla::gfx::BackendType BackendTypeForName(const nsCString& aName);
PRInt8 mAllowDownloadableFonts;
PRInt8 mDownloadableFontsSanitize;
#ifdef MOZ_GRAPHITE
@ -471,8 +496,10 @@ protected:
// which scripts should be shaped with harfbuzz
PRInt32 mUseHarfBuzzScripts;
// The preferred draw target backend to use
mozilla::gfx::BackendType mPreferredDrawTargetBackend;
// The preferred draw target backend to use for canvas
mozilla::gfx::BackendType mPreferredCanvasBackend;
// The fallback draw target backend to use for canvas, if the preferred backend fails
mozilla::gfx::BackendType mFallbackCanvasBackend;
private:
/**

View File

@ -743,11 +743,3 @@ gfxPlatformGtk::GetScaledFontForFont(DrawTarget* aTarget, gfxFont *aFont)
nativeFont.mFont = static_cast<gfxFT2FontBase*>(aFont)->GetFontOptions();
return Factory::CreateScaledFontForNativeFont(nativeFont, aFont->GetAdjustedSize());
}
bool
gfxPlatformGtk::SupportsAzure(BackendType& aBackend)
{
aBackend = BACKEND_SKIA;
return true;
}

View File

@ -38,8 +38,6 @@ public:
mozilla::RefPtr<mozilla::gfx::ScaledFont>
GetScaledFontForFont(mozilla::gfx::DrawTarget* aTarget, gfxFont *aFont);
virtual bool SupportsAzure(mozilla::gfx::BackendType& aBackend);
nsresult GetFontList(nsIAtom *aLangGroup,
const nsACString& aGenericFamily,
nsTArray<nsString>& aListOfFonts);

View File

@ -69,6 +69,9 @@ gfxPlatformMac::gfxPlatformMac()
DisableFontActivation();
}
mFontAntiAliasingThreshold = ReadAntiAliasingThreshold();
PRUint32 backendMask = (1 << BACKEND_CAIRO) | (1 << BACKEND_SKIA) | (1 << BACKEND_COREGRAPHICS);
InitCanvasBackend(backendMask);
}
gfxPlatformMac::~gfxPlatformMac()
@ -139,18 +142,6 @@ gfxPlatformMac::GetScaledFontForFont(DrawTarget* aTarget, gfxFont *aFont)
return font->GetScaledFont();
}
bool
gfxPlatformMac::SupportsAzure(BackendType& aBackend)
{
if (mPreferredDrawTargetBackend != BACKEND_NONE) {
aBackend = mPreferredDrawTargetBackend;
} else {
aBackend = BACKEND_COREGRAPHICS;
}
return true;
}
nsresult
gfxPlatformMac::ResolveFontName(const nsAString& aFontName,
FontResolverCallback aCallback,

View File

@ -41,8 +41,6 @@ public:
mozilla::RefPtr<mozilla::gfx::ScaledFont>
GetScaledFontForFont(mozilla::gfx::DrawTarget* aTarget, gfxFont *aFont);
virtual bool SupportsAzure(mozilla::gfx::BackendType& aBackend);
nsresult ResolveFontName(const nsAString& aFontName,
FontResolverCallback aCallback,
void *aClosure, bool& aAborted);

View File

@ -606,10 +606,3 @@ gfxQtPlatform::GetOffscreenFormat()
return sOffscreenFormat;
}
bool
gfxQtPlatform::SupportsAzure(BackendType& aBackend)
{
aBackend = BACKEND_SKIA;
return true;
}

View File

@ -47,8 +47,6 @@ public:
already_AddRefed<gfxASurface> CreateOffscreenSurface(const gfxIntSize& size,
gfxASurface::gfxContentType contentType);
virtual bool SupportsAzure(mozilla::gfx::BackendType& aBackend);
nsresult GetFontList(nsIAtom *aLangGroup,
const nsACString& aGenericFamily,
nsTArray<nsString>& aListOfFonts);

View File

@ -515,6 +515,14 @@ gfxWindowsPlatform::UpdateRenderMode()
}
}
#endif
PRUint32 backendMask = 1 << BACKEND_CAIRO;
if (mRenderMode == RENDER_DIRECT2D) {
backendMask |= 1 << BACKEND_DIRECT2D;
} else {
backendMask |= 1 << BACKEND_SKIA;
}
InitCanvasBackend(backendMask);
}
void
@ -841,24 +849,6 @@ gfxWindowsPlatform::GetThebesSurfaceForDrawTarget(DrawTarget *aTarget)
return gfxPlatform::GetThebesSurfaceForDrawTarget(aTarget);
}
bool
gfxWindowsPlatform::SupportsAzure(BackendType& aBackend)
{
#ifdef CAIRO_HAS_D2D_SURFACE
if (mRenderMode == RENDER_DIRECT2D) {
aBackend = BACKEND_DIRECT2D;
return true;
}
#endif
if (mPreferredDrawTargetBackend != BACKEND_NONE) {
aBackend = mPreferredDrawTargetBackend;
return true;
}
return false;
}
nsresult
gfxWindowsPlatform::GetFontList(nsIAtom *aLangGroup,
const nsACString& aGenericFamily,

View File

@ -111,8 +111,6 @@ public:
GetScaledFontForFont(mozilla::gfx::DrawTarget* aTarget, gfxFont *aFont);
virtual already_AddRefed<gfxASurface>
GetThebesSurfaceForDrawTarget(mozilla::gfx::DrawTarget *aTarget);
virtual bool SupportsAzure(mozilla::gfx::BackendType& aBackend);
enum RenderMode {
/* Use GDI and windows surfaces */