Bug 784382 - Part 2: Use new ID2D1DeviceContext interface in Azure. r=jrmuizel
authorBas Schouten <bschouten@mozilla.com>
Sun, 07 Oct 2012 01:43:16 +0200
changeset 115835 13ec2ee2b44798882ad2e58a0d349b699266688f
parent 115834 d3afcd4f3cc0f29bdf87e57417a3a85c8c801b51
child 115836 ecd4c43042193c599d446d712ac265319b70dc33
push id1708
push userakeybl@mozilla.com
push dateMon, 19 Nov 2012 21:10:21 +0000
treeherdermozilla-beta@27b14fe50103 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersjrmuizel
bugs784382
milestone18.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 784382 - Part 2: Use new ID2D1DeviceContext interface in Azure. r=jrmuizel
gfx/2d/DrawTargetD2D.cpp
gfx/2d/DrawTargetD2D.h
gfx/2d/HelpersD2D.h
gfx/2d/PathD2D.h
gfx/2d/moz-d2d1-1.h
--- a/gfx/2d/DrawTargetD2D.cpp
+++ b/gfx/2d/DrawTargetD2D.cpp
@@ -988,26 +988,17 @@ DrawTargetD2D::PushClip(const Path *aPat
   mPushedClips.push_back(clip);
 
   // The transform of clips is relative to the world matrix, since we use the total
   // transform for the clips, make the world matrix identity.
   mRT->SetTransform(D2D1::IdentityMatrix());
   mTransformDirty = true;
 
   if (mClipsArePushed) {
-    D2D1_LAYER_OPTIONS options = D2D1_LAYER_OPTIONS_NONE;
-
-    if (mFormat == FORMAT_B8G8R8X8) {
-      options = D2D1_LAYER_OPTIONS_INITIALIZE_FOR_CLEARTYPE;
-    }
-
-    mRT->PushLayer(D2D1::LayerParameters(D2D1::InfiniteRect(), pathD2D->mGeometry,
-                                         D2D1_ANTIALIAS_MODE_PER_PRIMITIVE,
-                                         clip.mTransform, 1.0f, nullptr,
-                                         options), clip.mLayer);
+    PushD2DLayer(pathD2D->mGeometry, clip.mLayer, clip.mTransform);
   }
 }
 
 void
 DrawTargetD2D::PushClipRect(const Rect &aRect)
 {
   mCurrentClipMaskTexture = nullptr;
   mCurrentClippedGeometry = nullptr;
@@ -1821,26 +1812,17 @@ DrawTargetD2D::PopAllClips()
 }
 
 void
 DrawTargetD2D::PushClipsToRT(ID2D1RenderTarget *aRT)
 {
   for (std::vector<PushedClip>::iterator iter = mPushedClips.begin();
         iter != mPushedClips.end(); iter++) {
     if (iter->mLayer) {
-      D2D1_LAYER_OPTIONS options = D2D1_LAYER_OPTIONS_NONE;
-
-      if (mFormat == FORMAT_B8G8R8X8) {
-        options = D2D1_LAYER_OPTIONS_INITIALIZE_FOR_CLEARTYPE;
-      }
-
-      aRT->PushLayer(D2D1::LayerParameters(D2D1::InfiniteRect(), iter->mPath->mGeometry,
-                                            D2D1_ANTIALIAS_MODE_PER_PRIMITIVE,
-                                            iter->mTransform, 1.0f, nullptr,
-                                            options), iter->mLayer);
+      PushD2DLayer(iter->mPath->mGeometry, iter->mLayer, iter->mTransform);
     } else {
       aRT->PushAxisAlignedClip(iter->mBounds, iter->mIsPixelAligned ? D2D1_ANTIALIAS_MODE_ALIASED : D2D1_ANTIALIAS_MODE_PER_PRIMITIVE);
     }
   }
 }
 
 void
 DrawTargetD2D::PopClipsFromRT(ID2D1RenderTarget *aRT)
@@ -2713,10 +2695,37 @@ DrawTargetD2D::SetScissorToRect(IntRect 
   } else {
     rect.left = rect.top = INT32_MIN;
     rect.right = rect.bottom = INT32_MAX;
   }
 
   mDevice->RSSetScissorRects(1, &rect);
 }
 
+void
+DrawTargetD2D::PushD2DLayer(ID2D1Geometry *aGeometry, ID2D1Layer *aLayer, const D2D1_MATRIX_3X2_F &aTransform)
+{
+  D2D1_LAYER_OPTIONS options = D2D1_LAYER_OPTIONS_NONE;
+  D2D1_LAYER_OPTIONS1 options1 =  D2D1_LAYER_OPTIONS1_NONE;
+
+  if (mFormat == FORMAT_B8G8R8X8) {
+    options = D2D1_LAYER_OPTIONS_INITIALIZE_FOR_CLEARTYPE;
+    options1 = D2D1_LAYER_OPTIONS1_IGNORE_ALPHA | D2D1_LAYER_OPTIONS1_INITIALIZE_FROM_BACKGROUND;
+  }
+
+	RefPtr<ID2D1DeviceContext> dc;
+	HRESULT hr = mRT->QueryInterface(IID_ID2D1DeviceContext, (void**)((ID2D1DeviceContext**)byRef(dc)));
+
+	if (FAILED(hr)) {
+	    mRT->PushLayer(D2D1::LayerParameters(D2D1::InfiniteRect(), aGeometry,
+				                                   D2D1_ANTIALIAS_MODE_PER_PRIMITIVE, aTransform,
+				                                   1.0, nullptr, options),
+				             aLayer);
+	} else {
+	    dc->PushLayer(D2D1::LayerParameters1(D2D1::InfiniteRect(), aGeometry,
+				                                   D2D1_ANTIALIAS_MODE_PER_PRIMITIVE, aTransform,
+				                                   1.0, nullptr, options1),
+				            aLayer);
+	}
+}
+
 }
 }
--- a/gfx/2d/DrawTargetD2D.h
+++ b/gfx/2d/DrawTargetD2D.h
@@ -206,16 +206,18 @@ private:
 
   void SetupEffectForRadialGradient(const RadialGradientPattern *aPattern);
   void SetupStateForRendering();
 
   // Set the scissor rect to a certain IntRects, resets the scissor rect to
   // surface bounds when NULL is specified.
   void SetScissorToRect(IntRect *aRect);
 
+  void PushD2DLayer(ID2D1Geometry *aGeometry, ID2D1Layer *aLayer, const D2D1_MATRIX_3X2_F &aTransform);
+
   static const uint32_t test = 4;
 
   IntSize mSize;
 
   RefPtr<ID3D10Device1> mDevice;
   RefPtr<ID3D10Texture2D> mTexture;
   RefPtr<ID3D10Texture2D> mCurrentClipMaskTexture;
   RefPtr<ID2D1Geometry> mCurrentClippedGeometry;
--- a/gfx/2d/HelpersD2D.h
+++ b/gfx/2d/HelpersD2D.h
@@ -1,17 +1,18 @@
 /* -*- Mode: C++; tab-width: 20; indent-tabs-mode: nil; c-basic-offset: 2 -*-
  * This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #ifndef MOZILLA_GFX_HELPERSD2D_H_
 #define MOZILLA_GFX_HELPERSD2D_H_
 
-#include <d2d1.h>
+#include "moz-d2d1-1.h"
+
 #include <dwrite.h>
 #include "2D.h"
 
 #include "ScaledFontDWrite.h"
 
 namespace mozilla {
 namespace gfx {
 
--- a/gfx/2d/PathD2D.h
+++ b/gfx/2d/PathD2D.h
@@ -2,17 +2,17 @@
  * This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #ifndef MOZILLA_GFX_PATHD2D_H_
 #define MOZILLA_GFX_PATHD2D_H_
 
 #include "2D.h"
-#include <d2d1.h>
+#include "moz-d2d1-1.h"
 
 namespace mozilla {
 namespace gfx {
 
 class PathD2D;
 
 class PathBuilderD2D : public PathBuilder
 {
new file mode 100644
--- /dev/null
+++ b/gfx/2d/moz-d2d1-1.h
@@ -0,0 +1,367 @@
+//---------------------------------------------------------------------------
+// Copyright (c) Microsoft Corporation.  All rights reserved.
+//
+// This file is automatically generated.  Please do not edit it directly.
+//
+// File name: D2D1_1.h
+//---------------------------------------------------------------------------
+#pragma once
+
+#ifndef _D2D1_1_H_
+#ifndef _D2D1_H_
+#include <d2d1.h>
+#endif // #ifndef _D2D1_H_
+
+//+-----------------------------------------------------------------------------
+//
+//  Flag:
+//      D2D1_LAYER_OPTIONS1
+//
+//  Synopsis:
+//      Specifies how the layer contents should be prepared.
+//
+//------------------------------------------------------------------------------
+typedef enum D2D1_LAYER_OPTIONS1
+{
+        D2D1_LAYER_OPTIONS1_NONE = 0,
+        D2D1_LAYER_OPTIONS1_INITIALIZE_FROM_BACKGROUND = 1,
+        D2D1_LAYER_OPTIONS1_IGNORE_ALPHA = 2,
+        D2D1_LAYER_OPTIONS1_FORCE_DWORD = 0xffffffff
+
+} D2D1_LAYER_OPTIONS1;
+
+//+-----------------------------------------------------------------------------
+//
+//  Struct:
+//      D2D1_LAYER_PARAMETERS1
+//
+//  Synopsis:
+//      All parameters related to pushing a layer.
+//
+//------------------------------------------------------------------------------
+typedef struct D2D1_LAYER_PARAMETERS1
+{
+    D2D1_RECT_F contentBounds;
+    ID2D1Geometry *geometricMask;
+    D2D1_ANTIALIAS_MODE maskAntialiasMode;
+    D2D1_MATRIX_3X2_F maskTransform;
+    FLOAT opacity;
+    ID2D1Brush *opacityBrush;
+    D2D1_LAYER_OPTIONS1 layerOptions;
+
+} D2D1_LAYER_PARAMETERS1;
+
+DEFINE_ENUM_FLAG_OPERATORS(D2D1_LAYER_OPTIONS1);
+
+#ifndef DX_DECLARE_INTERFACE
+#define DX_DECLARE_INTERFACE(x) DECLSPEC_UUID(x) DECLSPEC_NOVTABLE
+#endif
+
+namespace D2D1
+{
+    D2D1FORCEINLINE
+    D2D1_LAYER_PARAMETERS1
+    LayerParameters1(
+        CONST D2D1_RECT_F &contentBounds = D2D1::InfiniteRect(),
+        ID2D1Geometry *geometricMask = NULL,
+        D2D1_ANTIALIAS_MODE maskAntialiasMode = D2D1_ANTIALIAS_MODE_PER_PRIMITIVE,
+        D2D1_MATRIX_3X2_F maskTransform = D2D1::IdentityMatrix(),
+        FLOAT opacity = 1.0,
+        ID2D1Brush *opacityBrush = NULL,
+        D2D1_LAYER_OPTIONS1 layerOptions = D2D1_LAYER_OPTIONS1_NONE
+        )
+    {
+        D2D1_LAYER_PARAMETERS1 layerParameters = { 0 };
+
+        layerParameters.contentBounds = contentBounds;
+        layerParameters.geometricMask = geometricMask;
+        layerParameters.maskAntialiasMode = maskAntialiasMode;
+        layerParameters.maskTransform = maskTransform;
+        layerParameters.opacity = opacity;
+        layerParameters.opacityBrush = opacityBrush;
+        layerParameters.layerOptions = layerOptions;
+
+        return layerParameters;
+    }
+}
+
+DEFINE_GUID(IID_ID2D1DeviceContext, 0xe8f7fe7a, 0x191c, 0x466d, 0xad, 0x95, 0x97, 0x56, 0x78, 0xbd, 0xa9, 0x98);
+
+//+-----------------------------------------------------------------------------
+//
+//  Interface:
+//      ID2D1DeviceContext
+//
+//  Synopsis:
+//      The device context represents a set of state and a command buffer that is used
+//      to render to a target bitmap.
+//
+//------------------------------------------------------------------------------
+interface DX_DECLARE_INTERFACE("e8f7fe7a-191c-466d-ad95-975678bda998") ID2D1DeviceContext  : public ID2D1RenderTarget
+{
+    
+    
+    //
+    // Creates a bitmap with extended bitmap properties, potentially from a block of
+    // memory.
+    //
+    STDMETHOD(CreateBitmap)() PURE;
+    
+    //
+    // Create a D2D bitmap by copying a WIC bitmap.
+    //
+    STDMETHOD(CreateBitmapFromWicBitmap)() PURE;    
+    
+    //
+    // Creates a color context from a color space.  If the space is Custom, the context
+    // is initialized from the profile/profileSize arguments.  Otherwise the context is
+    // initialized with the profile bytes associated with the space and
+    // profile/profileSize are ignored.
+    //
+    STDMETHOD(CreateColorContext)() PURE;
+    
+    STDMETHOD(CreateColorContextFromFilename)() PURE;
+    
+    STDMETHOD(CreateColorContextFromWicColorContext)() PURE;
+    
+    
+    //
+    // Creates a bitmap from a DXGI surface with a set of extended properties.
+    //
+    STDMETHOD(CreateBitmapFromDxgiSurface)() PURE;
+    
+    
+    //
+    // Create a new effect, the effect must either be built in or previously registered
+    // through ID2D1Factory1::RegisterEffectFromStream or
+    // ID2D1Factory1::RegisterEffectFromString.
+    //
+    STDMETHOD(CreateEffect)() PURE;
+    
+    
+    //
+    // A gradient stop collection represents a set of stops in an ideal unit length.
+    // This is the source resource for a linear gradient and radial gradient brush.
+    //
+    STDMETHOD(CreateGradientStopCollection)() PURE;
+    
+    //
+    // Creates an image brush, the input image can be any type of image, including a
+    // bitmap, effect and a command list.
+    //
+    STDMETHOD(CreateImageBrush)() PURE;
+    
+    STDMETHOD(CreateBitmapBrush)() PURE;
+
+    //
+    // Creates a new command list.
+    //
+    STDMETHOD(CreateCommandList)() PURE;
+    
+    
+    //
+    // Indicates whether the format is supported by D2D.
+    //
+    STDMETHOD_(BOOL, IsDxgiFormatSupported)() CONST PURE;
+    
+    
+    //
+    // Indicates whether the buffer precision is supported by D2D.
+    //
+    STDMETHOD_(BOOL, IsBufferPrecisionSupported)() CONST PURE;
+    
+    
+    //
+    // This retrieves the local-space bounds in DIPs of the current image using the
+    // device context DPI.
+    //
+    STDMETHOD(GetImageLocalBounds)() CONST PURE;
+    
+    
+    //
+    // This retrieves the world-space bounds in DIPs of the current image using the
+    // device context DPI.
+    //
+    STDMETHOD(GetImageWorldBounds)() CONST PURE;
+    
+    
+    //
+    // Retrieves the world-space bounds in DIPs of the glyph run using the device
+    // context DPI.
+    //
+    STDMETHOD(GetGlyphRunWorldBounds)() CONST PURE;
+    
+    
+    //
+    // Retrieves the device associated with this device context.
+    //
+    STDMETHOD_(void, GetDevice)() CONST PURE;
+    
+    
+    //
+    // Sets the target for this device context to point to the given image. The image
+    // can be a command list or a bitmap created with the D2D1_BITMAP_OPTIONS_TARGET
+    // flag.
+    //
+    STDMETHOD_(void, SetTarget)() PURE;
+    
+    
+    //
+    // Gets the target that this device context is currently pointing to.
+    //
+    STDMETHOD_(void, GetTarget)() CONST PURE;
+    
+    
+    //
+    // Sets tuning parameters for internal rendering inside the device context.
+    //
+    STDMETHOD_(void, SetRenderingControls)() PURE;
+    
+    
+    //
+    // This retrieves the rendering controls currently selected into the device
+    // context.
+    //
+    STDMETHOD_(void, GetRenderingControls)() CONST PURE;
+    
+    
+    //
+    // Changes the primitive blending mode for all of the rendering operations.
+    //
+    STDMETHOD_(void, SetPrimitiveBlend)() PURE;
+    
+    
+    //
+    // Returns the primitive blend currently selected into the device context.
+    //
+    STDMETHOD_(void, GetPrimitiveBlend)(
+        ) CONST PURE;
+    
+    
+    //
+    // Changes the units used for all of the rendering operations.
+    //
+    STDMETHOD_(void, SetUnitMode)() PURE;
+    
+    
+    //
+    // Returns the unit mode currently set on the device context.
+    //
+    STDMETHOD_(void, GetUnitMode)(
+        ) CONST PURE;
+    
+    
+    //
+    // Draws the glyph run with an extended description to describe the glyphs.
+    //
+    STDMETHOD_(void, DrawGlyphRun)() PURE;
+    
+    //
+    // Draw an image to the device context. The image represents either a concrete
+    // bitmap or the output of an effect graph.
+    //
+    STDMETHOD_(void, DrawImage)() PURE;
+    
+    
+    //
+    // Draw a metafile to the device context.
+    //
+    STDMETHOD_(void, DrawGdiMetafile)() PURE;
+    
+    STDMETHOD_(void, DrawBitmap)() PURE;
+    
+    
+    //
+    // Push a layer on the device context.
+    //
+    STDMETHOD_(void, PushLayer)(
+        _In_ CONST D2D1_LAYER_PARAMETERS1 *layerParameters,
+        _In_opt_ ID2D1Layer *layer 
+        ) PURE;
+    
+    using ID2D1RenderTarget::PushLayer;
+    
+    
+    //
+    // This indicates that a portion of an effect's input is invalid. This method can
+    // be called many times.
+    //
+    STDMETHOD(InvalidateEffectInputRectangle)() PURE;
+    
+    
+    //
+    // Gets the number of invalid ouptut rectangles that have accumulated at the
+    // effect.
+    //
+    STDMETHOD(GetEffectInvalidRectangleCount)() PURE;
+    
+    
+    //
+    // Gets the invalid rectangles that are at the output of the effect.
+    //
+    STDMETHOD(GetEffectInvalidRectangles)() PURE;
+    
+    
+    //
+    // Gets the maximum region of each specified input which would be used during a
+    // subsequent rendering operation
+    //
+    STDMETHOD(GetEffectRequiredInputRectangles)() PURE;
+    
+    
+    //
+    // Fill using the alpha channel of the supplied opacity mask bitmap. The brush
+    // opacity will be modulated by the mask. The render target antialiasing mode must
+    // be set to aliased.
+    //
+    STDMETHOD_(void, FillOpacityMask)() PURE;
+    
+ 
+    HRESULT CreateBitmap1() { return S_OK; }
+    HRESULT CreateBitmap2() { return S_OK; }
+    HRESULT CreateBitmap3() { return S_OK; }
+    HRESULT CreateBitmap4() { return S_OK; }
+    
+    HRESULT CreateImageBrush1() { return S_OK; }
+    HRESULT CreateImageBrush2() { return S_OK; }
+    
+    HRESULT CreateBitmapBrush1() { return S_OK; }
+    HRESULT CreateBitmapBrush2() { return S_OK; }
+    HRESULT CreateBitmapBrush3() { return S_OK; }
+
+    //
+    // Draws the output of the effect as an image.
+    //
+    void DrawImage1() {}
+    void DrawImage2() {}
+    void DrawImage3() {}
+    void DrawImage4() {}
+    void DrawImage5() {}
+    void DrawImage6() {}
+    void DrawImage7() {}
+    
+    void
+    PushLayer(
+        CONST D2D1_LAYER_PARAMETERS1 &layerParameters,
+        _In_opt_ ID2D1Layer *layer 
+        )  
+    {
+        PushLayer(&layerParameters, layer);
+    }
+    
+    void DrawGdiMetafile1() {}
+    
+    void DrawBitmap1() {}
+    void DrawBitmap2() {}
+    void DrawBitmap3() {}
+    
+    void FillOpacityMask1() {}
+    void FillOpacityMask2() {}   
+    
+    //
+    // Sets tuning parameters for internal rendering inside the device context.
+    //
+    void SetRenderingControls1() {}
+}; // interface ID2D1DeviceContext
+
+#endif // #ifndef _D2D1_1_H_