swipe_home_to_overview_controller_unittest.cc 27 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724
  1. // Copyright 2019 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. #include "ash/shelf/swipe_home_to_overview_controller.h"
  5. #include <tuple>
  6. #include "ash/app_list/app_list_controller_impl.h"
  7. #include "ash/app_list/test/app_list_test_helper.h"
  8. #include "ash/app_list/views/app_list_view.h"
  9. #include "ash/app_list/views/search_box_view.h"
  10. #include "ash/root_window_controller.h"
  11. #include "ash/shelf/shelf.h"
  12. #include "ash/shelf/shelf_metrics.h"
  13. #include "ash/shelf/shelf_test_util.h"
  14. #include "ash/shelf/shelf_view.h"
  15. #include "ash/shell.h"
  16. #include "ash/test/ash_test_base.h"
  17. #include "ash/wm/overview/overview_controller.h"
  18. #include "ash/wm/tablet_mode/tablet_mode_controller_test_api.h"
  19. #include "base/bind.h"
  20. #include "base/run_loop.h"
  21. #include "base/test/metrics/histogram_tester.h"
  22. #include "base/test/simple_test_tick_clock.h"
  23. #include "third_party/abseil-cpp/absl/types/optional.h"
  24. #include "ui/compositor/layer.h"
  25. #include "ui/compositor/layer_animator.h"
  26. #include "ui/compositor/scoped_animation_duration_scale_mode.h"
  27. #include "ui/compositor/test/test_utils.h"
  28. #include "ui/gfx/geometry/point_f.h"
  29. #include "ui/gfx/geometry/rect_f.h"
  30. namespace ash {
  31. namespace {
  32. gfx::Rect GetShelfBounds() {
  33. return Shelf::ForWindow(Shell::GetPrimaryRootWindow())->GetIdealBounds();
  34. }
  35. gfx::RectF GetShelfBoundsInFloat() {
  36. return gfx::RectF(GetShelfBounds());
  37. }
  38. } // namespace
  39. class SwipeHomeToOverviewControllerTest : public AshTestBase {
  40. public:
  41. SwipeHomeToOverviewControllerTest() = default;
  42. SwipeHomeToOverviewControllerTest(const SwipeHomeToOverviewControllerTest&) =
  43. delete;
  44. SwipeHomeToOverviewControllerTest& operator=(
  45. const SwipeHomeToOverviewControllerTest&) = delete;
  46. ~SwipeHomeToOverviewControllerTest() override = default;
  47. // AshTestBase:
  48. void SetUp() override {
  49. AshTestBase::SetUp();
  50. UpdateDisplay("1000x756");
  51. TabletModeControllerTestApi().EnterTabletMode();
  52. base::RunLoop().RunUntilIdle();
  53. // Advance tick clock by arbitrary non-zero amount.
  54. tick_clock_.Advance(base::Seconds(1000));
  55. }
  56. void TearDown() override {
  57. home_to_overview_controller_.reset();
  58. AshTestBase::TearDown();
  59. }
  60. void StartDrag() {
  61. home_to_overview_controller_ =
  62. std::make_unique<SwipeHomeToOverviewController>(
  63. GetPrimaryDisplay().id(), &tick_clock_);
  64. }
  65. void Drag(const gfx::PointF& location_in_screen,
  66. float scroll_x,
  67. float scroll_y) {
  68. home_to_overview_controller_->Drag(location_in_screen, scroll_x, scroll_y);
  69. }
  70. void EndDrag(const gfx::PointF& location_in_screen,
  71. absl::optional<float> velocity_y) {
  72. home_to_overview_controller_->EndDrag(location_in_screen, velocity_y);
  73. }
  74. void CancelDrag() { home_to_overview_controller_->CancelDrag(); }
  75. AppListControllerImpl* app_list_controller() {
  76. return Shell::Get()->app_list_controller();
  77. }
  78. bool OverviewTransitionTimerRunning() const {
  79. return home_to_overview_controller_->overview_transition_timer_for_testing()
  80. ->IsRunning();
  81. }
  82. void FireOverviewTransitionTimer() {
  83. return home_to_overview_controller_->overview_transition_timer_for_testing()
  84. ->FireNow();
  85. }
  86. void WaitForHomeLauncherAnimationToFinish() {
  87. auto* compositor =
  88. Shell::GetPrimaryRootWindowController()->GetHost()->compositor();
  89. // Wait until home launcher animation finishes.
  90. while (GetAppListTestHelper()
  91. ->GetAppListView()
  92. ->GetWidget()
  93. ->GetLayer()
  94. ->GetAnimator()
  95. ->is_animating()) {
  96. EXPECT_TRUE(ui::WaitForNextFrameToBePresented(compositor));
  97. }
  98. // Ensure there is one more frame presented after animation finishes
  99. // to allow animation throughput data is passed from cc to ui.
  100. std::ignore =
  101. ui::WaitForNextFrameToBePresented(compositor, base::Milliseconds(200));
  102. }
  103. void TapOnHomeLauncherSearchBox() {
  104. GetEventGenerator()->GestureTapAt(GetAppListTestHelper()
  105. ->GetAppListView()
  106. ->search_box_view()
  107. ->GetBoundsInScreen()
  108. .CenterPoint());
  109. }
  110. base::TimeTicks GetTimerDesiredRunTime() const {
  111. return home_to_overview_controller_->overview_transition_timer_for_testing()
  112. ->desired_run_time();
  113. }
  114. bool OverviewStarted() const {
  115. return Shell::Get()->overview_controller()->InOverviewSession();
  116. }
  117. protected:
  118. base::SimpleTestTickClock tick_clock_;
  119. private:
  120. std::unique_ptr<SwipeHomeToOverviewController> home_to_overview_controller_;
  121. };
  122. // Verify that the metrics of home launcher animation are recorded correctly
  123. // when entering/exiting overview mode.
  124. TEST_F(SwipeHomeToOverviewControllerTest, VerifyHomeLauncherMetrics) {
  125. // Set non-zero animation duration to report animation metrics.
  126. ui::ScopedAnimationDurationScaleMode non_zero_duration_mode(
  127. ui::ScopedAnimationDurationScaleMode::NON_ZERO_DURATION);
  128. base::HistogramTester histogram_tester;
  129. // Enter overview mode by gesture swipe on shelf.
  130. {
  131. const gfx::Point gesture_start_point =
  132. Shelf::ForWindow(Shell::GetPrimaryRootWindow())
  133. ->GetShelfViewForTesting()
  134. ->GetBoundsInScreen()
  135. .CenterPoint();
  136. // Calculate the suitable gesture end location to trigger the overview mode
  137. // through the gesture scroll.
  138. // Note that we cannot access `SwipeHomeToOverviewController`'s non-static
  139. // members here since the class instance has not be created yet.
  140. const int extra_distance = 15;
  141. const gfx::Point gesture_end_point(
  142. gesture_start_point.x(),
  143. GetPrimaryDisplay().bounds().bottom() -
  144. ShelfConfig::Get()->shelf_size() -
  145. SwipeHomeToOverviewController::
  146. kVerticalThresholdForOverviewTransition -
  147. extra_distance);
  148. // Scroll should be slow enough to trigger the overview mode.
  149. constexpr int steps = 12;
  150. int update_count = 0;
  151. GetEventGenerator()->GestureScrollSequenceWithCallback(
  152. gesture_start_point, gesture_end_point, base::Milliseconds(100),
  153. /*steps=*/steps,
  154. base::BindRepeating(
  155. [](int* update_count, ui::EventType event_type,
  156. const gfx::Vector2dF& delta) {
  157. if (event_type != ui::ET_GESTURE_SCROLL_UPDATE)
  158. return;
  159. *update_count = *update_count + 1;
  160. if (*update_count == steps) {
  161. // Wait until overview animation finishes. If the gesture scroll
  162. // ends too early, we may not be able to enter the overview mode
  163. WaitForOverviewAnimation(/*enter=*/true);
  164. }
  165. },
  166. &update_count));
  167. }
  168. // Collect metrics data. Verify that the animation to hide the home launcher
  169. // is recorded.
  170. WaitForHomeLauncherAnimationToFinish();
  171. histogram_tester.ExpectTotalCount(
  172. "Apps.HomeLauncherTransition.AnimationSmoothness.FadeInOverview", 1);
  173. histogram_tester.ExpectTotalCount(
  174. "Apps.HomeLauncherTransition.AnimationSmoothness.FadeOutOverview", 0);
  175. // Exit overview mode by gesture tap.
  176. GetEventGenerator()->GestureTapAt(
  177. GetContext()->GetBoundsInScreen().top_center());
  178. // Wait until overview animation finishes.
  179. WaitForOverviewAnimation(/*enter=*/false);
  180. // Verify that the animation to show the home launcher is recorded.
  181. WaitForHomeLauncherAnimationToFinish();
  182. histogram_tester.ExpectTotalCount(
  183. "Apps.HomeLauncherTransition.AnimationSmoothness.FadeInOverview", 1);
  184. histogram_tester.ExpectTotalCount(
  185. "Apps.HomeLauncherTransition.AnimationSmoothness.FadeOutOverview", 1);
  186. }
  187. TEST_F(SwipeHomeToOverviewControllerTest, BasicFlow) {
  188. const gfx::RectF shelf_bounds = GetShelfBoundsInFloat();
  189. base::HistogramTester histogram_tester;
  190. histogram_tester.ExpectBucketCount(
  191. kEnterOverviewHistogramName, EnterOverviewFromHomeLauncher::kOverview, 0);
  192. StartDrag();
  193. // Drag to a point within shelf bounds - verify that app list has not been
  194. // scaled, and the transition to overview transition timer has not started.
  195. Drag(shelf_bounds.CenterPoint(), 0.f, 1.f);
  196. aura::Window* home_screen_window =
  197. app_list_controller()->GetHomeScreenWindow();
  198. ASSERT_TRUE(home_screen_window);
  199. EXPECT_EQ(gfx::Transform(),
  200. home_screen_window->layer()->GetTargetTransform());
  201. EXPECT_FALSE(OverviewTransitionTimerRunning());
  202. EXPECT_FALSE(OverviewStarted());
  203. histogram_tester.ExpectBucketCount(
  204. kEnterOverviewHistogramName, EnterOverviewFromHomeLauncher::kOverview, 0);
  205. const int transition_threshold =
  206. SwipeHomeToOverviewController::kVerticalThresholdForOverviewTransition;
  207. // Move above the shelf but not far enough to trigger transition to overview.
  208. // The home window is expected to be scaled at this point, but the overview
  209. // transition timer to should not yet be running.
  210. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold / 2),
  211. 0.f, 1.f);
  212. EXPECT_EQ(home_screen_window->transform(),
  213. home_screen_window->layer()->GetTargetTransform());
  214. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  215. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  216. EXPECT_EQ(1.f, home_screen_window->layer()->opacity());
  217. histogram_tester.ExpectBucketCount(
  218. kEnterOverviewHistogramName, EnterOverviewFromHomeLauncher::kOverview, 0);
  219. // Move above the transition threshold - verify the overview transition timer
  220. // has started.
  221. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  222. 0.f, 1.f);
  223. EXPECT_EQ(home_screen_window->transform(),
  224. home_screen_window->layer()->GetTargetTransform());
  225. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  226. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  227. EXPECT_TRUE(OverviewTransitionTimerRunning());
  228. EXPECT_FALSE(OverviewStarted());
  229. histogram_tester.ExpectBucketCount(
  230. kEnterOverviewHistogramName, EnterOverviewFromHomeLauncher::kOverview, 0);
  231. // Fire overview transition timer, and verify the overview has started.
  232. FireOverviewTransitionTimer();
  233. EXPECT_TRUE(OverviewStarted());
  234. histogram_tester.ExpectBucketCount(
  235. kEnterOverviewHistogramName, EnterOverviewFromHomeLauncher::kOverview, 1);
  236. // Home screen is still scaled down, and not visible.
  237. EXPECT_EQ(home_screen_window->transform(),
  238. home_screen_window->layer()->GetTargetTransform());
  239. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  240. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  241. EXPECT_EQ(0.f, home_screen_window->layer()->opacity());
  242. // The user ending drag after this point should be no-op.
  243. EndDrag(
  244. shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  245. 1.f);
  246. EXPECT_TRUE(OverviewStarted());
  247. histogram_tester.ExpectBucketCount(
  248. kEnterOverviewHistogramName, EnterOverviewFromHomeLauncher::kOverview, 1);
  249. // Home screen is still scaled down, and not visible.
  250. EXPECT_EQ(home_screen_window->transform(),
  251. home_screen_window->layer()->GetTargetTransform());
  252. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  253. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  254. EXPECT_EQ(0.f, home_screen_window->layer()->opacity());
  255. }
  256. TEST_F(SwipeHomeToOverviewControllerTest, EndDragBeforeTimeout) {
  257. const gfx::RectF shelf_bounds = GetShelfBoundsInFloat();
  258. StartDrag();
  259. aura::Window* home_screen_window =
  260. app_list_controller()->GetHomeScreenWindow();
  261. ASSERT_TRUE(home_screen_window);
  262. const int transition_threshold =
  263. SwipeHomeToOverviewController::kVerticalThresholdForOverviewTransition;
  264. // Move above the transition threshold - verify the overview transition timer
  265. // has started.
  266. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold / 2),
  267. 0.f, 1.f);
  268. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  269. 0.f, 1.f);
  270. EXPECT_EQ(home_screen_window->transform(),
  271. home_screen_window->layer()->GetTargetTransform());
  272. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  273. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  274. EXPECT_TRUE(OverviewTransitionTimerRunning());
  275. EXPECT_FALSE(OverviewStarted());
  276. // The user ending drag should reset the home view state.
  277. EndDrag(
  278. shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  279. 1.f);
  280. EXPECT_EQ(home_screen_window->transform(),
  281. home_screen_window->layer()->GetTargetTransform());
  282. EXPECT_EQ(gfx::Transform(), home_screen_window->transform());
  283. EXPECT_EQ(1.f, home_screen_window->layer()->opacity());
  284. EXPECT_FALSE(OverviewTransitionTimerRunning());
  285. EXPECT_FALSE(OverviewStarted());
  286. }
  287. TEST_F(SwipeHomeToOverviewControllerTest, GoBackOnHomeLauncher) {
  288. // Show home screen search results page.
  289. GetAppListTestHelper()->CheckVisibility(true);
  290. TapOnHomeLauncherSearchBox();
  291. GetAppListTestHelper()->CheckState(AppListViewState::kFullscreenSearch);
  292. const gfx::RectF shelf_bounds = GetShelfBoundsInFloat();
  293. StartDrag();
  294. aura::Window* home_screen_window =
  295. app_list_controller()->GetHomeScreenWindow();
  296. ASSERT_TRUE(home_screen_window);
  297. const int transition_threshold =
  298. SwipeHomeToOverviewController::kVerticalThresholdForOverviewTransition;
  299. // Move above the transition threshold - verify the overview transition timer
  300. // has started.
  301. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold / 2),
  302. 0.f, 1.f);
  303. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  304. 0.f, 1.f);
  305. EXPECT_EQ(home_screen_window->transform(),
  306. home_screen_window->layer()->GetTargetTransform());
  307. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  308. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  309. EXPECT_TRUE(OverviewTransitionTimerRunning());
  310. EXPECT_FALSE(OverviewStarted());
  311. // The user ending drag with a fling should move home to the initial state -
  312. // fullscreen all apps.
  313. EndDrag(
  314. shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  315. -1500.f);
  316. EXPECT_EQ(home_screen_window->transform(),
  317. home_screen_window->layer()->GetTargetTransform());
  318. EXPECT_EQ(gfx::Transform(), home_screen_window->transform());
  319. EXPECT_EQ(1.f, home_screen_window->layer()->opacity());
  320. EXPECT_FALSE(OverviewTransitionTimerRunning());
  321. EXPECT_FALSE(OverviewStarted());
  322. GetAppListTestHelper()->CheckState(AppListViewState::kFullscreenAllApps);
  323. }
  324. TEST_F(SwipeHomeToOverviewControllerTest, FlingOnAppsPage) {
  325. // Show home screen search results page.
  326. GetAppListTestHelper()->CheckVisibility(true);
  327. GetAppListTestHelper()->CheckState(AppListViewState::kFullscreenAllApps);
  328. const gfx::RectF shelf_bounds = GetShelfBoundsInFloat();
  329. StartDrag();
  330. aura::Window* home_screen_window =
  331. app_list_controller()->GetHomeScreenWindow();
  332. ASSERT_TRUE(home_screen_window);
  333. const int transition_threshold =
  334. SwipeHomeToOverviewController::kVerticalThresholdForOverviewTransition;
  335. // Move above the transition threshold - verify the overview transition timer
  336. // has started.
  337. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold / 2),
  338. 0.f, 1.f);
  339. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  340. 0.f, 1.f);
  341. EXPECT_EQ(home_screen_window->transform(),
  342. home_screen_window->layer()->GetTargetTransform());
  343. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  344. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  345. EXPECT_TRUE(OverviewTransitionTimerRunning());
  346. EXPECT_FALSE(OverviewStarted());
  347. // The user ending drag with a fling should move home to the initial state -
  348. // fullscreen all apps.
  349. EndDrag(
  350. shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  351. -1500.f);
  352. EXPECT_EQ(home_screen_window->transform(),
  353. home_screen_window->layer()->GetTargetTransform());
  354. EXPECT_EQ(gfx::Transform(), home_screen_window->transform());
  355. EXPECT_EQ(1.f, home_screen_window->layer()->opacity());
  356. EXPECT_FALSE(OverviewTransitionTimerRunning());
  357. EXPECT_FALSE(OverviewStarted());
  358. GetAppListTestHelper()->CheckState(AppListViewState::kFullscreenAllApps);
  359. }
  360. TEST_F(SwipeHomeToOverviewControllerTest, CancelDragBeforeTimeout) {
  361. // Show home screen search results page.
  362. GetAppListTestHelper()->CheckVisibility(true);
  363. TapOnHomeLauncherSearchBox();
  364. GetAppListTestHelper()->CheckState(AppListViewState::kFullscreenSearch);
  365. const gfx::RectF shelf_bounds = GetShelfBoundsInFloat();
  366. StartDrag();
  367. aura::Window* home_screen_window =
  368. app_list_controller()->GetHomeScreenWindow();
  369. ASSERT_TRUE(home_screen_window);
  370. const int transition_threshold =
  371. SwipeHomeToOverviewController::kVerticalThresholdForOverviewTransition;
  372. // Move above the transition threshold - verify the overview transition timer
  373. // has started.
  374. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold / 2),
  375. 0.f, 1.f);
  376. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  377. 0.f, 1.f);
  378. EXPECT_EQ(home_screen_window->transform(),
  379. home_screen_window->layer()->GetTargetTransform());
  380. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  381. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  382. EXPECT_TRUE(OverviewTransitionTimerRunning());
  383. EXPECT_FALSE(OverviewStarted());
  384. // Drag gesture getting canceled should reset the home view state.
  385. CancelDrag();
  386. EXPECT_EQ(home_screen_window->transform(),
  387. home_screen_window->layer()->GetTargetTransform());
  388. EXPECT_EQ(gfx::Transform(), home_screen_window->transform());
  389. EXPECT_EQ(1.f, home_screen_window->layer()->opacity());
  390. EXPECT_FALSE(OverviewTransitionTimerRunning());
  391. EXPECT_FALSE(OverviewStarted());
  392. // The gesture was not a fling - the home screen should have stayed in the
  393. // fullscreen search state.
  394. GetAppListTestHelper()->CheckState(AppListViewState::kFullscreenSearch);
  395. }
  396. TEST_F(SwipeHomeToOverviewControllerTest, DragMovementRestartsTimeout) {
  397. const gfx::RectF shelf_bounds = GetShelfBoundsInFloat();
  398. StartDrag();
  399. const int transition_threshold =
  400. SwipeHomeToOverviewController::kVerticalThresholdForOverviewTransition;
  401. // Move above the transition threshold - verify the overview transition timer
  402. // has started.
  403. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold / 2),
  404. 0.f, 1.f);
  405. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold), 0.f,
  406. 1.f);
  407. EXPECT_TRUE(OverviewTransitionTimerRunning());
  408. EXPECT_FALSE(OverviewStarted());
  409. const base::TimeDelta delay =
  410. GetTimerDesiredRunTime() - tick_clock_.NowTicks();
  411. EXPECT_GT(delay, base::TimeDelta());
  412. const float max_allowed_velocity =
  413. SwipeHomeToOverviewController::kMovementVelocityThreshold;
  414. // Advance clock, and simulate another drag whose speed is above the max
  415. // allowed.
  416. tick_clock_.Advance(base::Milliseconds(1));
  417. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, 2 * transition_threshold),
  418. 0.f, max_allowed_velocity + 10);
  419. // Verify the timer was stopped.
  420. EXPECT_FALSE(OverviewTransitionTimerRunning());
  421. EXPECT_FALSE(OverviewStarted());
  422. tick_clock_.Advance(base::Milliseconds(1));
  423. // Another slow drag should restart the timer.
  424. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, 2 * transition_threshold),
  425. 0.f, max_allowed_velocity / 2);
  426. EXPECT_TRUE(OverviewTransitionTimerRunning());
  427. EXPECT_FALSE(OverviewStarted());
  428. EXPECT_EQ(delay, GetTimerDesiredRunTime() - tick_clock_.NowTicks());
  429. }
  430. TEST_F(SwipeHomeToOverviewControllerTest,
  431. SmallDragMovementDoesNotRestartTimeout) {
  432. const gfx::RectF shelf_bounds = GetShelfBoundsInFloat();
  433. StartDrag();
  434. const int transition_threshold =
  435. SwipeHomeToOverviewController::kVerticalThresholdForOverviewTransition;
  436. // Move just below the transition threshold - verify overview transition timer
  437. // has not started.
  438. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold - 1),
  439. 0.f, 1.f);
  440. EXPECT_FALSE(OverviewTransitionTimerRunning());
  441. EXPECT_FALSE(OverviewStarted());
  442. // Move a little to reach the transition threshold - the timer should start at
  443. // this point.
  444. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold), 0.f,
  445. 1.f);
  446. EXPECT_TRUE(OverviewTransitionTimerRunning());
  447. EXPECT_FALSE(OverviewStarted());
  448. const base::TimeDelta delay =
  449. GetTimerDesiredRunTime() - tick_clock_.NowTicks();
  450. EXPECT_GT(delay, base::TimeDelta());
  451. const float movement_threshold =
  452. SwipeHomeToOverviewController::kMovementVelocityThreshold;
  453. // Advance clock, and simulate another drag, for an amount below the movement
  454. // threshold.
  455. tick_clock_.Advance(base::Milliseconds(1));
  456. Drag(shelf_bounds.top_center() -
  457. gfx::Vector2d(0, transition_threshold + movement_threshold - 1),
  458. 0.f, movement_threshold / 2);
  459. // Verify the expected timer run time was not updated.
  460. EXPECT_TRUE(OverviewTransitionTimerRunning());
  461. EXPECT_FALSE(OverviewStarted());
  462. EXPECT_EQ(delay - base::Milliseconds(1),
  463. GetTimerDesiredRunTime() - tick_clock_.NowTicks());
  464. // Movement with velocity above the allowed threshold restarts the timer.
  465. Drag(shelf_bounds.top_center() -
  466. gfx::Vector2d(0, transition_threshold + movement_threshold - 1),
  467. 0.f, movement_threshold + 1);
  468. EXPECT_FALSE(OverviewTransitionTimerRunning());
  469. EXPECT_FALSE(OverviewStarted());
  470. }
  471. TEST_F(SwipeHomeToOverviewControllerTest, DragBellowThresholdStopsTimer) {
  472. const gfx::RectF shelf_bounds = GetShelfBoundsInFloat();
  473. StartDrag();
  474. Drag(shelf_bounds.CenterPoint(), 0.f, 1.f);
  475. const int transition_threshold =
  476. SwipeHomeToOverviewController::kVerticalThresholdForOverviewTransition;
  477. // Move above the transition threshold - verify the overview transition timer
  478. // has started.
  479. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold / 2),
  480. 0.f, 1.f);
  481. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  482. 0.f, 1.f);
  483. aura::Window* home_screen_window =
  484. app_list_controller()->GetHomeScreenWindow();
  485. ASSERT_TRUE(home_screen_window);
  486. EXPECT_EQ(home_screen_window->transform(),
  487. home_screen_window->layer()->GetTargetTransform());
  488. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  489. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  490. EXPECT_TRUE(OverviewTransitionTimerRunning());
  491. EXPECT_FALSE(OverviewStarted());
  492. // Move bellow threshold, verify the timer has stopped.
  493. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold - 10),
  494. 0.f, 1.f);
  495. EXPECT_EQ(home_screen_window->transform(),
  496. home_screen_window->layer()->GetTargetTransform());
  497. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  498. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  499. EXPECT_FALSE(OverviewTransitionTimerRunning());
  500. EXPECT_FALSE(OverviewStarted());
  501. // Move further down, under the shelf.
  502. Drag(shelf_bounds.CenterPoint(), 0.f, 1.f);
  503. EXPECT_EQ(home_screen_window->transform(),
  504. home_screen_window->layer()->GetTargetTransform());
  505. EXPECT_EQ(gfx::Transform(), home_screen_window->transform());
  506. EXPECT_FALSE(OverviewTransitionTimerRunning());
  507. EXPECT_FALSE(OverviewStarted());
  508. // Move above the transition threshold again, the timer should be restarted..
  509. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  510. 0.f, 1.f);
  511. EXPECT_EQ(home_screen_window->transform(),
  512. home_screen_window->layer()->GetTargetTransform());
  513. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  514. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  515. EXPECT_TRUE(OverviewTransitionTimerRunning());
  516. EXPECT_FALSE(OverviewStarted());
  517. // Fire overview transition timer, and verify the overview has started.
  518. FireOverviewTransitionTimer();
  519. EXPECT_FALSE(OverviewTransitionTimerRunning());
  520. EXPECT_TRUE(OverviewStarted());
  521. // Home screen is still scaled down, and not visible.
  522. EXPECT_EQ(home_screen_window->transform(),
  523. home_screen_window->layer()->GetTargetTransform());
  524. EXPECT_TRUE(home_screen_window->transform().IsScaleOrTranslation());
  525. EXPECT_FALSE(home_screen_window->transform().IsIdentityOrTranslation());
  526. EXPECT_EQ(0.f, home_screen_window->layer()->opacity());
  527. }
  528. TEST_F(SwipeHomeToOverviewControllerTest, ScaleChangesDuringDrag) {
  529. const gfx::RectF shelf_bounds = GetShelfBoundsInFloat();
  530. StartDrag();
  531. Drag(shelf_bounds.CenterPoint(), 0.f, 1.f);
  532. aura::Window* home_screen_window =
  533. app_list_controller()->GetHomeScreenWindow();
  534. ASSERT_TRUE(home_screen_window);
  535. const gfx::RectF original_home_bounds(home_screen_window->bounds());
  536. const int transition_threshold =
  537. SwipeHomeToOverviewController::kVerticalThresholdForOverviewTransition;
  538. // Moving up should shrink home bounds.
  539. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold - 50),
  540. 0.f, 1.f);
  541. gfx::RectF last_home_bounds = original_home_bounds;
  542. home_screen_window->transform().TransformRect(&last_home_bounds);
  543. EXPECT_GT(original_home_bounds.width(), last_home_bounds.width());
  544. // Moving up should shrink home bounds further.
  545. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold + 10),
  546. 0.f, 1.f);
  547. gfx::RectF current_home_bounds = original_home_bounds;
  548. home_screen_window->transform().TransformRect(&current_home_bounds);
  549. EXPECT_GT(last_home_bounds.width(), current_home_bounds.width());
  550. last_home_bounds = current_home_bounds;
  551. // Moving down should expand bounds.
  552. Drag(shelf_bounds.top_center() - gfx::Vector2d(0, transition_threshold - 40),
  553. 0.f, 1.f);
  554. current_home_bounds = original_home_bounds;
  555. home_screen_window->transform().TransformRect(&current_home_bounds);
  556. EXPECT_LT(last_home_bounds.width(), current_home_bounds.width());
  557. last_home_bounds = current_home_bounds;
  558. // Horizontal movement should not change bounds.
  559. Drag(shelf_bounds.top_center() - gfx::Vector2d(50, transition_threshold - 40),
  560. 1.f, 0.f);
  561. current_home_bounds = original_home_bounds;
  562. home_screen_window->transform().TransformRect(&current_home_bounds);
  563. EXPECT_EQ(last_home_bounds, current_home_bounds);
  564. // At shelf top the home window should have no transform.
  565. Drag(shelf_bounds.top_center(), 0.f, 1.f);
  566. EXPECT_EQ(gfx::Transform(), home_screen_window->transform());
  567. }
  568. } // namespace ash