Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(107)

Side by Side Diff: cc/scheduler/begin_frame_source.h

Issue 267783004: Refactoring the way begin frame sources inside scheduler work. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Small fix. Created 6 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
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 #ifndef CC_SCHEDULER_BEGIN_FRAME_SOURCE_H_
6 #define CC_SCHEDULER_BEGIN_FRAME_SOURCE_H_
7
8 #include <set>
9 #include <string>
10
11 #include "base/debug/trace_event.h"
12 #include "base/logging.h"
13 #include "cc/output/begin_frame_args.h"
14 #include "cc/output/vsync_parameter_observer.h"
15 #include "cc/scheduler/delay_based_time_source.h"
16
17 namespace cc {
18
19 // (Pure) Interface for observing BeginFrame messages from BeginFrameSource
20 // objects.
21 class CC_EXPORT BeginFrameObserver {
22 public:
23 // The |args| given to OnBeginFrame is guaranteed to have
24 // |args|.IsValid()==true and have |args|.frame_time
25 // field be strictly greater than the previous call.
26 //
27 // Side effects: This function can (and most of the time *will*) change the
28 // return value of the LastUsedBeginFrameArgs method. See the documentation
29 // on that method for more information.
30 virtual void OnBeginFrame(const BeginFrameArgs& args) = 0;
31
32 // Some frame sources *may* provide the last missed begin frame when
33 // SetNeedsBeginFrames is set true (such as the SyntheticBeginFrameSource).
34 //
35 // **Don't** depend on this function ever being called.
36 virtual void OnMissedBeginFrame(const BeginFrameArgs& args) = 0;
37
38 // Returns the last BeginFrameArgs used by the observer. This method's return
39 // value is affected by the OnBeginFrame method!
40 //
41 // - Before the first call of OnBeginFrame, this method should return a
42 // BeginFrameArgs on which IsValid() returns false.
43 //
44 // - If the |args| passed to OnBeginFrame is (or *will be*) used, then
45 // LastUsedBeginFrameArgs return value should become the |args| given to
46 // OnBeginFrame.
47 //
48 // - If the |args| passed to OnBeginFrame is dropped, then
49 // LastUsedBeginFrameArgs return value should *not* change.
50 //
51 // These requirements are designed to allow chaining and nesting of
52 // BeginFrameObservers which filter the incoming BeginFrame messages while
53 // preventing "double dropping" and other bad side effects.
54 virtual const BeginFrameArgs LastUsedBeginFrameArgs() const = 0;
55
56 // Tracing support
57 virtual void AsValueInto(base::debug::TracedValue* dict) const = 0;
58 };
59
60 // Simple mix in which implements a BeginFrameObserver which checks the
61 // incoming values meet the BeginFrameObserver requirements and implements the
62 // required LastUsedBeginFrameArgs behaviour.
63 //
64 // Users of this mix in should;
65 // - Implement the ProcessBeginFrameArgs function.
66 // - Recommended (but not required) to call
67 // BeginFrameObserverMixIn::OnValueInto in their overridden OnValueInto
68 // function.
69 //
70 // Advance observers may also wish to override the OnMissedBeginFrame method.
71 class CC_EXPORT BeginFrameObserverMixIn : public BeginFrameObserver {
72 public:
73 // BeginFrameObserver
74 BeginFrameObserverMixIn();
75
76 // Traces |args| and DCHECK |args| satisfies pre-conditions then calls
77 // ProcessBeginFrameArgs and updates the last_begin_frame_args_ value on true.
78 virtual void OnBeginFrame(const BeginFrameArgs& args) OVERRIDE;
79
80 // Forwards call to the OnBeginFrame callback.
81 virtual void OnMissedBeginFrame(const BeginFrameArgs& args) OVERRIDE;
82
83 virtual const BeginFrameArgs LastUsedBeginFrameArgs() const OVERRIDE;
84
85 // Outputs last_begin_frame_args_
86 virtual void AsValueInto(base::debug::TracedValue* dict) const OVERRIDE;
87
88 protected:
89 // Subclasses should override this method!
90 // Return true if the given argument is (or will be) used.
91 virtual bool ProcessBeginFrameArgs(const BeginFrameArgs& args) = 0;
92 virtual bool ProcessMissedBeginFrameArgs(const BeginFrameArgs& args);
brianderson 2014/09/24 22:45:38 Was imagining this would be pure virtual. Also, I
danakj 2014/09/24 23:35:24 +1. Please avoid situations where we have non-pure
danakj 2014/09/24 23:59:25 (Or classes that mix pure virtual and concrete vir
mithro-old 2014/09/25 01:53:00 I'd really like implementation of this method to b
mithro-old 2014/09/25 01:53:00 How do you provide "default" implementations witho
danakj 2014/09/27 00:05:34 Brian and I talked about this some more the other
93
94 BeginFrameArgs last_begin_frame_args_;
95 int64_t dropped_begin_frame_args_;
96 };
97
98 // Interface for a class which produces BeginFrame calls to a
99 // BeginFrameObserver.
100 //
101 // BeginFrame calls *normally* occur just after a vsync interrupt when input
102 // processing has been finished and provide information about the time values
103 // of the vsync times. *However*, these values can be heavily modified or even
104 // plain made up (when no vsync signal is available or vsync throttling is
105 // turned off). See the BeginFrameObserver for information about the guarantees
106 // all BeginFrameSources *must* provide.
107 //
108 // Implementation classes should:
109 // - Use the CallOn(Missed)BeginFrame method to call to the observer(s).
110 // - Implement the pure virtual methods.
111 // - Recommend (but not required) to call BeginFrameSource::AsValueInto in
112 // their own AsValueInto implementation.
113 class CC_EXPORT BeginFrameSource {
114 public:
115 virtual ~BeginFrameSource() {}
116
117 // SetNeedsBeginFrames is the on/off "switch" for the BeginFrameSource. When
118 // set to false no more BeginFrame messages should be sent to observer.
119 virtual bool NeedsBeginFrames() const = 0;
120 virtual void SetNeedsBeginFrames(bool needs_begin_frames) = 0;
121
122 // DidFinishFrame provides back pressure to a frame source about frame
123 // processing (rather than toggling SetNeedsBeginFrames every frame). It is
124 // used by systems like the BackToBackFrameSource to make sure only one frame
125 // is pending at a time.
126 virtual void DidFinishFrame(size_t remaining_frames) = 0;
127
128 // Add/Remove and observer from the source.
129 // *At the moment* only a single observer can be added to the source, however
130 // in the future this may be extended to allow multiple observers.
131 // If making this change, please use base::ObserverList to do so.
132 void AddObserver(BeginFrameObserver* obs);
133 void RemoveObserver(BeginFrameObserver* obs);
134
135 // Tracing support - Recommend (but not required) to call this implementation
136 // in any override.
137 virtual void AsValueInto(base::debug::TracedValue* dict) const;
138
139 protected:
140 BeginFrameSource();
141
142 // These methods should be used by subclasses to make the call to the
143 // observers.
144 void CallOnBeginFrame(const BeginFrameArgs& args);
145 void CallOnMissedBeginFrame(const BeginFrameArgs& args);
146
147 BeginFrameObserver* observer_;
148
149 private:
150 bool inside_as_value_into_;
151 };
152
153 // A frame source which calls BeginFrame (at the next possible time) as soon as
154 // remaining frames reaches zero.
155 class CC_EXPORT BackToBackBeginFrameSource : public BeginFrameSource {
156 public:
157 static scoped_ptr<BackToBackBeginFrameSource> Create(
158 base::SingleThreadTaskRunner* task_runner);
159 virtual ~BackToBackBeginFrameSource();
160
161 // BeginFrameSource
162 virtual bool NeedsBeginFrames() const OVERRIDE;
163 virtual void SetNeedsBeginFrames(bool needs_begin_frames) OVERRIDE;
164 virtual void DidFinishFrame(size_t remaining_frames) OVERRIDE;
165
166 // Tracing
167 virtual void AsValueInto(base::debug::TracedValue* dict) const OVERRIDE;
168
169 protected:
170 explicit BackToBackBeginFrameSource(
171 base::SingleThreadTaskRunner* task_runner);
172 virtual base::TimeTicks Now(); // Now overridable for testing
173
174 base::WeakPtrFactory<BackToBackBeginFrameSource> weak_factory_;
175 base::SingleThreadTaskRunner* task_runner_;
176
177 bool needs_begin_frames_;
178 bool send_begin_frame_posted_;
179
180 void ScheduleBeginFrame();
181 void BeginFrame();
182 };
183
184 // A frame source which is locked to an external parameters provides from a
185 // vsync source and generates BeginFrameArgs for it.
186 class CC_EXPORT SyntheticBeginFrameSource : public BeginFrameSource,
187 public VSyncParameterObserver,
188 public TimeSourceClient {
189 public:
190 static scoped_ptr<SyntheticBeginFrameSource> Create(
191 base::SingleThreadTaskRunner* task_runner,
192 base::TimeTicks initial_vsync_timebase,
193 base::TimeDelta initial_vsync_interval);
194 virtual ~SyntheticBeginFrameSource();
195
196 // BeginFrameSource
197 virtual bool NeedsBeginFrames() const OVERRIDE;
198 virtual void SetNeedsBeginFrames(bool needs_begin_frames) OVERRIDE;
199 virtual void DidFinishFrame(size_t remaining_frames) OVERRIDE{};
200
201 // Tracing
202 virtual void AsValueInto(base::debug::TracedValue* dict) const OVERRIDE;
203
204 // VSyncParameterObserver
205 virtual void OnUpdateVSyncParameters(
206 base::TimeTicks new_vsync_timebase,
207 base::TimeDelta new_vsync_interval) OVERRIDE;
208
209 // TimeSourceClient
210 virtual void OnTimerTick() OVERRIDE;
211
212 protected:
213 explicit SyntheticBeginFrameSource(
214 scoped_refptr<DelayBasedTimeSource> time_source);
215
216 void SendBeginFrameFromTick(base::TimeTicks frame_time);
217
218 scoped_refptr<DelayBasedTimeSource> time_source_;
219 };
220
221 // A "virtual" frame source which lets you switch between multiple other frame
222 // sources while making sure the BeginFrameArgs stays increasing (possibly
223 // enforcing minimum boundry between BeginFrameArgs messages).
224 class CC_EXPORT BeginFrameSourceMultiplexer : public BeginFrameSource,
225 public BeginFrameObserver {
226 public:
227 static scoped_ptr<BeginFrameSourceMultiplexer> Create();
228 virtual ~BeginFrameSourceMultiplexer();
229
230 void SetMinimumInterval(base::TimeDelta new_minimum_interval);
231
232 void AddSource(BeginFrameSource* new_source);
233 void RemoveSource(BeginFrameSource* existing_source);
234 void SetActiveSource(BeginFrameSource* new_source);
235 const BeginFrameSource* ActiveSource();
236
237 // BeginFrameObserver
238 // The mux is an BeginFrameObserver as it needs to proxy the OnBeginFrame
239 // calls to preserve the monotonicity of the BeginFrameArgs when switching
240 // sources.
241 virtual void OnBeginFrame(const BeginFrameArgs& args) OVERRIDE;
242 virtual void OnMissedBeginFrame(const BeginFrameArgs& args) OVERRIDE;
243 virtual const BeginFrameArgs LastUsedBeginFrameArgs() const OVERRIDE;
244
245 // BeginFrameSource
246 virtual bool NeedsBeginFrames() const OVERRIDE;
247 virtual void SetNeedsBeginFrames(bool needs_begin_frames) OVERRIDE;
248 virtual void DidFinishFrame(size_t remaining_frames) OVERRIDE;
249
250 // Tracing
251 virtual void AsValueInto(base::debug::TracedValue* dict) const OVERRIDE;
252
253 protected:
254 BeginFrameSourceMultiplexer();
255 explicit BeginFrameSourceMultiplexer(base::TimeDelta minimum_interval);
256
257 bool HasSource(BeginFrameSource* source);
258 bool IsIncreasing(const BeginFrameArgs& args);
259
260 base::TimeDelta minimum_interval_;
261
262 BeginFrameSource* active_source_;
263 std::set<BeginFrameSource*> source_list_;
264 };
265
266 } // namespace cc
267
268 #endif // CC_SCHEDULER_BEGIN_FRAME_SOURCE_H_
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698