Index: cc/scheduler/begin_frame_source.cc |
diff --git a/cc/scheduler/begin_frame_source.cc b/cc/scheduler/begin_frame_source.cc |
index 42b8f6f1c735db05dfca52c00ed6070bb8b63a36..43a84bda571190f47d2e87e4886abaa5996004d1 100644 |
--- a/cc/scheduler/begin_frame_source.cc |
+++ b/cc/scheduler/begin_frame_source.cc |
@@ -60,7 +60,91 @@ void BeginFrameObserverMixIn::AsValueInto( |
dict->SetInteger("dropped_begin_frame_args_", dropped_begin_frame_args_); |
} |
-// BeginFrameSourceMixIn ------------------------------------------------------ |
+// BeginFrameObserverMultiplexer ------------------------------------------ |
+BeginFrameObserverMultiplexer::BeginFrameObserverMultiplexer() |
+ : last_callback_state_(false), has_observers_callback_() { |
+} |
+ |
+BeginFrameObserverMultiplexer::~BeginFrameObserverMultiplexer() { |
simonhong
2015/03/25 02:03:21
How about checking empty() of observer list?
mithro-old
2015/03/25 02:34:47
Do we (and should we) require a user to remove all
|
+ observer_list_.Clear(); |
+ CallCallbackOnChange(); |
+} |
+ |
+scoped_ptr<BeginFrameObserverMultiplexer> |
+BeginFrameObserverMultiplexer::Create() { |
+ return make_scoped_ptr(new BeginFrameObserverMultiplexer()); |
+} |
+ |
+void BeginFrameObserverMultiplexer::AddObserver(BeginFrameObserver* obs) { |
simonhong
2015/03/25 02:03:21
As you can see in my previous landed cl (https://c
mithro-old
2015/03/25 02:34:47
I'm not sure what you are saying here? This code a
|
+ DCHECK(!observer_list_.HasObserver(obs)); |
+ // If have a LastBeginFrameArgs is still effective, send it to the new |
+ // |obs| immediately. |
+ if (last_begin_frame_args_.IsValid() && |
+ obs->LastUsedBeginFrameArgs().frame_time < |
+ last_begin_frame_args_.frame_time) { |
+ BeginFrameArgs missed = last_begin_frame_args_; |
+ missed.type = BeginFrameArgs::MISSED; |
+ obs->OnBeginFrame(missed); |
+ } |
+ observer_list_.AddObserver(obs); |
+ CallCallbackOnChange(); |
+} |
+ |
+void BeginFrameObserverMultiplexer::RemoveObserver(BeginFrameObserver* obs) { |
+ DCHECK(observer_list_.HasObserver(obs)); |
+ observer_list_.RemoveObserver(obs); |
+ CallCallbackOnChange(); |
+} |
+ |
+bool BeginFrameObserverMultiplexer::HasObservers() { |
+ return observer_list_.might_have_observers(); |
simonhong
2015/03/25 02:03:21
Also in my previous cl, there is some suggestion.
mithro-old
2015/03/25 02:34:47
Looking at the ObserverList implementation, the re
|
+} |
+ |
+void BeginFrameObserverMultiplexer::SetHasObserverCallback( |
+ const HasObserversCallback& cb) { |
+ if (last_callback_state_ != false) |
+ CallCallback(false); |
+ has_observers_callback_ = cb; |
+ CallCallback(HasObservers()); |
+} |
+ |
+void BeginFrameObserverMultiplexer::AsValueInto( |
+ base::trace_event::TracedValue* dict) const { |
+ BeginFrameObserverMixIn::AsValueInto(dict); |
+ if (observer_list_.might_have_observers()) { |
+ ObserverList<BeginFrameObserver>::Iterator it( |
+ const_cast<ObserverList<BeginFrameObserver>*>(&observer_list_)); |
+ BeginFrameObserver* obs; |
+ dict->BeginArray("observers"); |
+ while ((obs = it.GetNext()) != NULL) { |
+ dict->BeginDictionary(); |
+ obs->AsValueInto(dict); |
+ dict->EndDictionary(); |
+ } |
+ dict->EndArray(); |
+ } |
+} |
+ |
+bool BeginFrameObserverMultiplexer::OnBeginFrameMixInDelegate( |
+ const BeginFrameArgs& args) { |
+ FOR_EACH_OBSERVER(BeginFrameObserver, observer_list_, OnBeginFrame(args)); |
+ return true; |
+} |
+ |
+void BeginFrameObserverMultiplexer::CallCallbackOnChange() { |
+ if (HasObservers() == last_callback_state_) |
+ return; |
+ CallCallback(HasObservers()); |
+} |
+ |
+void BeginFrameObserverMultiplexer::CallCallback(bool has_observers) { |
+ if (!has_observers_callback_.is_null()) { |
+ has_observers_callback_.Run(has_observers); |
+ last_callback_state_ = has_observers; |
+ } |
+} |
+ |
+// BeginFrameSourceMixIn -------------------------------------------------- |
BeginFrameSourceMixIn::BeginFrameSourceMixIn() |
: observer_(NULL), |
needs_begin_frames_(false), |