Home | History | Annotate | Download | only in app_list
      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 #include "ui/app_list/pagination_controller.h"
      6 
      7 #include "ui/app_list/pagination_model.h"
      8 #include "ui/events/event.h"
      9 #include "ui/gfx/geometry/rect.h"
     10 #include "ui/gfx/geometry/vector2d.h"
     11 
     12 namespace app_list {
     13 
     14 namespace {
     15 
     16 // Constants for dealing with scroll events.
     17 const int kMinScrollToSwitchPage = 20;
     18 const int kMinHorizVelocityToSwitchPage = 800;
     19 
     20 const double kFinishTransitionThreshold = 0.33;
     21 
     22 }  // namespace
     23 
     24 PaginationController::PaginationController(PaginationModel* model,
     25                                            ScrollAxis scroll_axis)
     26     : pagination_model_(model), scroll_axis_(scroll_axis) {
     27 }
     28 
     29 bool PaginationController::OnScroll(const gfx::Vector2d& offset) {
     30   int offset_magnitude;
     31   if (scroll_axis_ == SCROLL_AXIS_HORIZONTAL) {
     32     // If the view scrolls horizontally, both horizontal and vertical scroll
     33     // events are valid (since most mouse wheels only have vertical scrolling).
     34     offset_magnitude =
     35         abs(offset.x()) > abs(offset.y()) ? offset.x() : offset.y();
     36   } else {
     37     // If the view scrolls vertically, only vertical scroll events are valid.
     38     offset_magnitude = offset.y();
     39   }
     40 
     41   if (abs(offset_magnitude) > kMinScrollToSwitchPage) {
     42     if (!pagination_model_->has_transition()) {
     43       pagination_model_->SelectPageRelative(offset_magnitude > 0 ? -1 : 1,
     44                                             true);
     45     }
     46     return true;
     47   }
     48 
     49   return false;
     50 }
     51 
     52 bool PaginationController::OnGestureEvent(const ui::GestureEvent& event,
     53                                           const gfx::Rect& bounds) {
     54   const ui::GestureEventDetails& details = event.details();
     55   switch (event.type()) {
     56     case ui::ET_GESTURE_SCROLL_BEGIN:
     57       pagination_model_->StartScroll();
     58       return true;
     59     case ui::ET_GESTURE_SCROLL_UPDATE: {
     60       float scroll = scroll_axis_ == SCROLL_AXIS_HORIZONTAL
     61                          ? details.scroll_x()
     62                          : details.scroll_y();
     63       int width = scroll_axis_ == SCROLL_AXIS_HORIZONTAL ? bounds.width()
     64                                                          : bounds.height();
     65       // scroll > 0 means moving contents right or down. That is, transitioning
     66       // to the previous page.
     67       pagination_model_->UpdateScroll(scroll / width);
     68       return true;
     69     }
     70     case ui::ET_GESTURE_SCROLL_END:
     71       pagination_model_->EndScroll(pagination_model_->transition().progress <
     72                                    kFinishTransitionThreshold);
     73       return true;
     74     case ui::ET_SCROLL_FLING_START: {
     75       float velocity = scroll_axis_ == SCROLL_AXIS_HORIZONTAL
     76                            ? details.velocity_x()
     77                            : details.velocity_y();
     78       pagination_model_->EndScroll(true);
     79       if (fabs(velocity) > kMinHorizVelocityToSwitchPage)
     80         pagination_model_->SelectPageRelative(velocity < 0 ? 1 : -1, true);
     81       return true;
     82     }
     83     default:
     84       return false;
     85   }
     86 }
     87 
     88 }  // namespace app_list
     89