Index: cc/surfaces/surface.cc |
diff --git a/cc/surfaces/surface.cc b/cc/surfaces/surface.cc |
index 16987cb84e49b356bd2cf4afa0fd255f9ddf82a6..5fcba9f2b18eaa3c1bf683de1e170b9cde1f6919 100644 |
--- a/cc/surfaces/surface.cc |
+++ b/cc/surfaces/surface.cc |
@@ -14,6 +14,14 @@ |
namespace cc { |
+namespace { |
+template <typename Collection, typename Value> |
+void EraseValueAndCompact(Collection* collection, const Value& value) { |
+ collection->erase(std::remove(collection->begin(), collection->end(), value), |
+ collection->end()); |
+} |
+} // namespace |
+ |
// The frame index starts at 2 so that empty frames will be treated as |
// completely damaged the first time they're drawn from. |
static const int kFrameIndexStart = 2; |
@@ -35,6 +43,9 @@ Surface::~Surface() { |
} |
if (!draw_callback_.is_null()) |
draw_callback_.Run(SurfaceDrawStatus::DRAW_SKIPPED); |
+ |
+ if (factory_) |
+ factory_->SetBeginFrameSource(surface_id_, NULL); |
} |
void Surface::QueueFrame(scoped_ptr<CompositorFrame> frame, |
@@ -164,6 +175,44 @@ void Surface::SatisfyDestructionDependencies( |
destruction_dependencies_.end()); |
} |
+void Surface::AddBeginFrameSource(BeginFrameSource* begin_frame_source) { |
+ DCHECK(base::STLIsSorted(begin_frame_sources_)); |
+ |
+ // Find the insertion point. |
+ auto insert_index = begin_frame_sources_.begin(); |
+ while (insert_index != begin_frame_sources_.end()) { |
+ if (begin_frame_source < *insert_index) |
+ break; |
+ insert_index++; |
+ } |
+ |
+ // Verify it doesn't already exist and insert it. |
+ DCHECK(insert_index == begin_frame_sources_.end() || |
+ *insert_index != begin_frame_source); |
+ begin_frame_sources_.insert(insert_index, begin_frame_source); |
+ UpdatePrimaryBeginFrameSource(); |
+} |
+ |
+void Surface::RemoveBeginFrameSource(BeginFrameSource* begin_frame_source) { |
+ DCHECK(ContainsValue(begin_frame_sources_, begin_frame_source)); |
+ EraseValueAndCompact(&begin_frame_sources_, begin_frame_source); |
+ UpdatePrimaryBeginFrameSource(); |
+} |
+ |
+void Surface::UpdatePrimaryBeginFrameSource() { |
+ // Ensure the BeginFrameSources are sorted so our we make a stable decision |
+ // regarding which source is primary. |
+ // TODO(brianderson): Do something smarter based on coverage instead. |
+ DCHECK(base::STLIsSorted(begin_frame_sources_)); |
+ |
+ BeginFrameSource* primary_source = nullptr; |
+ if (!begin_frame_sources_.empty()) |
+ primary_source = begin_frame_sources_[0]; |
+ |
+ if (factory_) |
+ factory_->SetBeginFrameSource(surface_id_, primary_source); |
+} |
+ |
void Surface::ClearCopyRequests() { |
if (current_frame_) { |
for (const auto& render_pass : |