Enable snappy for IndexedDB.
[chromium-blink-merge.git] / ash / wm / video_detector_unittest.cc
blob01c79cf879746bf9b9d2deb5a2deec1bfcfa8263
1 // Copyright (c) 2012 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.
5 #include "ash/wm/video_detector.h"
7 #include "ash/shell.h"
8 #include "ash/test/ash_test_base.h"
9 #include "ash/wm/window_util.h"
10 #include "base/compiler_specific.h"
11 #include "base/memory/scoped_ptr.h"
12 #include "base/time/time.h"
13 #include "third_party/skia/include/core/SkColor.h"
14 #include "ui/aura/client/aura_constants.h"
15 #include "ui/aura/client/window_types.h"
16 #include "ui/aura/root_window.h"
17 #include "ui/aura/test/test_windows.h"
18 #include "ui/aura/window.h"
19 #include "ui/gfx/rect.h"
21 namespace ash {
22 namespace test {
24 // Implementation that just counts the number of times we've been told that a
25 // video is playing.
26 class TestVideoDetectorObserver : public VideoDetectorObserver {
27 public:
28 TestVideoDetectorObserver() : num_invocations_(0),
29 num_fullscreens_(0),
30 num_not_fullscreens_(0) {}
32 int num_invocations() const { return num_invocations_; }
33 int num_fullscreens() const { return num_fullscreens_; }
34 int num_not_fullscreens() const { return num_not_fullscreens_; }
35 void reset_stats() {
36 num_invocations_ = 0;
37 num_fullscreens_ = 0;
38 num_not_fullscreens_ = 0;
41 // VideoDetectorObserver implementation.
42 virtual void OnVideoDetected(bool is_fullscreen) OVERRIDE {
43 num_invocations_++;
44 if (is_fullscreen)
45 num_fullscreens_++;
46 else
47 num_not_fullscreens_++;
50 private:
51 // Number of times that OnVideoDetected() has been called.
52 int num_invocations_;
53 // Number of times that OnVideoDetected() has been called with is_fullscreen
54 // == true.
55 int num_fullscreens_;
56 // Number of times that OnVideoDetected() has been called with is_fullscreen
57 // == false.
58 int num_not_fullscreens_;
60 DISALLOW_COPY_AND_ASSIGN(TestVideoDetectorObserver);
63 class VideoDetectorTest : public AshTestBase {
64 public:
65 VideoDetectorTest() {}
66 virtual ~VideoDetectorTest() {}
68 virtual void SetUp() OVERRIDE {
69 AshTestBase::SetUp();
70 observer_.reset(new TestVideoDetectorObserver);
71 detector_ = Shell::GetInstance()->video_detector();
72 detector_->AddObserver(observer_.get());
74 now_ = base::TimeTicks::Now();
75 detector_->set_now_for_test(now_);
78 virtual void TearDown() OVERRIDE {
79 detector_->RemoveObserver(observer_.get());
80 AshTestBase::TearDown();
83 protected:
84 // Move |detector_|'s idea of the current time forward by |delta|.
85 void AdvanceTime(base::TimeDelta delta) {
86 now_ += delta;
87 detector_->set_now_for_test(now_);
90 VideoDetector* detector_; // not owned
92 scoped_ptr<TestVideoDetectorObserver> observer_;
94 base::TimeTicks now_;
96 private:
97 DISALLOW_COPY_AND_ASSIGN(VideoDetectorTest);
100 TEST_F(VideoDetectorTest, Basic) {
101 gfx::Rect window_bounds(gfx::Point(), gfx::Size(1024, 768));
102 scoped_ptr<aura::Window> window(
103 CreateTestWindowInShell(SK_ColorRED, 12345, window_bounds));
105 // Send enough updates, but make them be too small to trigger detection.
106 gfx::Rect update_region(
107 gfx::Point(),
108 gfx::Size(VideoDetector::kMinUpdateWidth - 1,
109 VideoDetector::kMinUpdateHeight));
110 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
111 detector_->OnWindowPaintScheduled(window.get(), update_region);
112 EXPECT_EQ(0, observer_->num_invocations());
114 // Send not-quite-enough adaquately-sized updates.
115 observer_->reset_stats();
116 AdvanceTime(base::TimeDelta::FromSeconds(2));
117 update_region.set_size(
118 gfx::Size(VideoDetector::kMinUpdateWidth,
119 VideoDetector::kMinUpdateHeight));
120 for (int i = 0; i < VideoDetector::kMinFramesPerSecond - 1; ++i)
121 detector_->OnWindowPaintScheduled(window.get(), update_region);
122 EXPECT_EQ(0, observer_->num_invocations());
124 // We should get notified after the next update, but not in response to
125 // additional updates.
126 detector_->OnWindowPaintScheduled(window.get(), update_region);
127 EXPECT_EQ(1, observer_->num_invocations());
128 EXPECT_EQ(0, observer_->num_fullscreens());
129 EXPECT_EQ(1, observer_->num_not_fullscreens());
130 detector_->OnWindowPaintScheduled(window.get(), update_region);
131 EXPECT_EQ(1, observer_->num_invocations());
132 EXPECT_EQ(0, observer_->num_fullscreens());
133 EXPECT_EQ(1, observer_->num_not_fullscreens());
135 // Spread out the frames over a longer period of time, but send enough
136 // over a one-second window that the observer should be notified.
137 observer_->reset_stats();
138 AdvanceTime(base::TimeDelta::FromSeconds(2));
139 detector_->OnWindowPaintScheduled(window.get(), update_region);
140 EXPECT_EQ(0, observer_->num_invocations());
142 AdvanceTime(base::TimeDelta::FromMilliseconds(500));
143 const int kNumFrames = VideoDetector::kMinFramesPerSecond + 1;
144 base::TimeDelta kInterval =
145 base::TimeDelta::FromMilliseconds(1000 / kNumFrames);
146 for (int i = 0; i < kNumFrames; ++i) {
147 AdvanceTime(kInterval);
148 detector_->OnWindowPaintScheduled(window.get(), update_region);
150 EXPECT_EQ(1, observer_->num_invocations());
152 // Keep going and check that the observer is notified again.
153 for (int i = 0; i < kNumFrames; ++i) {
154 AdvanceTime(kInterval);
155 detector_->OnWindowPaintScheduled(window.get(), update_region);
157 EXPECT_EQ(2, observer_->num_invocations());
159 // Send updates at a slower rate and check that the observer isn't notified.
160 base::TimeDelta kSlowInterval = base::TimeDelta::FromMilliseconds(
161 1000 / (VideoDetector::kMinFramesPerSecond - 2));
162 for (int i = 0; i < kNumFrames; ++i) {
163 AdvanceTime(kSlowInterval);
164 detector_->OnWindowPaintScheduled(window.get(), update_region);
166 EXPECT_EQ(2, observer_->num_invocations());
169 TEST_F(VideoDetectorTest, Shutdown) {
170 gfx::Rect window_bounds(gfx::Point(), gfx::Size(1024, 768));
171 scoped_ptr<aura::Window> window(
172 CreateTestWindowInShell(SK_ColorRED, 12345, window_bounds));
173 gfx::Rect update_region(
174 gfx::Point(),
175 gfx::Size(VideoDetector::kMinUpdateWidth,
176 VideoDetector::kMinUpdateHeight));
178 // It should not detect video during the shutdown.
179 Shell::GetInstance()->OnAppTerminating();
180 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
181 detector_->OnWindowPaintScheduled(window.get(), update_region);
182 EXPECT_EQ(0, observer_->num_invocations());
185 TEST_F(VideoDetectorTest, WindowNotVisible) {
186 gfx::Rect window_bounds(gfx::Point(), gfx::Size(1024, 768));
187 scoped_ptr<aura::Window> window(
188 CreateTestWindowInShell(SK_ColorRED, 12345, window_bounds));
190 // Reparent the window to the root to make sure that visibility changes aren't
191 // animated.
192 Shell::GetPrimaryRootWindow()->AddChild(window.get());
194 // We shouldn't report video that's played in a hidden window.
195 window->Hide();
196 gfx::Rect update_region(
197 gfx::Point(),
198 gfx::Size(VideoDetector::kMinUpdateWidth,
199 VideoDetector::kMinUpdateHeight));
200 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
201 detector_->OnWindowPaintScheduled(window.get(), update_region);
202 EXPECT_EQ(0, observer_->num_invocations());
204 // Make the window visible and send more updates.
205 observer_->reset_stats();
206 AdvanceTime(base::TimeDelta::FromSeconds(2));
207 window->Show();
208 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
209 detector_->OnWindowPaintScheduled(window.get(), update_region);
210 EXPECT_EQ(1, observer_->num_invocations());
211 EXPECT_EQ(0, observer_->num_fullscreens());
212 EXPECT_EQ(1, observer_->num_not_fullscreens());
214 // We also shouldn't report video in a window that's fully offscreen.
215 observer_->reset_stats();
216 AdvanceTime(base::TimeDelta::FromSeconds(2));
217 gfx::Rect offscreen_bounds(
218 gfx::Point(Shell::GetPrimaryRootWindow()->bounds().width(), 0),
219 window_bounds.size());
220 window->SetBounds(offscreen_bounds);
221 ASSERT_EQ(offscreen_bounds, window->bounds());
222 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
223 detector_->OnWindowPaintScheduled(window.get(), update_region);
224 EXPECT_EQ(0, observer_->num_invocations());
227 TEST_F(VideoDetectorTest, MultipleWindows) {
228 // Create two windows.
229 gfx::Rect window_bounds(gfx::Point(), gfx::Size(1024, 768));
230 scoped_ptr<aura::Window> window1(
231 CreateTestWindowInShell(SK_ColorRED, 12345, window_bounds));
232 scoped_ptr<aura::Window> window2(
233 CreateTestWindowInShell(SK_ColorBLUE, 23456, window_bounds));
235 // Even if there's video playing in both, the observer should only receive a
236 // single notification.
237 gfx::Rect update_region(
238 gfx::Point(),
239 gfx::Size(VideoDetector::kMinUpdateWidth,
240 VideoDetector::kMinUpdateHeight));
241 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
242 detector_->OnWindowPaintScheduled(window1.get(), update_region);
243 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
244 detector_->OnWindowPaintScheduled(window2.get(), update_region);
245 EXPECT_EQ(1, observer_->num_invocations());
246 EXPECT_EQ(0, observer_->num_fullscreens());
247 EXPECT_EQ(1, observer_->num_not_fullscreens());
250 // Test that the observer receives repeated notifications.
251 TEST_F(VideoDetectorTest, RepeatedNotifications) {
252 gfx::Rect window_bounds(gfx::Point(), gfx::Size(1024, 768));
253 scoped_ptr<aura::Window> window(
254 CreateTestWindowInShell(SK_ColorRED, 12345, window_bounds));
256 gfx::Rect update_region(
257 gfx::Point(),
258 gfx::Size(VideoDetector::kMinUpdateWidth,
259 VideoDetector::kMinUpdateHeight));
260 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
261 detector_->OnWindowPaintScheduled(window.get(), update_region);
262 EXPECT_EQ(1, observer_->num_invocations());
263 EXPECT_EQ(0, observer_->num_fullscreens());
264 EXPECT_EQ(1, observer_->num_not_fullscreens());
265 // Let enough time pass that a second notification should be sent.
266 observer_->reset_stats();
267 AdvanceTime(base::TimeDelta::FromSeconds(
268 static_cast<int64>(VideoDetector::kNotifyIntervalSec + 1)));
269 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
270 detector_->OnWindowPaintScheduled(window.get(), update_region);
271 EXPECT_EQ(1, observer_->num_invocations());
272 EXPECT_EQ(0, observer_->num_fullscreens());
273 EXPECT_EQ(1, observer_->num_not_fullscreens());
276 // Test that the observer receives a true value when the window is fullscreen.
277 TEST_F(VideoDetectorTest, FullscreenWindow) {
278 gfx::Rect window_bounds(gfx::Point(), gfx::Size(1024, 768));
279 scoped_ptr<aura::Window> window(
280 CreateTestWindowInShell(SK_ColorRED, 12345, window_bounds));
281 window->SetProperty(aura::client::kShowStateKey, ui::SHOW_STATE_FULLSCREEN);
282 window->Focus();
283 gfx::Rect update_region(
284 gfx::Point(),
285 gfx::Size(VideoDetector::kMinUpdateWidth,
286 VideoDetector::kMinUpdateHeight));
287 for (int i = 0; i < VideoDetector::kMinFramesPerSecond; ++i)
288 detector_->OnWindowPaintScheduled(window.get(), update_region);
289 EXPECT_EQ(1, observer_->num_invocations());
290 EXPECT_EQ(1, observer_->num_fullscreens());
291 EXPECT_EQ(0, observer_->num_not_fullscreens());
294 } // namespace test
295 } // namespace ash