c986591a78ad9440aaac5043c39d34bbaf954875
[WebKit-https.git] / Source / WebCore / platform / graphics / chromium / cc / CCLayerImpl.cpp
1 /*
2  * Copyright (C) 2011 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
6  * are met:
7  *
8  * 1.  Redistributions of source code must retain the above copyright
9  *     notice, this list of conditions and the following disclaimer.
10  * 2.  Redistributions in binary form must reproduce the above copyright
11  *     notice, this list of conditions and the following disclaimer in the
12  *     documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
15  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17  * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
18  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
19  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
20  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
21  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
23  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24  */
25
26 #include "config.h"
27
28 #if USE(ACCELERATED_COMPOSITING)
29
30 #include "cc/CCLayerImpl.h"
31
32 #include "GraphicsContext3D.h"
33 #include "LayerChromium.h"
34 #include "LayerRendererChromium.h"
35 #include "cc/CCLayerSorter.h"
36 #include <wtf/text/WTFString.h>
37
38 namespace WebCore {
39
40 CCLayerImpl::CCLayerImpl(int id)
41     : m_parent(0)
42     , m_layerId(id)
43     , m_anchorPoint(0.5, 0.5)
44     , m_anchorPointZ(0)
45     , m_doubleSided(true)
46     , m_masksToBounds(false)
47     , m_opacity(1.0)
48     , m_preserves3D(false)
49     , m_usesLayerScissor(false)
50     , m_isNonCompositedContent(false)
51     , m_drawsContent(false)
52     , m_targetRenderSurface(0)
53     , m_drawDepth(0)
54     , m_drawOpacity(0)
55     , m_debugBorderColor(0, 0, 0, 0)
56     , m_debugBorderWidth(0)
57 {
58 }
59
60 CCLayerImpl::~CCLayerImpl()
61 {
62 }
63
64 void CCLayerImpl::addChild(PassRefPtr<CCLayerImpl> child)
65 {
66     child->setParent(this);
67     m_children.append(child);
68 }
69
70 void CCLayerImpl::removeFromParent()
71 {
72     if (!m_parent)
73         return;
74     for (size_t i = 0; i < m_parent->m_children.size(); ++i) {
75         if (m_parent->m_children[i].get() == this) {
76             m_parent->m_children.remove(i);
77             break;
78         }
79     }
80     m_parent = 0;
81 }
82
83 void CCLayerImpl::removeAllChildren()
84 {
85     while (m_children.size())
86         m_children[0]->removeFromParent();
87 }
88
89 void CCLayerImpl::clearChildList()
90 {
91     m_children.clear();
92 }
93
94 void CCLayerImpl::createRenderSurface()
95 {
96     ASSERT(!m_renderSurface);
97     m_renderSurface = adoptPtr(new CCRenderSurface(this));
98 }
99
100 bool CCLayerImpl::descendantDrawsContent()
101 {
102     for (size_t i = 0; i < m_children.size(); ++i) {
103         if (m_children[i]->drawsContent() || m_children[i]->descendantDrawsContent())
104             return true;
105     }
106     return false;
107 }
108
109 void CCLayerImpl::draw(LayerRendererChromium*)
110 {
111     ASSERT_NOT_REACHED();
112 }
113
114 void CCLayerImpl::bindContentsTexture(LayerRendererChromium*)
115 {
116     ASSERT_NOT_REACHED();
117 }
118
119 void CCLayerImpl::cleanupResources()
120 {
121     if (renderSurface())
122         renderSurface()->cleanupResources();
123 }
124
125 const IntRect CCLayerImpl::getDrawRect() const
126 {
127     // Form the matrix used by the shader to map the corners of the layer's
128     // bounds into the view space.
129     FloatRect layerRect(-0.5 * bounds().width(), -0.5 * bounds().height(), bounds().width(), bounds().height());
130     IntRect mappedRect = enclosingIntRect(drawTransform().mapRect(layerRect));
131     return mappedRect;
132 }
133
134 void CCLayerImpl::drawDebugBorder(LayerRendererChromium* layerRenderer)
135 {
136     static float glMatrix[16];
137     if (!debugBorderColor().alpha())
138         return;
139
140     GraphicsContext3D* context = layerRenderer->context();
141     const LayerChromium::BorderProgram* program = layerRenderer->borderProgram();
142     ASSERT(program && program->initialized());
143     GLC(context, context->useProgram(program->program()));
144
145     TransformationMatrix renderMatrix = drawTransform();
146     renderMatrix.scale3d(bounds().width(), bounds().height(), 1);
147     LayerRendererChromium::toGLMatrix(&glMatrix[0], layerRenderer->projectionMatrix() * renderMatrix);
148     GLC(context, context->uniformMatrix4fv(program->vertexShader().matrixLocation(), false, &glMatrix[0], 1));
149
150     GLC(context, context->uniform4f(program->fragmentShader().colorLocation(), debugBorderColor().red() / 255.0, debugBorderColor().green() / 255.0, debugBorderColor().blue() / 255.0, 1));
151
152     GLC(context, context->lineWidth(debugBorderWidth()));
153
154     // The indices for the line are stored in the same array as the triangle indices.
155     GLC(context, context->drawElements(GraphicsContext3D::LINE_LOOP, 4, GraphicsContext3D::UNSIGNED_SHORT, 6 * sizeof(unsigned short)));
156 }
157
158 void CCLayerImpl::writeIndent(TextStream& ts, int indent)
159 {
160     for (int i = 0; i != indent; ++i)
161         ts << "  ";
162 }
163
164 void CCLayerImpl::dumpLayerProperties(TextStream& ts, int indent) const
165 {
166     writeIndent(ts, indent);
167     ts << "bounds: " << bounds().width() << ", " << bounds().height() << "\n";
168
169     if (m_targetRenderSurface) {
170         writeIndent(ts, indent);
171         ts << "targetRenderSurface: " << m_targetRenderSurface->name() << "\n";
172     }
173
174     writeIndent(ts, indent);
175     ts << "drawTransform: ";
176     ts << m_drawTransform.m11() << ", " << m_drawTransform.m12() << ", " << m_drawTransform.m13() << ", " << m_drawTransform.m14() << ", ";
177     ts << m_drawTransform.m21() << ", " << m_drawTransform.m22() << ", " << m_drawTransform.m23() << ", " << m_drawTransform.m24() << ", ";
178     ts << m_drawTransform.m31() << ", " << m_drawTransform.m32() << ", " << m_drawTransform.m33() << ", " << m_drawTransform.m34() << ", ";
179     ts << m_drawTransform.m41() << ", " << m_drawTransform.m42() << ", " << m_drawTransform.m43() << ", " << m_drawTransform.m44() << "\n";
180 }
181
182 void sortLayers(Vector<RefPtr<CCLayerImpl> >::iterator first, Vector<RefPtr<CCLayerImpl> >::iterator end, CCLayerSorter* layerSorter)
183 {
184     TRACE_EVENT("LayerRendererChromium::sortLayers", 0, 0);
185     layerSorter->sort(first, end);
186 }
187
188 String CCLayerImpl::layerTreeAsText() const
189 {
190     TextStream ts;
191     dumpLayer(ts, 0);
192     return ts.release();
193 }
194
195 void CCLayerImpl::dumpLayer(TextStream& ts, int indent) const
196 {
197     writeIndent(ts, indent);
198     ts << layerTypeAsString() << "(" << m_name << ")\n";
199     dumpLayerProperties(ts, indent+2);
200     if (m_replicaLayer) {
201         writeIndent(ts, indent+2);
202         ts << "Replica:\n";
203         m_replicaLayer->dumpLayer(ts, indent+3);
204     }
205     if (m_maskLayer) {
206         writeIndent(ts, indent+2);
207         ts << "Mask:\n";
208         m_maskLayer->dumpLayer(ts, indent+3);
209     }
210     for (size_t i = 0; i < m_children.size(); ++i)
211         m_children[i]->dumpLayer(ts, indent+1);
212 }
213
214 }
215
216
217 #endif // USE(ACCELERATED_COMPOSITING)