| 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 "core/dom/Document.h" | 5 #include "core/dom/Document.h" |
| 6 #include "core/html/AutoplayExperimentHelper.h" | 6 #include "core/html/AutoplayExperimentHelper.h" |
| 7 #include "platform/UserGestureIndicator.h" | 7 #include "platform/UserGestureIndicator.h" |
| 8 #include "testing/gmock/include/gmock/gmock.h" | 8 #include "testing/gmock/include/gmock/gmock.h" |
| 9 #include "testing/gtest/include/gtest/gtest.h" | 9 #include "testing/gtest/include/gtest/gtest.h" |
| 10 | 10 |
| (...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 73 } | 73 } |
| 74 | 74 |
| 75 virtual ~MockAutoplayClient() {} | 75 virtual ~MockAutoplayClient() {} |
| 76 | 76 |
| 77 MOCK_CONST_METHOD0(currentTime, double()); | 77 MOCK_CONST_METHOD0(currentTime, double()); |
| 78 MOCK_CONST_METHOD0(duration, double()); | 78 MOCK_CONST_METHOD0(duration, double()); |
| 79 MOCK_CONST_METHOD0(ended, bool()); | 79 MOCK_CONST_METHOD0(ended, bool()); |
| 80 MOCK_CONST_METHOD0(muted, bool()); | 80 MOCK_CONST_METHOD0(muted, bool()); |
| 81 MOCK_METHOD1(setMuted, void(bool)); | 81 MOCK_METHOD1(setMuted, void(bool)); |
| 82 MOCK_METHOD0(playInternal, void()); | 82 MOCK_METHOD0(playInternal, void()); |
| 83 MOCK_CONST_METHOD0(isUserGestureRequiredForPlay, bool()); | 83 MOCK_CONST_METHOD0(isLockedPendingUserGesture, bool()); |
| 84 MOCK_METHOD0(removeUserGestureRequirement, void()); | 84 MOCK_METHOD0(removeUserGestureRequirement, void()); |
| 85 MOCK_METHOD1(recordAutoplayMetric, void(AutoplayMetrics)); | 85 MOCK_METHOD1(recordAutoplayMetric, void(AutoplayMetrics)); |
| 86 MOCK_METHOD0(shouldAutoplay, bool()); | 86 MOCK_METHOD0(shouldAutoplay, bool()); |
| 87 MOCK_CONST_METHOD0(isHTMLVideoElement, bool()); | 87 MOCK_CONST_METHOD0(isHTMLVideoElement, bool()); |
| 88 MOCK_CONST_METHOD0(isHTMLAudioElement, bool()); | 88 MOCK_CONST_METHOD0(isHTMLAudioElement, bool()); |
| 89 MOCK_METHOD0(isLegacyViewportType, bool()); | 89 MOCK_METHOD0(isLegacyViewportType, bool()); |
| 90 MOCK_CONST_METHOD0(pageVisibilityState, PageVisibilityState()); | 90 MOCK_CONST_METHOD0(pageVisibilityState, PageVisibilityState()); |
| 91 MOCK_CONST_METHOD0(autoplayExperimentMode, String()); | 91 MOCK_CONST_METHOD0(autoplayExperimentMode, String()); |
| 92 MOCK_CONST_METHOD0(isCrossOrigin, bool()); | 92 MOCK_CONST_METHOD0(isCrossOrigin, bool()); |
| 93 MOCK_CONST_METHOD0(isAutoplayAllowedPerSettings, bool()); | 93 MOCK_CONST_METHOD0(isAutoplayAllowedPerSettings, bool()); |
| (...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 152 | 152 |
| 153 void startPlaybackWithUserGesture() | 153 void startPlaybackWithUserGesture() |
| 154 { | 154 { |
| 155 UserGestureIndicator indicator(DefinitelyProcessingUserGesture); | 155 UserGestureIndicator indicator(DefinitelyProcessingUserGesture); |
| 156 EXPECT_TRUE(UserGestureIndicator::processingUserGesture()); | 156 EXPECT_TRUE(UserGestureIndicator::processingUserGesture()); |
| 157 startPlayback(); | 157 startPlayback(); |
| 158 } | 158 } |
| 159 | 159 |
| 160 void setUserGestureRequiredForPlay(bool required) | 160 void setUserGestureRequiredForPlay(bool required) |
| 161 { | 161 { |
| 162 ON_CALL(*m_client, isUserGestureRequiredForPlay()) | 162 ON_CALL(*m_client, isLockedPendingUserGesture()) |
| 163 .WillByDefault(Return(required)); | 163 .WillByDefault(Return(required)); |
| 164 } | 164 } |
| 165 | 165 |
| 166 void setShouldAutoplay(bool should) | 166 void setShouldAutoplay(bool should) |
| 167 { | 167 { |
| 168 ON_CALL(*m_client, shouldAutoplay()) | 168 ON_CALL(*m_client, shouldAutoplay()) |
| 169 .WillByDefault(Return(should)); | 169 .WillByDefault(Return(should)); |
| 170 } | 170 } |
| 171 | 171 |
| 172 void setIsMuted(bool isMuted) | 172 void setIsMuted(bool isMuted) |
| (...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 246 { | 246 { |
| 247 // Audio should not be eligible for video mode. | 247 // Audio should not be eligible for video mode. |
| 248 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Audio)); | 248 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Audio)); |
| 249 EXPECT_FALSE(isEligible()); | 249 EXPECT_FALSE(isEligible()); |
| 250 } | 250 } |
| 251 | 251 |
| 252 TEST_F(AutoplayExperimentTest, IsEligibleRequiresUserGesture) | 252 TEST_F(AutoplayExperimentTest, IsEligibleRequiresUserGesture) |
| 253 { | 253 { |
| 254 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); | 254 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); |
| 255 // If a user gesture is not required, then we're not eligible. | 255 // If a user gesture is not required, then we're not eligible. |
| 256 ON_CALL(*m_client, isUserGestureRequiredForPlay()) | 256 ON_CALL(*m_client, isLockedPendingUserGesture()) |
| 257 .WillByDefault(Return(false)); | 257 .WillByDefault(Return(false)); |
| 258 EXPECT_FALSE(isEligible()); | 258 EXPECT_FALSE(isEligible()); |
| 259 } | 259 } |
| 260 | 260 |
| 261 TEST_F(AutoplayExperimentTest, IsEligibleRequiresShouldAutoplay) | 261 TEST_F(AutoplayExperimentTest, IsEligibleRequiresShouldAutoplay) |
| 262 { | 262 { |
| 263 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); | 263 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); |
| 264 // If we shouldn't autoplay, then we're not eligible. | 264 // If we shouldn't autoplay, then we're not eligible. |
| 265 ON_CALL(*m_client, shouldAutoplay()) | 265 ON_CALL(*m_client, shouldAutoplay()) |
| 266 .WillByDefault(Return(false)); | 266 .WillByDefault(Return(false)); |
| (...skipping 25 matching lines...) Expand all Loading... |
| 292 | 292 |
| 293 ON_CALL(*m_client, muted()) | 293 ON_CALL(*m_client, muted()) |
| 294 .WillByDefault(Return(true)); | 294 .WillByDefault(Return(true)); |
| 295 EXPECT_TRUE(isEligible()); | 295 EXPECT_TRUE(isEligible()); |
| 296 } | 296 } |
| 297 | 297 |
| 298 TEST_F(AutoplayExperimentTest, BecameReadyAutoplayThenBailout) | 298 TEST_F(AutoplayExperimentTest, BecameReadyAutoplayThenBailout) |
| 299 { | 299 { |
| 300 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); | 300 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); |
| 301 | 301 |
| 302 EXPECT_CALL(*m_client, removeUserGestureRequirement()) | |
| 303 .Times(1); | |
| 304 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) | 302 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) |
| 305 .Times(1); | 303 .Times(1); |
| 306 m_helper->becameReadyToPlay(); | 304 m_helper->becameReadyToPlay(); |
| 305 EXPECT_TRUE(m_helper->isGestureRequirementOverridden()); |
| 307 | 306 |
| 308 EXPECT_CALL(*m_client, recordAutoplayMetric(GesturelessPlaybackStartedByAuto
playFlagImmediately)) | 307 EXPECT_CALL(*m_client, recordAutoplayMetric(GesturelessPlaybackStartedByAuto
playFlagImmediately)) |
| 309 .Times(1); | 308 .Times(1); |
| 310 startPlaybackWithoutUserGesture(); | 309 startPlaybackWithoutUserGesture(); |
| 311 | 310 |
| 312 pausePlaybackExpectingBailout(true); | 311 pausePlaybackExpectingBailout(true); |
| 313 } | 312 } |
| 314 | 313 |
| 315 TEST_F(AutoplayExperimentTest, BecameReadyAutoplayThenPause) | 314 TEST_F(AutoplayExperimentTest, BecameReadyAutoplayThenPause) |
| 316 { | 315 { |
| 317 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); | 316 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); |
| 318 | 317 |
| 319 EXPECT_CALL(*m_client, removeUserGestureRequirement()) | |
| 320 .Times(1); | |
| 321 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) | 318 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) |
| 322 .Times(1); | 319 .Times(1); |
| 323 m_helper->becameReadyToPlay(); | 320 m_helper->becameReadyToPlay(); |
| 321 EXPECT_TRUE(m_helper->isGestureRequirementOverridden()); |
| 324 | 322 |
| 325 EXPECT_CALL(*m_client, recordAutoplayMetric(GesturelessPlaybackStartedByAuto
playFlagImmediately)) | 323 EXPECT_CALL(*m_client, recordAutoplayMetric(GesturelessPlaybackStartedByAuto
playFlagImmediately)) |
| 326 .Times(1); | 324 .Times(1); |
| 327 startPlaybackWithoutUserGesture(); | 325 startPlaybackWithoutUserGesture(); |
| 328 | 326 |
| 329 pausePlaybackNotExpectingBailout(true); | 327 pausePlaybackNotExpectingBailout(true); |
| 330 } | 328 } |
| 331 | 329 |
| 332 TEST_F(AutoplayExperimentTest, BecameReadyAutoplayThenComplete) | 330 TEST_F(AutoplayExperimentTest, BecameReadyAutoplayThenComplete) |
| 333 { | 331 { |
| 334 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); | 332 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); |
| 335 | 333 |
| 336 EXPECT_CALL(*m_client, removeUserGestureRequirement()) | |
| 337 .Times(1); | |
| 338 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) | 334 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) |
| 339 .Times(1); | 335 .Times(1); |
| 340 m_helper->becameReadyToPlay(); | 336 m_helper->becameReadyToPlay(); |
| 337 EXPECT_TRUE(m_helper->isGestureRequirementOverridden()); |
| 341 | 338 |
| 342 EXPECT_CALL(*m_client, recordAutoplayMetric(GesturelessPlaybackStartedByAuto
playFlagImmediately)) | 339 EXPECT_CALL(*m_client, recordAutoplayMetric(GesturelessPlaybackStartedByAuto
playFlagImmediately)) |
| 343 .Times(1); | 340 .Times(1); |
| 344 startPlaybackWithoutUserGesture(); | 341 startPlaybackWithoutUserGesture(); |
| 345 | 342 |
| 346 // Now stop at the end. | 343 // Now stop at the end. |
| 347 endPlayback(true); | 344 endPlayback(true); |
| 348 } | 345 } |
| 349 | 346 |
| 350 TEST_F(AutoplayExperimentTest, NoUserGestureNeededShouldNotOverride) | 347 TEST_F(AutoplayExperimentTest, NoUserGestureNeededShouldNotOverride) |
| (...skipping 23 matching lines...) Expand all Loading... |
| 374 | 371 |
| 375 // Expect bailout, but not from autoplay. | 372 // Expect bailout, but not from autoplay. |
| 376 pausePlaybackExpectingBailout(false); | 373 pausePlaybackExpectingBailout(false); |
| 377 } | 374 } |
| 378 | 375 |
| 379 TEST_F(AutoplayExperimentTest, PlayMethodThenBailout) | 376 TEST_F(AutoplayExperimentTest, PlayMethodThenBailout) |
| 380 { | 377 { |
| 381 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); | 378 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); |
| 382 setShouldAutoplay(false); // No autoplay attribute. | 379 setShouldAutoplay(false); // No autoplay attribute. |
| 383 | 380 |
| 384 EXPECT_CALL(*m_client, removeUserGestureRequirement()) | |
| 385 .Times(1); | |
| 386 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) | 381 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) |
| 387 .Times(1); | 382 .Times(1); |
| 388 m_helper->playMethodCalled(); | 383 m_helper->playMethodCalled(false); |
| 384 EXPECT_TRUE(m_helper->isGestureRequirementOverridden()); |
| 389 | 385 |
| 390 EXPECT_CALL(*m_client, recordAutoplayMetric(GesturelessPlaybackStartedByPlay
MethodImmediately)) | 386 EXPECT_CALL(*m_client, recordAutoplayMetric(GesturelessPlaybackStartedByPlay
MethodImmediately)) |
| 391 .Times(1); | 387 .Times(1); |
| 392 startPlaybackWithoutUserGesture(); | 388 startPlaybackWithoutUserGesture(); |
| 393 | 389 |
| 394 pausePlaybackExpectingBailout(true); | 390 pausePlaybackExpectingBailout(true); |
| 395 } | 391 } |
| 396 | 392 |
| 397 TEST_F(AutoplayExperimentTest, DeferAutoplayUntilMuted) | 393 TEST_F(AutoplayExperimentTest, DeferAutoplayUntilMuted) |
| 398 { | 394 { |
| 399 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo-ifmuted", Mo
ckAutoplayClient::Video)); | 395 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo-ifmuted", Mo
ckAutoplayClient::Video)); |
| 400 | 396 |
| 401 // Should not override the gesture requirement yet. | 397 // Should not override the gesture requirement yet. |
| 402 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) | 398 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) |
| 403 .Times(1); | 399 .Times(1); |
| 404 m_helper->becameReadyToPlay(); | 400 m_helper->becameReadyToPlay(); |
| 405 | 401 |
| 406 // When we toggle the muted attribute, it should start. | 402 // When we toggle the muted attribute, it should become eligible to start. |
| 407 EXPECT_CALL(*m_client, removeUserGestureRequirement()) | 403 EXPECT_FALSE(m_helper->isGestureRequirementOverridden()); |
| 408 .Times(1); | |
| 409 EXPECT_CALL(*m_client, playInternal()) | |
| 410 .Times(1); | |
| 411 setIsMuted(true); | 404 setIsMuted(true); |
| 412 m_helper->mutedChanged(); | 405 EXPECT_TRUE(m_helper->isGestureRequirementOverridden()); |
| 413 | |
| 414 // When playback starts (in response to playInternal()), it should also | |
| 415 // record why. 'After scroll' isn't the best name, but this isn't a common
case. | |
| 416 EXPECT_CALL(*m_client, recordAutoplayMetric(GesturelessPlaybackStartedByAuto
playFlagAfterScroll)) | |
| 417 .Times(1); | |
| 418 startPlaybackWithoutUserGesture(); | |
| 419 } | 406 } |
| 420 | 407 |
| 421 TEST_F(AutoplayExperimentTest, DeferPlaybackUntilInViewport) | 408 TEST_F(AutoplayExperimentTest, DeferPlaybackUntilInViewport) |
| 422 { | 409 { |
| 423 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo-ifviewport",
MockAutoplayClient::Video)); | 410 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo-ifviewport",
MockAutoplayClient::Video)); |
| 424 | 411 |
| 425 // Should not override the gesture requirement yet. | 412 // Should not override the gesture requirement yet. |
| 426 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) | 413 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) |
| 427 .Times(1); | 414 .Times(1); |
| 428 EXPECT_CALL(*m_client, setRequestPositionUpdates(true)) | 415 EXPECT_CALL(*m_client, setRequestPositionUpdates(true)) |
| 429 .Times(1); | 416 .Times(1); |
| 430 m_helper->becameReadyToPlay(); | 417 m_helper->becameReadyToPlay(); |
| 431 | 418 |
| 432 EXPECT_CALL(*m_client, removeUserGestureRequirement()) | |
| 433 .Times(1); | |
| 434 EXPECT_CALL(*m_client, playInternal()) | 419 EXPECT_CALL(*m_client, playInternal()) |
| 435 .Times(1); | 420 .Times(1); |
| 436 EXPECT_CALL(*m_client, setRequestPositionUpdates(false)) | 421 EXPECT_CALL(*m_client, setRequestPositionUpdates(false)) |
| 437 .Times(1); | 422 .Times(1); |
| 438 moveIntoViewport(); | 423 moveIntoViewport(); |
| 424 EXPECT_TRUE(m_helper->isGestureRequirementOverridden()); |
| 439 } | 425 } |
| 440 | 426 |
| 441 TEST_F(AutoplayExperimentTest, WithSameOriginTests) | 427 TEST_F(AutoplayExperimentTest, WithSameOriginTests) |
| 442 { | 428 { |
| 443 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo-ifsameorigin
", MockAutoplayClient::Video)); | 429 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo-ifsameorigin
", MockAutoplayClient::Video)); |
| 444 ON_CALL(*m_client, isCrossOrigin()).WillByDefault(Return(false)); | 430 ON_CALL(*m_client, isCrossOrigin()).WillByDefault(Return(false)); |
| 445 EXPECT_TRUE(isEligible()); | 431 EXPECT_TRUE(isEligible()); |
| 446 ON_CALL(*m_client, isCrossOrigin()).WillByDefault(Return(true)); | 432 ON_CALL(*m_client, isCrossOrigin()).WillByDefault(Return(true)); |
| 447 EXPECT_FALSE(isEligible()); | 433 EXPECT_FALSE(isEligible()); |
| 448 } | 434 } |
| 449 | 435 |
| 450 TEST_F(AutoplayExperimentTest, WithoutSameOriginTests) | 436 TEST_F(AutoplayExperimentTest, WithoutSameOriginTests) |
| 451 { | 437 { |
| 452 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); | 438 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); |
| 453 ON_CALL(*m_client, isCrossOrigin()).WillByDefault(Return(false)); | 439 ON_CALL(*m_client, isCrossOrigin()).WillByDefault(Return(false)); |
| 454 EXPECT_TRUE(isEligible()); | 440 EXPECT_TRUE(isEligible()); |
| 455 ON_CALL(*m_client, isCrossOrigin()).WillByDefault(Return(true)); | 441 ON_CALL(*m_client, isCrossOrigin()).WillByDefault(Return(true)); |
| 456 EXPECT_TRUE(isEligible()); | 442 EXPECT_TRUE(isEligible()); |
| 457 } | 443 } |
| 458 | 444 |
| 445 TEST_F(AutoplayExperimentTest, PlayTwiceIsIgnored) |
| 446 { |
| 447 setInterface(new NiceMock<MockAutoplayClient>("enabled-forvideo", MockAutopl
ayClient::Video)); |
| 448 setShouldAutoplay(false); // No autoplay attribute. |
| 449 |
| 450 EXPECT_CALL(*m_client, recordAutoplayMetric(AutoplayMediaFound)) |
| 451 .Times(1); |
| 452 m_helper->playMethodCalled(false); |
| 453 m_helper->playMethodCalled(true); |
| 459 } | 454 } |
| 455 |
| 456 } |
| OLD | NEW |