6ac96b2d7a442bb7aa611c0b8042b76f0ff468cd
[platform/framework/web/crosswalk.git] / src / cc / output / overlay_strategy_single_on_top.cc
1 // Copyright 2014 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.
4
5 #include "cc/output/overlay_strategy_single_on_top.h"
6
7 #include "cc/quads/draw_quad.h"
8 #include "cc/quads/texture_draw_quad.h"
9 #include "ui/gfx/geometry/rect_conversions.h"
10 #include "ui/gfx/transform.h"
11
12 namespace cc {
13
14 OverlayStrategySingleOnTop::OverlayStrategySingleOnTop(
15     OverlayCandidateValidator* capability_checker,
16     ResourceProvider* resource_provider)
17     : capability_checker_(capability_checker),
18       resource_provider_(resource_provider) {}
19
20 bool OverlayStrategySingleOnTop::Attempt(
21     RenderPassList* render_passes_in_draw_order,
22     OverlayCandidateList* candidate_list) {
23   // Only attempt to handle very simple case for now.
24   if (!capability_checker_)
25     return false;
26
27   RenderPass* root_render_pass = render_passes_in_draw_order->back();
28   DCHECK(root_render_pass);
29
30   QuadList& quad_list = root_render_pass->quad_list;
31   QuadList::Iterator candidate_iterator = quad_list.end();
32   for (QuadList::Iterator it = quad_list.begin(); it != quad_list.end(); ++it) {
33     const DrawQuad* draw_quad = &*it;
34     if (draw_quad->material == DrawQuad::TEXTURE_CONTENT) {
35       const TextureDrawQuad& quad = *TextureDrawQuad::MaterialCast(draw_quad);
36       if (!resource_provider_->AllowOverlay(quad.resource_id)) {
37         continue;
38       }
39       // Check that no prior quads overlap it.
40       bool intersects = false;
41       gfx::RectF rect = draw_quad->rect;
42       draw_quad->quadTransform().TransformRect(&rect);
43       for (QuadList::Iterator overlap_iter = quad_list.begin();
44            overlap_iter != it;
45            ++overlap_iter) {
46         gfx::RectF overlap_rect = overlap_iter->rect;
47         overlap_iter->quadTransform().TransformRect(&overlap_rect);
48         if (rect.Intersects(overlap_rect)) {
49           intersects = true;
50           break;
51         }
52       }
53       if (intersects)
54         continue;
55       candidate_iterator = it;
56       break;
57     }
58   }
59   if (candidate_iterator == quad_list.end())
60     return false;
61   const TextureDrawQuad& quad =
62       *TextureDrawQuad::MaterialCast(&*candidate_iterator);
63
64   // Simple quads only.
65   gfx::OverlayTransform overlay_transform =
66       OverlayCandidate::GetOverlayTransform(quad.quadTransform(), quad.flipped);
67   if (overlay_transform == gfx::OVERLAY_TRANSFORM_INVALID ||
68       !quad.quadTransform().IsIdentityOrTranslation() || quad.needs_blending ||
69       quad.shared_quad_state->opacity != 1.f ||
70       quad.shared_quad_state->blend_mode != SkXfermode::kSrcOver_Mode ||
71       quad.premultiplied_alpha || quad.background_color != SK_ColorTRANSPARENT)
72     return false;
73
74   // Add our primary surface.
75   OverlayCandidateList candidates;
76   OverlayCandidate main_image;
77   main_image.display_rect = root_render_pass->output_rect;
78   main_image.format = RGBA_8888;
79   candidates.push_back(main_image);
80
81   // Add the overlay.
82   OverlayCandidate candidate;
83   candidate.transform = overlay_transform;
84   candidate.display_rect =
85       OverlayCandidate::GetOverlayRect(quad.quadTransform(), quad.rect);
86   candidate.uv_rect = BoundingRect(quad.uv_top_left, quad.uv_bottom_right);
87   candidate.format = RGBA_8888;
88   candidate.resource_id = quad.resource_id;
89   candidate.plane_z_order = 1;
90   candidates.push_back(candidate);
91
92   // Check for support.
93   capability_checker_->CheckOverlaySupport(&candidates);
94
95   // If the candidate can be handled by an overlay, create a pass for it.
96   if (candidates[1].overlay_handled) {
97     quad_list.EraseAndInvalidateAllPointers(candidate_iterator);
98     candidate_list->swap(candidates);
99     return true;
100   }
101   return false;
102 }
103
104 }  // namespace cc