Title: [136755] trunk
Revision
136755
Author
[email protected]
Date
2012-12-05 13:40:26 -0800 (Wed, 05 Dec 2012)

Log Message

[skia] Improve performance of GraphicsContext::createCompatibleBuffer by using SkDevice:createCompatibleDevice
https://bugs.webkit.org/show_bug.cgi?id=103896

Reviewed by Stephen White.

Source/WebCore:

Refactored GraphicsContext::createCompatibleBuffer (platform common
code) to use platform-specific implementations provided by ImageBuffer.
There is no change in behavior for non-skia ports. The skia
implementation uses skia'a own createCompatibleDevice implementation,
which offers several performance benefits:
1. For accelerated contexts, the backing store may be allocated from
the scratch texture pool, which minimizes texture allocation and
deallocation overhead.
2. The backing store will not be initially cleared if it is known
in advance that fully opaque contents will be drawn into the buffer.
3. For non-accelerated contexts, if the backing store is flagged as
opaque, faster blitter loop implementations will be used for drawing
the buffer contents into other buffers. (e.g. generated opaque gradient
fills)

No new tests: covered by existing layout tests

* platform/graphics/Generator.h:
(Generator):
Added hasAlpha method so that it can be used by GeneratorGeneratedImage
* platform/graphics/GeneratorGeneratedImage.cpp:
(WebCore::GeneratorGeneratedImage::drawPattern):
Passing m_generator->hasAlpha() to createCompatibleBuffer in order to
take advantage of optimizations that apply to opaque buffers.
* platform/graphics/Gradient.h:
(Gradient):
Made hasAlpha virtual so that it now overrides Generator::hasAlpha
* platform/graphics/GraphicsContext.cpp:
(WebCore::GraphicsContext::createCompatibleBuffer):
Refactored to use platform-specific implementation
* platform/graphics/GraphicsContext.h:
* platform/graphics/ImageBuffer.cpp:
(WebCore::createCompatibleBuffer):
Non-skia implementation. Mimics old
GraphicsContext::createCompatibleBuffer
* platform/graphics/ImageBuffer.h:
(ImageBuffer):
New skia-specific constructor
* platform/graphics/skia/ImageBufferSkia.cpp:
(WebCore::ImageBuffer::createCompatibleBuffer):
(WebCore::ImageBuffer::ImageBuffer):
* platform/graphics/skia/PlatformContextSkia.cpp:
(WebCore::PlatformContextSkia::createCompatibleDevice):
(WebCore):
* platform/graphics/skia/PlatformContextSkia.h:
(PlatformContextSkia):

LayoutTests:

Added image failure expectation for test needing new baselines

* platform/chromium/TestExpectations:

Modified Paths

Diff

Modified: trunk/LayoutTests/ChangeLog (136754 => 136755)


--- trunk/LayoutTests/ChangeLog	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/LayoutTests/ChangeLog	2012-12-05 21:40:26 UTC (rev 136755)
@@ -1,3 +1,14 @@
+2012-12-05  Justin Novosad  <[email protected]>
+
+        [skia] Improve performance of GraphicsContext::createCompatibleBuffer by using SkDevice:createCompatibleDevice
+        https://bugs.webkit.org/show_bug.cgi?id=103896
+
+        Reviewed by Stephen White.
+
+        Added image failure expectation for test needing new baselines
+
+        * platform/chromium/TestExpectations:
+
 2012-12-05  Stephen White  <[email protected]>
 
         [Chromium] Unreviewed gardening.

Modified: trunk/LayoutTests/platform/chromium/TestExpectations (136754 => 136755)


--- trunk/LayoutTests/platform/chromium/TestExpectations	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/LayoutTests/platform/chromium/TestExpectations	2012-12-05 21:40:26 UTC (rev 136755)
@@ -2188,6 +2188,9 @@
 
 crbug.com/43890 [ Win ] http/tests/loading/basic.html [ Failure Pass ]
 
+# Test requires ne baseline after fixing webkit.org/b/103896
+webkit.org/b/103896 fast/backgrounds/gradient-background-leakage.html [ Pass ImageOnlyFailure ]
+
 # The following tests fail on all platforms and need further investigation.
 # Many of these are skipped on the Mac platform
 webkit.org/b/45991 canvas/philip/tests/2d.drawImage.broken.html [ Failure ]

Modified: trunk/Source/WebCore/ChangeLog (136754 => 136755)


--- trunk/Source/WebCore/ChangeLog	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/ChangeLog	2012-12-05 21:40:26 UTC (rev 136755)
@@ -1,3 +1,57 @@
+2012-12-05  Justin Novosad  <[email protected]>
+
+        [skia] Improve performance of GraphicsContext::createCompatibleBuffer by using SkDevice:createCompatibleDevice
+        https://bugs.webkit.org/show_bug.cgi?id=103896
+
+        Reviewed by Stephen White.
+
+        Refactored GraphicsContext::createCompatibleBuffer (platform common
+        code) to use platform-specific implementations provided by ImageBuffer.
+        There is no change in behavior for non-skia ports. The skia
+        implementation uses skia'a own createCompatibleDevice implementation,
+        which offers several performance benefits:
+        1. For accelerated contexts, the backing store may be allocated from
+        the scratch texture pool, which minimizes texture allocation and
+        deallocation overhead.
+        2. The backing store will not be initially cleared if it is known
+        in advance that fully opaque contents will be drawn into the buffer.
+        3. For non-accelerated contexts, if the backing store is flagged as
+        opaque, faster blitter loop implementations will be used for drawing
+        the buffer contents into other buffers. (e.g. generated opaque gradient
+        fills)
+
+        No new tests: covered by existing layout tests 
+
+        * platform/graphics/Generator.h:
+        (Generator):
+        Added hasAlpha method so that it can be used by GeneratorGeneratedImage
+        * platform/graphics/GeneratorGeneratedImage.cpp:
+        (WebCore::GeneratorGeneratedImage::drawPattern):
+        Passing m_generator->hasAlpha() to createCompatibleBuffer in order to
+        take advantage of optimizations that apply to opaque buffers.
+        * platform/graphics/Gradient.h:
+        (Gradient):
+        Made hasAlpha virtual so that it now overrides Generator::hasAlpha
+        * platform/graphics/GraphicsContext.cpp:
+        (WebCore::GraphicsContext::createCompatibleBuffer):
+        Refactored to use platform-specific implementation
+        * platform/graphics/GraphicsContext.h:
+        * platform/graphics/ImageBuffer.cpp:
+        (WebCore::createCompatibleBuffer):
+        Non-skia implementation. Mimics old
+        GraphicsContext::createCompatibleBuffer
+        * platform/graphics/ImageBuffer.h:
+        (ImageBuffer):
+        New skia-specific constructor
+        * platform/graphics/skia/ImageBufferSkia.cpp:
+        (WebCore::ImageBuffer::createCompatibleBuffer):
+        (WebCore::ImageBuffer::ImageBuffer):
+        * platform/graphics/skia/PlatformContextSkia.cpp:
+        (WebCore::PlatformContextSkia::createCompatibleDevice):
+        (WebCore):
+        * platform/graphics/skia/PlatformContextSkia.h:
+        (PlatformContextSkia):
+
 2012-12-05  Alexis Menard  <[email protected]>
 
         REGRESSION (r136683): css3/calc/background-position-parsing.html failing on EFL Linux 64-bit Debug WK2

Modified: trunk/Source/WebCore/platform/graphics/Generator.h (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/Generator.h	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/Generator.h	2012-12-05 21:40:26 UTC (rev 136755)
@@ -40,6 +40,7 @@
     virtual void fill(GraphicsContext*, const FloatRect&) = 0;
     virtual void adjustParametersForTiledDrawing(IntSize& /* size */, FloatRect& /* srcRect */) { }
     virtual unsigned hash() const = 0;
+    virtual bool hasAlpha() const = 0;
 };
 
 } //namespace

Modified: trunk/Source/WebCore/platform/graphics/GeneratorGeneratedImage.cpp (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/GeneratorGeneratedImage.cpp	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/GeneratorGeneratedImage.cpp	2012-12-05 21:40:26 UTC (rev 136755)
@@ -64,7 +64,7 @@
     unsigned generatorHash = m_generator->hash();
 
     if (!m_cachedImageBuffer || m_cachedGeneratorHash != generatorHash || m_cachedAdjustedSize != adjustedSize || !destContext->isCompatibleWithBuffer(m_cachedImageBuffer.get())) {
-        m_cachedImageBuffer = destContext->createCompatibleBuffer(adjustedSize);
+        m_cachedImageBuffer = destContext->createCompatibleBuffer(adjustedSize, m_generator->hasAlpha());
         if (!m_cachedImageBuffer)
             return;
 

Modified: trunk/Source/WebCore/platform/graphics/Gradient.h (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/Gradient.h	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/Gradient.h	2012-12-05 21:40:26 UTC (rev 136755)
@@ -82,7 +82,7 @@
         void addColorStop(float, const Color&);
 
         void getColor(float value, float* r, float* g, float* b, float* a) const;
-        bool hasAlpha() const;
+        virtual bool hasAlpha() const OVERRIDE;
 
         bool isRadial() const { return m_radial; }
         bool isZeroSize() const { return m_p0.x() == m_p1.x() && m_p0.y() == m_p1.y() && (!m_radial || m_r0 == m_r1); }

Modified: trunk/Source/WebCore/platform/graphics/GraphicsContext.cpp (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/GraphicsContext.cpp	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/GraphicsContext.cpp	2012-12-05 21:40:26 UTC (rev 136755)
@@ -771,7 +771,7 @@
     return a.xScale() == b.xScale() && a.yScale() == b.yScale();
 }
 
-PassOwnPtr<ImageBuffer> GraphicsContext::createCompatibleBuffer(const IntSize& size) const
+PassOwnPtr<ImageBuffer> GraphicsContext::createCompatibleBuffer(const IntSize& size, bool hasAlpha) const
 {
     // Make the buffer larger if the context's transform is scaling it so we need a higher
     // resolution than one pixel per unit. Also set up a corresponding scale factor on the
@@ -780,7 +780,7 @@
     AffineTransform transform = getCTM(DefinitelyIncludeDeviceScale);
     IntSize scaledSize(static_cast<int>(ceil(size.width() * transform.xScale())), static_cast<int>(ceil(size.height() * transform.yScale())));
 
-    OwnPtr<ImageBuffer> buffer = ImageBuffer::create(scaledSize, 1, ColorSpaceDeviceRGB, isAcceleratedContext() ? Accelerated : Unaccelerated);
+    OwnPtr<ImageBuffer> buffer = ImageBuffer::createCompatibleBuffer(scaledSize, 1, ColorSpaceDeviceRGB, this, hasAlpha);
     if (!buffer)
         return nullptr;
 

Modified: trunk/Source/WebCore/platform/graphics/GraphicsContext.h (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/GraphicsContext.h	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/GraphicsContext.h	2012-12-05 21:40:26 UTC (rev 136755)
@@ -434,7 +434,7 @@
 #endif
         // Create an image buffer compatible with this context, with suitable resolution
         // for drawing into the buffer and then into this context.
-        PassOwnPtr<ImageBuffer> createCompatibleBuffer(const IntSize&) const;
+        PassOwnPtr<ImageBuffer> createCompatibleBuffer(const IntSize&, bool hasAlpha = true) const;
         bool isCompatibleWithBuffer(ImageBuffer*) const;
 
         // This function applies the device scale factor to the context, making the context capable of

Modified: trunk/Source/WebCore/platform/graphics/ImageBuffer.cpp (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/ImageBuffer.cpp	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/ImageBuffer.cpp	2012-12-05 21:40:26 UTC (rev 136755)
@@ -111,6 +111,11 @@
 {
     return false;
 }
+
+PassOwnPtr<ImageBuffer> ImageBuffer::createCompatibleBuffer(const IntSize& size, float resolutionScale, ColorSpace colorSpace, const GraphicsContext* context, bool)
+{
+    return create(size, resolutionScale, colorSpace, context->isAcceleratedContext() ? Accelerated : Unaccelerated);
+}
 #endif
 
 void ImageBuffer::reportMemoryUsage(MemoryObjectInfo* memoryObjectInfo) const

Modified: trunk/Source/WebCore/platform/graphics/ImageBuffer.h (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/ImageBuffer.h	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/ImageBuffer.h	2012-12-05 21:40:26 UTC (rev 136755)
@@ -93,6 +93,8 @@
             return buf.release();
         }
 
+        static PassOwnPtr<ImageBuffer> createCompatibleBuffer(const IntSize&, float resolutionScale, ColorSpace, const GraphicsContext*, bool hasAlpha);
+
         ~ImageBuffer();
 
         // The actual resolution of the backing store
@@ -156,6 +158,9 @@
         // This constructor will place its success into the given out-variable
         // so that create() knows when it should return failure.
         ImageBuffer(const IntSize&, float resolutionScale, ColorSpace, RenderingMode, DeferralMode, bool& success);
+#if USE(SKIA)
+        ImageBuffer(const IntSize&, float resolutionScale, ColorSpace, const GraphicsContext*, bool hasAlpha, bool& success);
+#endif
     };
 
 #if USE(CG) || USE(SKIA)

Modified: trunk/Source/WebCore/platform/graphics/skia/ImageBufferSkia.cpp (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/skia/ImageBufferSkia.cpp	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/skia/ImageBufferSkia.cpp	2012-12-05 21:40:26 UTC (rev 136755)
@@ -108,6 +108,42 @@
     return pixelRef ? new SkCanvas(device) : 0;
 }
 
+PassOwnPtr<ImageBuffer> ImageBuffer::createCompatibleBuffer(const IntSize& size, float resolutionScale, ColorSpace colorSpace, const GraphicsContext* context, bool hasAlpha)
+{
+    bool success = false;
+    OwnPtr<ImageBuffer> buf = adoptPtr(new ImageBuffer(size, resolutionScale, colorSpace, context, hasAlpha, success));
+    if (!success)
+        return nullptr;
+    return buf.release();
+}
+
+ImageBuffer::ImageBuffer(const IntSize& size, float resolutionScale, ColorSpace, const GraphicsContext* compatibleContext, bool hasAlpha, bool& success)
+    : m_data(size)
+    , m_size(size)
+    , m_logicalSize(size)
+    , m_resolutionScale(resolutionScale)
+{
+    if (!compatibleContext) {
+        success = false;
+        return;
+    }
+
+    SkAutoTUnref<SkDevice> device(compatibleContext->platformContext()->createCompatibleDevice(size, hasAlpha));
+    SkPixelRef* pixelRef = device->accessBitmap(false).pixelRef();
+    if (!pixelRef) {
+        success = false;
+        return;
+    }
+
+    m_data.m_canvas = adoptPtr(new SkCanvas(device));
+    m_data.m_platformContext.setCanvas(m_data.m_canvas.get());
+    m_context = adoptPtr(new GraphicsContext(&m_data.m_platformContext));
+    m_context->platformContext()->setDrawingToImageBuffer(true);
+    m_context->scale(FloatSize(m_resolutionScale, m_resolutionScale));
+
+    success = true;
+}
+
 ImageBuffer::ImageBuffer(const IntSize& size, float resolutionScale, ColorSpace, RenderingMode renderingMode, DeferralMode deferralMode, bool& success)
     : m_data(size)
     , m_size(size)

Modified: trunk/Source/WebCore/platform/graphics/skia/PlatformContextSkia.cpp (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/skia/PlatformContextSkia.cpp	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/skia/PlatformContextSkia.cpp	2012-12-05 21:40:26 UTC (rev 136755)
@@ -222,6 +222,11 @@
     m_drawingToImageBuffer = value;
 }
 
+SkDevice* PlatformContextSkia::createCompatibleDevice(const IntSize& size, bool hasAlpha)
+{
+    return m_canvas->createCompatibleDevice(bitmap()->config(), size.width(), size.height(), !hasAlpha);
+}
+
 bool PlatformContextSkia::isDrawingToImageBuffer() const
 {
     return m_drawingToImageBuffer;

Modified: trunk/Source/WebCore/platform/graphics/skia/PlatformContextSkia.h (136754 => 136755)


--- trunk/Source/WebCore/platform/graphics/skia/PlatformContextSkia.h	2012-12-05 21:38:52 UTC (rev 136754)
+++ trunk/Source/WebCore/platform/graphics/skia/PlatformContextSkia.h	2012-12-05 21:40:26 UTC (rev 136755)
@@ -82,6 +82,8 @@
     // to the constructor.
     void setCanvas(SkCanvas*);
 
+    SkDevice* createCompatibleDevice(const IntSize&, bool hasAlpha);
+
     // If false we're rendering to a GraphicsContext for a web page, if false
     // we're not (as is the case when rendering to a canvas object).
     // If this is true the contents have not been marked up with the magic
_______________________________________________
webkit-changes mailing list
[email protected]
http://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to