Add Sad Tab resources to the iOS build.
[chromium-blink-merge.git] / cc / delegated_renderer_layer_impl.cc
blob1c04e3361f372b4dda86ed1d777e50562f628144
1 // Copyright 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "config.h"
7 #include "cc/delegated_renderer_layer_impl.h"
9 #include "cc/append_quads_data.h"
10 #include "cc/math_util.h"
11 #include "cc/quad_sink.h"
12 #include "cc/render_pass_draw_quad.h"
13 #include "cc/render_pass_sink.h"
15 namespace cc {
17 DelegatedRendererLayerImpl::DelegatedRendererLayerImpl(int id)
18 : LayerImpl(id)
22 DelegatedRendererLayerImpl::~DelegatedRendererLayerImpl()
24 clearRenderPasses();
27 bool DelegatedRendererLayerImpl::descendantDrawsContent()
29 // FIXME: This could possibly return false even though there are some
30 // quads present as they could all be from a single layer (or set of
31 // layers without children). If this happens, then make a test that
32 // ensures the opacity is being changed on quads in the root RenderPass
33 // when this layer doesn't own a RenderSurfaceImpl.
34 return !m_renderPassesInDrawOrder.isEmpty();
37 bool DelegatedRendererLayerImpl::hasContributingDelegatedRenderPasses() const
39 // The root RenderPass for the layer is merged with its target
40 // RenderPass in each frame. So we only have extra RenderPasses
41 // to merge when we have a non-root RenderPass present.
42 return m_renderPassesInDrawOrder.size() > 1;
45 void DelegatedRendererLayerImpl::setRenderPasses(ScopedPtrVector<RenderPass>& renderPassesInDrawOrder)
47 gfx::RectF oldRootDamage;
48 if (!m_renderPassesInDrawOrder.isEmpty())
49 oldRootDamage = m_renderPassesInDrawOrder.last()->damageRect();
51 clearRenderPasses();
53 for (size_t i = 0; i < renderPassesInDrawOrder.size(); ++i) {
54 m_renderPassesIndexById.insert(std::pair<RenderPass::Id, int>(renderPassesInDrawOrder[i]->id(), i));
55 m_renderPassesInDrawOrder.append(renderPassesInDrawOrder.take(i));
57 renderPassesInDrawOrder.clear();
59 if (!m_renderPassesInDrawOrder.isEmpty()) {
60 gfx::RectF newRootDamage = m_renderPassesInDrawOrder.last()->damageRect();
61 m_renderPassesInDrawOrder.last()->setDamageRect(gfx::UnionRects(oldRootDamage, newRootDamage));
65 void DelegatedRendererLayerImpl::clearRenderPasses()
67 // FIXME: Release the resources back to the nested compositor.
68 m_renderPassesIndexById.clear();
69 m_renderPassesInDrawOrder.clear();
72 void DelegatedRendererLayerImpl::didLoseContext()
74 clearRenderPasses();
77 static inline int indexToId(int index) { return index + 1; }
78 static inline int idToIndex(int id) { return id - 1; }
80 RenderPass::Id DelegatedRendererLayerImpl::firstContributingRenderPassId() const
82 return RenderPass::Id(id(), indexToId(0));
85 RenderPass::Id DelegatedRendererLayerImpl::nextContributingRenderPassId(RenderPass::Id previous) const
87 return RenderPass::Id(previous.layerId, previous.index + 1);
90 RenderPass::Id DelegatedRendererLayerImpl::convertDelegatedRenderPassId(RenderPass::Id delegatedRenderPassId) const
92 base::hash_map<RenderPass::Id, int>::const_iterator it = m_renderPassesIndexById.find(delegatedRenderPassId);
93 DCHECK(it != m_renderPassesIndexById.end());
94 unsigned delegatedRenderPassIndex = it->second;
95 return RenderPass::Id(id(), indexToId(delegatedRenderPassIndex));
98 void DelegatedRendererLayerImpl::appendContributingRenderPasses(RenderPassSink& renderPassSink)
100 DCHECK(hasContributingDelegatedRenderPasses());
102 for (size_t i = 0; i < m_renderPassesInDrawOrder.size() - 1; ++i) {
103 RenderPass::Id outputRenderPassId = convertDelegatedRenderPassId(m_renderPassesInDrawOrder[i]->id());
105 // Don't clash with the RenderPass we generate if we own a RenderSurfaceImpl.
106 DCHECK(outputRenderPassId.index > 0);
108 renderPassSink.appendRenderPass(m_renderPassesInDrawOrder[i]->copy(outputRenderPassId));
112 void DelegatedRendererLayerImpl::appendQuads(QuadSink& quadSink, AppendQuadsData& appendQuadsData)
114 if (m_renderPassesInDrawOrder.isEmpty())
115 return;
117 RenderPass::Id targetRenderPassId = appendQuadsData.renderPassId;
119 // If the index of the renderPassId is 0, then it is a renderPass generated for a layer
120 // in this compositor, not the delegated renderer. Then we want to merge our root renderPass with
121 // the target renderPass. Otherwise, it is some renderPass which we added from the delegated
122 // renderer.
123 bool shouldMergeRootRenderPassWithTarget = !targetRenderPassId.index;
124 if (shouldMergeRootRenderPassWithTarget) {
125 // Verify that the renderPass we are appending to is created our renderTarget.
126 DCHECK(targetRenderPassId.layerId == renderTarget()->id());
128 RenderPass* rootDelegatedRenderPass = m_renderPassesInDrawOrder.last();
129 appendRenderPassQuads(quadSink, appendQuadsData, rootDelegatedRenderPass);
130 } else {
131 // Verify that the renderPass we are appending to was created by us.
132 DCHECK(targetRenderPassId.layerId == id());
134 int renderPassIndex = idToIndex(targetRenderPassId.index);
135 RenderPass* delegatedRenderPass = m_renderPassesInDrawOrder[renderPassIndex];
136 appendRenderPassQuads(quadSink, appendQuadsData, delegatedRenderPass);
140 void DelegatedRendererLayerImpl::appendRenderPassQuads(QuadSink& quadSink, AppendQuadsData& appendQuadsData, RenderPass* delegatedRenderPass) const
142 const SharedQuadState* currentSharedQuadState = 0;
143 SharedQuadState* copiedSharedQuadState = 0;
144 for (size_t i = 0; i < delegatedRenderPass->quadList().size(); ++i) {
145 DrawQuad* quad = delegatedRenderPass->quadList()[i];
147 if (quad->sharedQuadState() != currentSharedQuadState) {
148 currentSharedQuadState = quad->sharedQuadState();
149 copiedSharedQuadState = quadSink.useSharedQuadState(currentSharedQuadState->copy());
150 bool targetIsFromDelegatedRendererLayer = appendQuadsData.renderPassId.layerId == id();
151 if (!targetIsFromDelegatedRendererLayer) {
152 // Should be the root render pass.
153 DCHECK(delegatedRenderPass == m_renderPassesInDrawOrder.last());
154 // This layer must be drawing to a renderTarget other than itself.
155 DCHECK(renderTarget() != this);
157 copiedSharedQuadState->clippedRectInTarget = MathUtil::mapClippedRect(drawTransform(), copiedSharedQuadState->clippedRectInTarget);
158 copiedSharedQuadState->quadTransform = copiedSharedQuadState->quadTransform * drawTransform();
159 copiedSharedQuadState->opacity *= drawOpacity();
162 DCHECK(copiedSharedQuadState);
164 scoped_ptr<DrawQuad> copyQuad;
165 if (quad->material() != DrawQuad::RenderPass)
166 copyQuad = quad->copy(copiedSharedQuadState);
167 else {
168 RenderPass::Id contributingDelegatedRenderPassId = RenderPassDrawQuad::materialCast(quad)->renderPassId();
169 RenderPass::Id contributingRenderPassId = convertDelegatedRenderPassId(contributingDelegatedRenderPassId);
170 DCHECK(contributingRenderPassId != appendQuadsData.renderPassId);
172 copyQuad = RenderPassDrawQuad::materialCast(quad)->copy(copiedSharedQuadState, contributingRenderPassId).PassAs<DrawQuad>();
174 DCHECK(copyQuad.get());
176 quadSink.append(copyQuad.Pass(), appendQuadsData);
180 const char* DelegatedRendererLayerImpl::layerTypeAsString() const
182 return "DelegatedRendererLayer";
185 } // namespace cc