| OLD | NEW |
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "cc/output/overlay_strategy_sandwich.h" | 5 #include "cc/output/overlay_strategy_sandwich.h" |
| 6 | 6 |
| 7 #include "cc/base/math_util.h" | 7 #include "cc/base/math_util.h" |
| 8 #include "cc/base/region.h" | 8 #include "cc/base/region.h" |
| 9 #include "cc/output/overlay_candidate_validator.h" | 9 #include "cc/output/overlay_candidate_validator.h" |
| 10 #include "cc/quads/draw_quad.h" | 10 #include "cc/quads/draw_quad.h" |
| (...skipping 14 matching lines...) Expand all Loading... |
| 25 uv_cropped_rect.Scale(uv_rect->width() / display_rect->width(), | 25 uv_cropped_rect.Scale(uv_rect->width() / display_rect->width(), |
| 26 uv_rect->height() / display_rect->height()); | 26 uv_rect->height() / display_rect->height()); |
| 27 uv_cropped_rect += gfx::Vector2dF(uv_rect->x(), uv_rect->y()); | 27 uv_cropped_rect += gfx::Vector2dF(uv_rect->x(), uv_rect->y()); |
| 28 | 28 |
| 29 *display_rect = display_cropped_rect; | 29 *display_rect = display_cropped_rect; |
| 30 *uv_rect = uv_cropped_rect; | 30 *uv_rect = uv_cropped_rect; |
| 31 } | 31 } |
| 32 | 32 |
| 33 } // namespace | 33 } // namespace |
| 34 | 34 |
| 35 OverlayStrategySandwich::OverlayStrategySandwich( |
| 36 OverlayCandidateValidator* capability_checker) |
| 37 : capability_checker_(capability_checker) { |
| 38 DCHECK(capability_checker); |
| 39 } |
| 40 |
| 35 OverlayStrategySandwich::~OverlayStrategySandwich() {} | 41 OverlayStrategySandwich::~OverlayStrategySandwich() {} |
| 36 | 42 |
| 37 OverlayResult OverlayStrategySandwich::TryOverlay( | 43 bool OverlayStrategySandwich::Attempt(RenderPassList* render_passes, |
| 38 OverlayCandidateValidator* capability_checker, | 44 OverlayCandidateList* candidate_list) { |
| 39 RenderPassList* render_passes_in_draw_order, | 45 QuadList& quad_list = render_passes->back()->quad_list; |
| 46 for (auto it = quad_list.begin(); it != quad_list.end();) { |
| 47 OverlayCandidate candidate; |
| 48 if (OverlayCandidate::FromDrawQuad(*it, &candidate)) |
| 49 it = TryOverlay(render_passes->back(), candidate_list, candidate, it); |
| 50 else |
| 51 ++it; |
| 52 } |
| 53 |
| 54 return candidate_list->size() > 1; |
| 55 } |
| 56 |
| 57 QuadList::Iterator OverlayStrategySandwich::TryOverlay( |
| 58 RenderPass* render_pass, |
| 40 OverlayCandidateList* candidate_list, | 59 OverlayCandidateList* candidate_list, |
| 41 const OverlayCandidate& candidate, | 60 const OverlayCandidate& candidate, |
| 42 QuadList::Iterator* candidate_iter_in_quad_list, | 61 QuadList::Iterator candidate_iter_in_quad_list) { |
| 43 float device_scale_factor) { | 62 QuadList& quad_list = render_pass->quad_list; |
| 44 RenderPass* root_render_pass = render_passes_in_draw_order->back(); | 63 gfx::Rect pixel_bounds = render_pass->output_rect; |
| 45 QuadList& quad_list = root_render_pass->quad_list; | |
| 46 gfx::Rect pixel_bounds = root_render_pass->output_rect; | |
| 47 | 64 |
| 48 const DrawQuad* candidate_quad = **candidate_iter_in_quad_list; | 65 const DrawQuad* candidate_quad = *candidate_iter_in_quad_list; |
| 49 const gfx::Transform& candidate_transform = | 66 const gfx::Transform& candidate_transform = |
| 50 candidate_quad->shared_quad_state->quad_to_target_transform; | 67 candidate_quad->shared_quad_state->quad_to_target_transform; |
| 51 gfx::Transform candidate_inverse_transform; | 68 gfx::Transform candidate_inverse_transform; |
| 52 if (!candidate_transform.GetInverse(&candidate_inverse_transform)) | 69 if (!candidate_transform.GetInverse(&candidate_inverse_transform)) |
| 53 return DID_NOT_CREATE_OVERLAY; | 70 return ++candidate_iter_in_quad_list; |
| 54 | 71 |
| 55 // Compute the candidate's rect in display space (pixels on the screen). | 72 // Compute the candidate's rect in display space (pixels on the screen). |
| 56 gfx::Rect candidate_pixel_rect = candidate.quad_rect_in_target_space; | 73 gfx::Rect candidate_pixel_rect = candidate.quad_rect_in_target_space; |
| 57 gfx::RectF candidate_uv_rect = candidate.uv_rect; | 74 gfx::RectF candidate_uv_rect = candidate.uv_rect; |
| 58 if (candidate.is_clipped && | 75 if (candidate.is_clipped && |
| 59 !candidate.clip_rect.Contains(candidate_pixel_rect)) { | 76 !candidate.clip_rect.Contains(candidate_pixel_rect)) { |
| 60 ClipDisplayAndUVRects(&candidate_pixel_rect, &candidate_uv_rect, | 77 ClipDisplayAndUVRects(&candidate_pixel_rect, &candidate_uv_rect, |
| 61 candidate.clip_rect); | 78 candidate.clip_rect); |
| 62 } | 79 } |
| 63 | 80 |
| 64 // Don't allow overlapping overlays for now. | 81 // Don't allow overlapping overlays for now. |
| 65 for (const OverlayCandidate& other_candidate : *candidate_list) { | 82 for (const OverlayCandidate& other_candidate : *candidate_list) { |
| 66 if (other_candidate.display_rect.Intersects(candidate.display_rect) && | 83 if (other_candidate.display_rect.Intersects(candidate.display_rect) && |
| 67 other_candidate.plane_z_order == 1) { | 84 other_candidate.plane_z_order == 1) { |
| 68 return DID_NOT_CREATE_OVERLAY; | 85 return ++candidate_iter_in_quad_list; |
| 69 } | 86 } |
| 70 } | 87 } |
| 71 | 88 |
| 72 // Iterate through the quads in front of |candidate|, and compute the region | 89 // Iterate through the quads in front of |candidate|, and compute the region |
| 73 // of |candidate| that is covered. | 90 // of |candidate| that is covered. |
| 74 Region pixel_covered_region; | 91 Region pixel_covered_region; |
| 75 for (auto overlap_iter = quad_list.cbegin(); | 92 for (auto overlap_iter = quad_list.cbegin(); |
| 76 overlap_iter != *candidate_iter_in_quad_list; ++overlap_iter) { | 93 overlap_iter != candidate_iter_in_quad_list; ++overlap_iter) { |
| 77 if (OverlayStrategyCommon::IsInvisibleQuad(*overlap_iter)) | 94 if (OverlayCandidate::IsInvisibleQuad(*overlap_iter)) |
| 78 continue; | 95 continue; |
| 79 // Compute the quad's bounds in display space. | 96 // Compute the quad's bounds in display space. |
| 80 gfx::Rect pixel_covered_rect = MathUtil::MapEnclosingClippedRect( | 97 gfx::Rect pixel_covered_rect = MathUtil::MapEnclosingClippedRect( |
| 81 overlap_iter->shared_quad_state->quad_to_target_transform, | 98 overlap_iter->shared_quad_state->quad_to_target_transform, |
| 82 overlap_iter->rect); | 99 overlap_iter->rect); |
| 83 | 100 |
| 84 // Include the intersection of that quad with the candidate's quad in the | 101 // Include the intersection of that quad with the candidate's quad in the |
| 85 // covered region. | 102 // covered region. |
| 86 pixel_covered_rect.Intersect(candidate_pixel_rect); | 103 pixel_covered_rect.Intersect(candidate_pixel_rect); |
| 87 pixel_covered_region.Union(pixel_covered_rect); | 104 pixel_covered_region.Union(pixel_covered_rect); |
| (...skipping 20 matching lines...) Expand all Loading... |
| 108 main_image_on_top.uv_rect = gfx::RectF(pixel_covered_rect); | 125 main_image_on_top.uv_rect = gfx::RectF(pixel_covered_rect); |
| 109 main_image_on_top.uv_rect.Scale(1.f / pixel_bounds.width(), | 126 main_image_on_top.uv_rect.Scale(1.f / pixel_bounds.width(), |
| 110 1.f / pixel_bounds.height()); | 127 1.f / pixel_bounds.height()); |
| 111 main_image_on_top.plane_z_order = 2; | 128 main_image_on_top.plane_z_order = 2; |
| 112 main_image_on_top.transform = gfx::OVERLAY_TRANSFORM_NONE; | 129 main_image_on_top.transform = gfx::OVERLAY_TRANSFORM_NONE; |
| 113 main_image_on_top.use_output_surface_for_resource = true; | 130 main_image_on_top.use_output_surface_for_resource = true; |
| 114 new_candidate_list.push_back(main_image_on_top); | 131 new_candidate_list.push_back(main_image_on_top); |
| 115 } | 132 } |
| 116 | 133 |
| 117 // Check for support. | 134 // Check for support. |
| 118 capability_checker->CheckOverlaySupport(&new_candidate_list); | 135 capability_checker_->CheckOverlaySupport(&new_candidate_list); |
| 119 for (const OverlayCandidate& candidate : new_candidate_list) { | 136 for (const OverlayCandidate& candidate : new_candidate_list) { |
| 120 if (!candidate.overlay_handled) | 137 if (!candidate.overlay_handled) |
| 121 return DID_NOT_CREATE_OVERLAY; | 138 return ++candidate_iter_in_quad_list; |
| 122 } | 139 } |
| 123 | 140 |
| 124 // Remove the quad for the overlay quad. Replace it with a transparent quad | 141 // Remove the quad for the overlay quad. Replace it with a transparent quad |
| 125 // if we're putting a new overlay on top. | 142 // if we're putting a new overlay on top. |
| 126 if (pixel_covered_rects.empty()) { | 143 if (pixel_covered_rects.empty()) { |
| 127 *candidate_iter_in_quad_list = | 144 candidate_iter_in_quad_list = |
| 128 quad_list.EraseAndInvalidateAllPointers(*candidate_iter_in_quad_list); | 145 quad_list.EraseAndInvalidateAllPointers(candidate_iter_in_quad_list); |
| 129 } else { | 146 } else { |
| 130 // Cache the information from the candidate quad that we'll need to | 147 // Cache the information from the candidate quad that we'll need to |
| 131 // construct the solid color quads. | 148 // construct the solid color quads. |
| 132 const SharedQuadState* candidate_shared_quad_state = | 149 const SharedQuadState* candidate_shared_quad_state = |
| 133 candidate_quad->shared_quad_state; | 150 candidate_quad->shared_quad_state; |
| 134 const gfx::Rect candidate_rect = candidate_quad->rect; | 151 const gfx::Rect candidate_rect = candidate_quad->rect; |
| 135 | 152 |
| 136 // Reserve space in the quad list for the transparent quads. | 153 // Reserve space in the quad list for the transparent quads. |
| 137 quad_list.ReplaceExistingElement<SolidColorDrawQuad>( | 154 quad_list.ReplaceExistingElement<SolidColorDrawQuad>( |
| 138 *candidate_iter_in_quad_list); | 155 candidate_iter_in_quad_list); |
| 139 *candidate_iter_in_quad_list = | 156 candidate_iter_in_quad_list = |
| 140 quad_list.InsertBeforeAndInvalidateAllPointers<SolidColorDrawQuad>( | 157 quad_list.InsertBeforeAndInvalidateAllPointers<SolidColorDrawQuad>( |
| 141 *candidate_iter_in_quad_list, pixel_covered_rects.size() - 1); | 158 candidate_iter_in_quad_list, pixel_covered_rects.size() - 1); |
| 142 | 159 |
| 143 // Cover the region with transparent quads. | 160 // Cover the region with transparent quads. |
| 144 for (const gfx::Rect& pixel_covered_rect : pixel_covered_rects) { | 161 for (const gfx::Rect& pixel_covered_rect : pixel_covered_rects) { |
| 145 gfx::Rect quad_space_covered_rect = MathUtil::MapEnclosingClippedRect( | 162 gfx::Rect quad_space_covered_rect = MathUtil::MapEnclosingClippedRect( |
| 146 candidate_inverse_transform, pixel_covered_rect); | 163 candidate_inverse_transform, pixel_covered_rect); |
| 147 quad_space_covered_rect.Intersect(candidate_rect); | 164 quad_space_covered_rect.Intersect(candidate_rect); |
| 148 | 165 |
| 149 SolidColorDrawQuad* transparent_quad = | 166 SolidColorDrawQuad* transparent_quad = |
| 150 static_cast<SolidColorDrawQuad*>(**candidate_iter_in_quad_list); | 167 static_cast<SolidColorDrawQuad*>(*candidate_iter_in_quad_list); |
| 151 transparent_quad->SetAll(candidate_shared_quad_state, | 168 transparent_quad->SetAll(candidate_shared_quad_state, |
| 152 quad_space_covered_rect, quad_space_covered_rect, | 169 quad_space_covered_rect, quad_space_covered_rect, |
| 153 quad_space_covered_rect, false, | 170 quad_space_covered_rect, false, |
| 154 SK_ColorTRANSPARENT, true); | 171 SK_ColorTRANSPARENT, true); |
| 155 ++(*candidate_iter_in_quad_list); | 172 ++candidate_iter_in_quad_list; |
| 156 } | 173 } |
| 157 } | 174 } |
| 158 | 175 |
| 159 candidate_list->swap(new_candidate_list); | 176 candidate_list->swap(new_candidate_list); |
| 160 return CREATED_OVERLAY_KEEP_LOOKING; | 177 return candidate_iter_in_quad_list; |
| 161 } | 178 } |
| 162 | 179 |
| 163 } // namespace cc | 180 } // namespace cc |
| OLD | NEW |