[chromium] Add TextureCopier for copying texture contents
[WebKit-https.git] / Source / WebCore / platform / graphics / chromium / Canvas2DLayerChromium.cpp
1 /*
2  * Copyright (C) 2010 Google Inc. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions are
6  * met:
7  *
8  *     * Redistributions of source code must retain the above copyright
9  * notice, this list of conditions and the following disclaimer.
10  *     * Redistributions in binary form must reproduce the above
11  * copyright notice, this list of conditions and the following disclaimer
12  * in the documentation and/or other materials provided with the
13  * distribution.
14  *     * Neither the name of Google Inc. nor the names of its
15  * contributors may be used to endorse or promote products derived from
16  * this software without specific prior written permission.
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29  */
30
31 #include "config.h"
32
33 #if USE(ACCELERATED_COMPOSITING)
34
35 #include "Canvas2DLayerChromium.h"
36
37 #include "Extensions3DChromium.h"
38 #include "GraphicsContext3D.h"
39 #include "LayerRendererChromium.h" // For the GLC() macro
40 #include "TextureCopier.h"
41 #include "cc/CCLayerTreeHost.h"
42 #include "cc/CCTextureLayerImpl.h"
43 #include "cc/CCTextureUpdater.h"
44
45 #include "SkCanvas.h"
46
47 namespace WebCore {
48
49 PassRefPtr<Canvas2DLayerChromium> Canvas2DLayerChromium::create(PassRefPtr<GraphicsContext3D> context, const IntSize& size)
50 {
51     return adoptRef(new Canvas2DLayerChromium(context, size));
52 }
53
54 Canvas2DLayerChromium::Canvas2DLayerChromium(PassRefPtr<GraphicsContext3D> context, const IntSize& size)
55     : CanvasLayerChromium()
56     , m_context(context)
57     , m_contextLost(false)
58     , m_size(size)
59     , m_backTextureId(0)
60     , m_useDoubleBuffering(CCProxy::hasImplThread())
61     , m_canvas(0)
62 {
63 }
64
65 Canvas2DLayerChromium::~Canvas2DLayerChromium()
66 {
67     if (m_context && layerTreeHost())
68         layerTreeHost()->stopRateLimiter(m_context.get());
69 }
70
71 void Canvas2DLayerChromium::setTextureId(unsigned textureId)
72 {
73     m_backTextureId = textureId;
74     setNeedsCommit();
75 }
76
77 void Canvas2DLayerChromium::setNeedsDisplayRect(const FloatRect& dirtyRect)
78 {
79     LayerChromium::setNeedsDisplayRect(dirtyRect);
80
81     if (layerTreeHost())
82         layerTreeHost()->startRateLimiter(m_context.get());
83 }
84
85 bool Canvas2DLayerChromium::drawsContent() const
86 {
87     return LayerChromium::drawsContent() && m_backTextureId && !m_size.isEmpty()
88         && !m_contextLost;
89 }
90
91 void Canvas2DLayerChromium::setCanvas(SkCanvas* canvas)
92 {
93     m_canvas = canvas;
94 }
95
96 void Canvas2DLayerChromium::paintContentsIfDirty(const CCOcclusionTracker* /* occlusion */)
97 {
98     TRACE_EVENT("Canvas2DLayerChromium::paintContentsIfDirty", this, 0);
99     if (!drawsContent())
100         return;
101
102     if (m_useDoubleBuffering && layerTreeHost()) {
103         TextureManager* textureManager = layerTreeHost()->contentsTextureManager();
104         if (m_frontTexture)
105             m_frontTexture->setTextureManager(textureManager);
106         else
107             m_frontTexture = ManagedTexture::create(textureManager);
108         m_frontTexture->reserve(m_size, GraphicsContext3D::RGBA);
109     }
110
111     if (!needsDisplay())
112         return;
113
114     m_needsDisplay = false;
115
116     bool success = m_context->makeContextCurrent();
117     ASSERT_UNUSED(success, success);
118
119     m_contextLost = m_context->getExtensions()->getGraphicsResetStatusARB() != GraphicsContext3D::NO_ERROR;
120     if (m_contextLost)
121         return;
122
123     if (m_canvas) {
124         TRACE_EVENT("SkDeferredCanvas::flush", m_canvas, 0);
125         m_canvas->flush();
126     }
127
128     TRACE_EVENT("GrContext::flush", m_context, 0);
129     m_context->flush();
130 }
131
132 void Canvas2DLayerChromium::updateCompositorResources(GraphicsContext3D* context, CCTextureUpdater& updater)
133 {
134     if (!m_backTextureId || !m_frontTexture || !m_frontTexture->isValid(m_size, GraphicsContext3D::RGBA))
135         return;
136
137     m_frontTexture->allocate(updater.allocator());
138     updater.copier()->copyTexture(context, m_backTextureId, m_frontTexture->textureId(), m_size);
139 }
140
141 void Canvas2DLayerChromium::pushPropertiesTo(CCLayerImpl* layer)
142 {
143     CanvasLayerChromium::pushPropertiesTo(layer);
144
145     CCTextureLayerImpl* textureLayer = static_cast<CCTextureLayerImpl*>(layer);
146     if (m_useDoubleBuffering) {
147         if (m_frontTexture && m_frontTexture->isValid(m_size, GraphicsContext3D::RGBA))
148             textureLayer->setTextureId(m_frontTexture->textureId());
149         else
150             textureLayer->setTextureId(0);
151     } else
152         textureLayer->setTextureId(m_backTextureId);
153 }
154
155 void Canvas2DLayerChromium::unreserveContentsTexture()
156 {
157     if (m_useDoubleBuffering)
158         m_frontTexture->unreserve();
159 }
160
161 }
162
163 #endif // USE(ACCELERATED_COMPOSITING)