diff options
author | sadrul@chromium.org <sadrul@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-04-05 22:14:49 +0000 |
---|---|---|
committer | sadrul@chromium.org <sadrul@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-04-05 22:14:49 +0000 |
commit | 81675c914ddcaaf9f8f8ff2a8db1c5783223fd49 (patch) | |
tree | eccb226b79f2bbb98d4ec0514db5fede5931654d /ui/aura/gestures | |
parent | 19ce5c5150f0900e0365720bb2c9ccde589b07b7 (diff) | |
download | chromium_src-81675c914ddcaaf9f8f8ff2a8db1c5783223fd49.zip chromium_src-81675c914ddcaaf9f8f8ff2a8db1c5783223fd49.tar.gz chromium_src-81675c914ddcaaf9f8f8ff2a8db1c5783223fd49.tar.bz2 |
ui: Move gesture-recognizer into ui/base/.
Moving the gesture-recognizer into ui/base/ makes it possible to be used by both
aura and views independently. This is the first step: add an interface for
touch-events and gesture-events so that the gesture recognizer does not have to
depend on aura or views events.
BUG=121744
TEST=none
Review URL: https://chromiumcodereview.appspot.com/9958136
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@131023 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'ui/aura/gestures')
-rw-r--r-- | ui/aura/gestures/OWNERS | 3 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_configuration.cc | 33 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_configuration.h | 131 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_point.cc | 166 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_point.h | 108 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_recognizer.h | 71 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_recognizer_aura.cc | 201 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_recognizer_aura.h | 74 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_recognizer_unittest.cc | 75 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_sequence.cc | 584 | ||||
-rw-r--r-- | ui/aura/gestures/gesture_sequence.h | 163 | ||||
-rw-r--r-- | ui/aura/gestures/gestures.dot | 32 | ||||
-rw-r--r-- | ui/aura/gestures/velocity_calculator.cc | 109 | ||||
-rw-r--r-- | ui/aura/gestures/velocity_calculator.h | 51 | ||||
-rw-r--r-- | ui/aura/gestures/velocity_calculator_unittest.cc | 146 |
15 files changed, 39 insertions, 1908 deletions
diff --git a/ui/aura/gestures/OWNERS b/ui/aura/gestures/OWNERS deleted file mode 100644 index a324de8..0000000 --- a/ui/aura/gestures/OWNERS +++ /dev/null @@ -1,3 +0,0 @@ -# Do not set noparent -rjkroege@chromium.org -sadrul@chromium.org diff --git a/ui/aura/gestures/gesture_configuration.cc b/ui/aura/gestures/gesture_configuration.cc deleted file mode 100644 index 0ee11fa..0000000 --- a/ui/aura/gestures/gesture_configuration.cc +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ui/aura/gestures/gesture_configuration.h" - -namespace aura { - -// Ordered alphabetically ignoring underscores, to align with the -// associated list of prefs in gesture_prefs_aura.cc. -double GestureConfiguration::long_press_time_in_seconds_ = 0.5; -double GestureConfiguration::max_seconds_between_double_click_ = 0.7; -double - GestureConfiguration::max_separation_for_gesture_touches_in_pixels_ = 150; -double - GestureConfiguration::max_touch_down_duration_in_seconds_for_click_ = 0.8; -double GestureConfiguration::max_touch_move_in_pixels_for_click_ = 20; -double GestureConfiguration::min_distance_for_pinch_scroll_in_pixels_ = 20; -double GestureConfiguration::min_flick_speed_squared_ = 550.f * 550.f; -double GestureConfiguration::min_pinch_update_distance_in_pixels_ = 5; -double GestureConfiguration::min_rail_break_velocity_ = 200; -double GestureConfiguration::min_scroll_delta_squared_ = 5 * 5; -double - GestureConfiguration::min_touch_down_duration_in_seconds_for_click_ = 0.01; - -// The number of points used in the linear regression which determines -// touch velocity. If fewer than this number of points have been seen, -// velocity is reported as 0. -int GestureConfiguration::points_buffered_for_velocity_ = 10; -double GestureConfiguration::rail_break_proportion_ = 15; -double GestureConfiguration::rail_start_proportion_ = 2; - -} // namespace aura diff --git a/ui/aura/gestures/gesture_configuration.h b/ui/aura/gestures/gesture_configuration.h deleted file mode 100644 index 7564a8d..0000000 --- a/ui/aura/gestures/gesture_configuration.h +++ /dev/null @@ -1,131 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef UI_AURA_GESTURES_GESTURE_CONFIGURATION_H_ -#define UI_AURA_GESTURES_GESTURE_CONFIGURATION_H_ -#pragma once - -#include "base/basictypes.h" -#include "ui/aura/aura_export.h" - -namespace aura { - -// TODO: Expand this design to support multiple OS configuration -// approaches (windows, chrome, others). This would turn into an -// abstract base class. - -class AURA_EXPORT GestureConfiguration { - public: - // Ordered alphabetically ignoring underscores, to align with the - // associated list of prefs in gesture_prefs_aura.cc. - static double long_press_time_in_seconds() { - return long_press_time_in_seconds_; - } - static void set_long_press_time_in_seconds(double val) { - long_press_time_in_seconds_ = val; - } - static double max_seconds_between_double_click() { - return max_seconds_between_double_click_; - } - static void set_max_seconds_between_double_click(double val) { - max_seconds_between_double_click_ = val; - } - static int max_separation_for_gesture_touches_in_pixels() { - return max_separation_for_gesture_touches_in_pixels_; - } - static void set_max_separation_for_gesture_touches_in_pixels(int val) { - max_separation_for_gesture_touches_in_pixels_ = val; - } - static double max_touch_down_duration_in_seconds_for_click() { - return max_touch_down_duration_in_seconds_for_click_; - } - static void set_max_touch_down_duration_in_seconds_for_click(double val) { - max_touch_down_duration_in_seconds_for_click_ = val; - } - static double max_touch_move_in_pixels_for_click() { - return max_touch_move_in_pixels_for_click_; - } - static void set_max_touch_move_in_pixels_for_click(double val) { - max_touch_move_in_pixels_for_click_ = val; - } - static double min_distance_for_pinch_scroll_in_pixels() { - return min_distance_for_pinch_scroll_in_pixels_; - } - static void set_min_distance_for_pinch_scroll_in_pixels(double val) { - min_distance_for_pinch_scroll_in_pixels_ = val; - } - static double min_flick_speed_squared() { - return min_flick_speed_squared_; - } - static void set_min_flick_speed_squared(double val) { - min_flick_speed_squared_ = val; - } - static double min_pinch_update_distance_in_pixels() { - return min_pinch_update_distance_in_pixels_; - } - static void set_min_pinch_update_distance_in_pixels(double val) { - min_pinch_update_distance_in_pixels_ = val; - } - static double min_rail_break_velocity() { - return min_rail_break_velocity_; - } - static void set_min_rail_break_velocity(double val) { - min_rail_break_velocity_ = val; - } - static double min_scroll_delta_squared() { - return min_scroll_delta_squared_; - } - static void set_min_scroll_delta_squared(double val) { - min_scroll_delta_squared_ = val; - } - static double min_touch_down_duration_in_seconds_for_click() { - return min_touch_down_duration_in_seconds_for_click_; - } - static void set_min_touch_down_duration_in_seconds_for_click(double val) { - min_touch_down_duration_in_seconds_for_click_ = val; - } - static int points_buffered_for_velocity() { - return points_buffered_for_velocity_; - } - static void set_points_buffered_for_velocity(int val) { - points_buffered_for_velocity_ = val; - } - static double rail_break_proportion() { - return rail_break_proportion_; - } - static void set_rail_break_proportion(double val) { - rail_break_proportion_ = val; - } - static double rail_start_proportion() { - return rail_start_proportion_; - } - static void set_rail_start_proportion(double val) { - rail_start_proportion_ = val; - } - - private: - // These are listed in alphabetical order ignoring underscores, to - // align with the associated list of preferences in - // gesture_prefs_aura.cc. These two lists should be kept in sync. - static double long_press_time_in_seconds_; - static double max_seconds_between_double_click_; - static double max_separation_for_gesture_touches_in_pixels_; - static double max_touch_down_duration_in_seconds_for_click_; - static double max_touch_move_in_pixels_for_click_; - static double min_distance_for_pinch_scroll_in_pixels_; - static double min_flick_speed_squared_; - static double min_pinch_update_distance_in_pixels_; - static double min_rail_break_velocity_; - static double min_scroll_delta_squared_; - static double min_touch_down_duration_in_seconds_for_click_; - static int points_buffered_for_velocity_; - static double rail_break_proportion_; - static double rail_start_proportion_; - - DISALLOW_COPY_AND_ASSIGN(GestureConfiguration); -}; - -} // namespace aura - -#endif // UI_AURA_GESTURES_GESTURE_CONFIGURATION_H_ diff --git a/ui/aura/gestures/gesture_point.cc b/ui/aura/gestures/gesture_point.cc deleted file mode 100644 index 978b2d4..0000000 --- a/ui/aura/gestures/gesture_point.cc +++ /dev/null @@ -1,166 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ui/aura/gestures/gesture_point.h" - -#include <cmath> - -#include "base/basictypes.h" -#include "ui/aura/event.h" -#include "ui/aura/gestures/gesture_configuration.h" -#include "ui/base/events.h" - -namespace aura { - -GesturePoint::GesturePoint() - : first_touch_time_(0.0), - last_touch_time_(0.0), - last_tap_time_(0.0), - velocity_calculator_( - GestureConfiguration::points_buffered_for_velocity()), - point_id_(-1) { -} - -GesturePoint::~GesturePoint() {} - -void GesturePoint::Reset() { - first_touch_time_ = last_touch_time_ = 0.0; - velocity_calculator_.ClearHistory(); - point_id_ = -1; -} - -void GesturePoint::UpdateValues(const TouchEvent& event) { - const int64 event_timestamp_microseconds = - event.time_stamp().InMicroseconds(); - if (event.type() == ui::ET_TOUCH_MOVED) { - velocity_calculator_.PointSeen(event.x(), - event.y(), - event_timestamp_microseconds); - } - - last_touch_time_ = event.time_stamp().InSecondsF(); - last_touch_position_ = event.location(); - - if (event.type() == ui::ET_TOUCH_PRESSED) { - first_touch_time_ = last_touch_time_; - first_touch_position_ = event.location(); - velocity_calculator_.ClearHistory(); - velocity_calculator_.PointSeen(event.x(), - event.y(), - event_timestamp_microseconds); - } -} - -void GesturePoint::UpdateForTap() { - // Update the tap-position and time, and reset every other state. - last_tap_time_ = last_touch_time_; - last_tap_position_ = last_touch_position_; - Reset(); -} - -void GesturePoint::UpdateForScroll() { - // Update the first-touch position and time so that the scroll-delta and - // scroll-velocity can be computed correctly for the next scroll gesture - // event. - first_touch_position_ = last_touch_position_; - first_touch_time_ = last_touch_time_; -} - -bool GesturePoint::IsInClickWindow(const TouchEvent& event) const { - return IsInClickTimeWindow() && IsInsideManhattanSquare(event); -} - -bool GesturePoint::IsInDoubleClickWindow(const TouchEvent& event) const { - return IsInSecondClickTimeWindow() && - IsSecondClickInsideManhattanSquare(event); -} - -bool GesturePoint::IsInScrollWindow(const TouchEvent& event) const { - return event.type() == ui::ET_TOUCH_MOVED && - !IsInsideManhattanSquare(event); -} - -bool GesturePoint::IsInFlickWindow(const TouchEvent& event) { - return IsOverMinFlickSpeed() && event.type() != ui::ET_TOUCH_CANCELLED; -} - -bool GesturePoint::DidScroll(const TouchEvent& event, int dist) const { - return abs(last_touch_position_.x() - first_touch_position_.x()) > dist || - abs(last_touch_position_.y() - first_touch_position_.y()) > dist; -} - -float GesturePoint::Distance(const GesturePoint& point) const { - float x_diff = point.last_touch_position_.x() - last_touch_position_.x(); - float y_diff = point.last_touch_position_.y() - last_touch_position_.y(); - return sqrt(x_diff * x_diff + y_diff * y_diff); -} - -bool GesturePoint::HasEnoughDataToEstablishRail() const { - int dx = x_delta(); - int dy = y_delta(); - - int delta_squared = dx * dx + dy * dy; - return delta_squared > GestureConfiguration::min_scroll_delta_squared(); -} - -bool GesturePoint::IsInHorizontalRailWindow() const { - int dx = x_delta(); - int dy = y_delta(); - return abs(dx) > GestureConfiguration::rail_start_proportion() * abs(dy); -} - -bool GesturePoint::IsInVerticalRailWindow() const { - int dx = x_delta(); - int dy = y_delta(); - return abs(dy) > GestureConfiguration::rail_start_proportion() * abs(dx); -} - -bool GesturePoint::BreaksHorizontalRail() { - float vx = XVelocity(); - float vy = YVelocity(); - return fabs(vy) > GestureConfiguration::rail_break_proportion() * fabs(vx) + - GestureConfiguration::min_rail_break_velocity(); -} - -bool GesturePoint::BreaksVerticalRail() { - float vx = XVelocity(); - float vy = YVelocity(); - return fabs(vx) > GestureConfiguration::rail_break_proportion() * fabs(vy) + - GestureConfiguration::min_rail_break_velocity(); -} - -bool GesturePoint::IsInClickTimeWindow() const { - double duration = last_touch_time_ - first_touch_time_; - return duration >= - GestureConfiguration::min_touch_down_duration_in_seconds_for_click() && - duration < - GestureConfiguration::max_touch_down_duration_in_seconds_for_click(); -} - -bool GesturePoint::IsInSecondClickTimeWindow() const { - double duration = last_touch_time_ - last_tap_time_; - return duration < GestureConfiguration::max_seconds_between_double_click(); -} - -bool GesturePoint::IsInsideManhattanSquare(const TouchEvent& event) const { - int manhattanDistance = abs(event.x() - first_touch_position_.x()) + - abs(event.y() - first_touch_position_.y()); - return manhattanDistance < - GestureConfiguration::max_touch_move_in_pixels_for_click(); -} - -bool GesturePoint::IsSecondClickInsideManhattanSquare( - const TouchEvent& event) const { - int manhattanDistance = abs(event.x() - last_tap_position_.x()) + - abs(event.y() - last_tap_position_.y()); - return manhattanDistance < - GestureConfiguration::max_touch_move_in_pixels_for_click(); -} - -bool GesturePoint::IsOverMinFlickSpeed() { - return velocity_calculator_.VelocitySquared() > - GestureConfiguration::min_flick_speed_squared(); -} - -} // namespace aura diff --git a/ui/aura/gestures/gesture_point.h b/ui/aura/gestures/gesture_point.h deleted file mode 100644 index 95c5d3e..0000000 --- a/ui/aura/gestures/gesture_point.h +++ /dev/null @@ -1,108 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef UI_AURA_GESTURES_GESTURE_POINT_H_ -#define UI_AURA_GESTURES_GESTURE_POINT_H_ -#pragma once - -#include "base/basictypes.h" -#include "ui/aura/gestures/velocity_calculator.h" -#include "ui/gfx/point.h" - -namespace aura { -class TouchEvent; - -// A GesturePoint represents a single touch-point/finger during a gesture -// recognition process. -class GesturePoint { - public: - GesturePoint(); - ~GesturePoint(); - - // Resets various states. - void Reset(); - - // Updates some states when a Tap gesture has been recognized for this point. - void UpdateForTap(); - - // Updates some states when a Scroll gesture has been recognized for this - // point. - void UpdateForScroll(); - - // Updates states depending on the event and the gesture-state. - void UpdateValues(const TouchEvent& event); - - // Responds according to the state of the gesture point (i.e. the point can - // represent a click or scroll etc.) - bool IsInClickWindow(const TouchEvent& event) const; - bool IsInDoubleClickWindow(const TouchEvent& event) const; - bool IsInScrollWindow(const TouchEvent& event) const; - bool IsInFlickWindow(const TouchEvent& event); - bool IsInHorizontalRailWindow() const; - bool IsInVerticalRailWindow() const; - bool HasEnoughDataToEstablishRail() const; - bool BreaksHorizontalRail(); - bool BreaksVerticalRail(); - bool DidScroll(const TouchEvent& event, int distance) const; - - const gfx::Point& first_touch_position() const { - return first_touch_position_; - } - - double last_touch_time() const { return last_touch_time_; } - const gfx::Point& last_touch_position() const { return last_touch_position_; } - - // point_id_ is used to drive GestureSequence::ProcessTouchEventForGesture. - // point_ids are maintained such that the set of point_ids is always - // contiguous, from 0 to the number of current touches. - // A lower point_id indicates that a touch occurred first. - // A negative point_id indicates that the GesturePoint is not currently - // associated with a touch. - void set_point_id(int point_id) { point_id_ = point_id; } - int point_id() const { return point_id_; } - - void set_touch_id(int touch_id) { touch_id_ = touch_id; } - int touch_id() const { return touch_id_; } - - bool in_use() const { return point_id_ >= 0; } - - double x_delta() const { - return last_touch_position_.x() - first_touch_position_.x(); - } - - double y_delta() const { - return last_touch_position_.y() - first_touch_position_.y(); - } - - float XVelocity() { return velocity_calculator_.XVelocity(); } - float YVelocity() { return velocity_calculator_.YVelocity(); } - - float Distance(const GesturePoint& point) const; - - private: - // Various statistical functions to manipulate gestures. - bool IsInClickTimeWindow() const; - bool IsInSecondClickTimeWindow() const; - bool IsInsideManhattanSquare(const TouchEvent& event) const; - bool IsSecondClickInsideManhattanSquare(const TouchEvent& event) const; - bool IsOverMinFlickSpeed(); - - gfx::Point first_touch_position_; - double first_touch_time_; - gfx::Point last_touch_position_; - double last_touch_time_; - - double last_tap_time_; - gfx::Point last_tap_position_; - - VelocityCalculator velocity_calculator_; - - int point_id_; - int touch_id_; - DISALLOW_COPY_AND_ASSIGN(GesturePoint); -}; - -} // namespace aura - -#endif // UI_AURA_GESTURES_GESTURE_POINT_H_ diff --git a/ui/aura/gestures/gesture_recognizer.h b/ui/aura/gestures/gesture_recognizer.h deleted file mode 100644 index ce130c7..0000000 --- a/ui/aura/gestures/gesture_recognizer.h +++ /dev/null @@ -1,71 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef UI_AURA_GESTURES_GESTURE_RECOGNIZER_H_ -#define UI_AURA_GESTURES_GESTURE_RECOGNIZER_H_ -#pragma once - -#include <vector> - -#include "base/memory/linked_ptr.h" -#include "ui/aura/aura_export.h" -#include "ui/base/events.h" - -namespace aura { -class GestureEvent; -class RootWindow; -class TouchEvent; -class Window; - -// A GestureRecognizer is an abstract base class for conversion of touch events -// into gestures. -class AURA_EXPORT GestureRecognizer { - public: - static GestureRecognizer* Create(); - - // List of GestureEvent*. - typedef std::vector<linked_ptr<GestureEvent> > Gestures; - - virtual ~GestureRecognizer() {} - - // Invoked for each touch event that could contribute to the current gesture. - // Returns list of zero or more GestureEvents identified after processing - // TouchEvent. - // Caller would be responsible for freeing up Gestures. - virtual Gestures* ProcessTouchEventForGesture(const TouchEvent& event, - ui::TouchStatus status, - Window* target) = 0; - - // Touch-events can be queued to be played back at a later time. The queues - // are identified by the target window. - virtual void QueueTouchEventForGesture(Window* window, - const TouchEvent& event) = 0; - - // Process the touch-event in the queue for the window. Returns a list of - // zero or more GestureEvents identified after processing the queueud - // TouchEvent. Caller is responsible for freeing up Gestures. - virtual Gestures* AdvanceTouchQueue(Window* window, - bool processed) = 0; - - // Flushes the touch event queue (or removes the queue) for the window. - virtual void FlushTouchQueue(Window* window) = 0; - - // Return the window which should handle this TouchEvent, in the case where - // the touch is already associated with a target, or the touch occurs - // near another touch. - // Otherwise, returns null. - virtual Window* GetTargetForTouchEvent(TouchEvent* event) = 0; - - // Return the window which should handle this GestureEvent. - virtual Window* GetTargetForGestureEvent(GestureEvent* event) = 0; - - // If there is an active touch within - // GestureConfiguration::max_separation_for_gesture_touches_in_pixels, - // of |location|, returns the target of the nearest active touch. - virtual Window* GetTargetForLocation(const gfx::Point& location) = 0; -}; - -} // namespace aura - -#endif // UI_AURA_GESTURES_GESTURE_RECOGNIZER_H_ diff --git a/ui/aura/gestures/gesture_recognizer_aura.cc b/ui/aura/gestures/gesture_recognizer_aura.cc deleted file mode 100644 index 6760804..0000000 --- a/ui/aura/gestures/gesture_recognizer_aura.cc +++ /dev/null @@ -1,201 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ui/aura/gestures/gesture_recognizer_aura.h" - -#include "base/logging.h" -#include "base/memory/scoped_ptr.h" -#include "base/time.h" -#include "ui/aura/event.h" -#include "ui/aura/gestures/gesture_configuration.h" -#include "ui/aura/gestures/gesture_sequence.h" -#include "ui/aura/window.h" -#include "ui/base/events.h" - -namespace { -// This is used to pop a std::queue when returning from a function. -class ScopedPop { - public: - explicit ScopedPop(std::queue<aura::TouchEvent*>* queue) : queue_(queue) { - } - - ~ScopedPop() { - delete queue_->front(); - queue_->pop(); - } - - private: - std::queue<aura::TouchEvent*>* queue_; - DISALLOW_COPY_AND_ASSIGN(ScopedPop); -}; - -} // namespace - -namespace aura { - -//////////////////////////////////////////////////////////////////////////////// -// GestureRecognizerAura, public: - -GestureRecognizerAura::GestureRecognizerAura() { -} - -GestureRecognizerAura::~GestureRecognizerAura() { -} - -Window* GestureRecognizerAura::GetTargetForTouchEvent(TouchEvent* event) { - Window* target = touch_id_target_[event->touch_id()]; - if (!target) - target = GetTargetForLocation(event->location()); - return target; -} - -Window* GestureRecognizerAura::GetTargetForGestureEvent(GestureEvent* event) { - Window* target = NULL; - int touch_id = event->GetLowestTouchId(); - target = touch_id_target_for_gestures_[touch_id]; - return target; -} - -Window* GestureRecognizerAura::GetTargetForLocation( - const gfx::Point& location) { - const GesturePoint* closest_point = NULL; - int closest_distance_squared = 0; - std::map<Window*, GestureSequence*>::iterator i; - for (i = window_sequence_.begin(); i != window_sequence_.end(); ++i) { - const GesturePoint* points = i->second->points(); - for (int j = 0; j < GestureSequence::kMaxGesturePoints; ++j) { - if (!points[j].in_use()) - continue; - gfx::Point delta = - points[j].last_touch_position().Subtract(location); - int distance = delta.x() * delta.x() + delta.y() * delta.y(); - if ( !closest_point || distance < closest_distance_squared ) { - closest_point = &points[j]; - closest_distance_squared = distance; - } - } - } - - const int max_distance = - GestureConfiguration::max_separation_for_gesture_touches_in_pixels(); - - if (closest_distance_squared < max_distance * max_distance && closest_point) - return touch_id_target_[closest_point->touch_id()]; - else - return NULL; -} - -//////////////////////////////////////////////////////////////////////////////// -// GestureRecognizerAura, protected: - -GestureSequence* GestureRecognizerAura::CreateSequence( - RootWindow* root_window) { - return new GestureSequence(root_window); -} - -//////////////////////////////////////////////////////////////////////////////// -// GestureRecognizerAura, private: - -GestureSequence* GestureRecognizerAura::GetGestureSequenceForWindow( - Window* window) { - GestureSequence* gesture_sequence = window_sequence_[window]; - if (!gesture_sequence) { - gesture_sequence = CreateSequence(window->GetRootWindow()); - window_sequence_[window] = gesture_sequence; - } - return gesture_sequence; -} - -GestureSequence::Gestures* GestureRecognizerAura::ProcessTouchEventForGesture( - const TouchEvent& event, - ui::TouchStatus status, - Window* target) { - if (event.type() == ui::ET_TOUCH_RELEASED || - event.type() == ui::ET_TOUCH_CANCELLED) { - touch_id_target_[event.touch_id()] = NULL; - } else { - touch_id_target_[event.touch_id()] = target; - if (target) - touch_id_target_for_gestures_[event.touch_id()] = target; - } - - GestureSequence* gesture_sequence = GetGestureSequenceForWindow(target); - return gesture_sequence->ProcessTouchEventForGesture(event, status); -} - -void GestureRecognizerAura::QueueTouchEventForGesture(Window* window, - const TouchEvent& event) { - if (!event_queue_[window]) - event_queue_[window] = new std::queue<TouchEvent*>(); - event_queue_[window]->push(event.Copy()); -} - -GestureSequence::Gestures* GestureRecognizerAura::AdvanceTouchQueue( - Window* window, - bool processed) { - if (!event_queue_[window] || event_queue_[window]->empty()) { - LOG(ERROR) << "Trying to advance an empty gesture queue for " << window; - return NULL; - } - - ScopedPop pop(event_queue_[window]); - TouchEvent* event = event_queue_[window]->front(); - - GestureSequence* sequence = GetGestureSequenceForWindow(window); - - if (processed && event->type() == ui::ET_TOUCH_RELEASED) { - // A touch release was was processed (e.g. preventDefault()ed by a - // web-page), but we still need to process a touch cancel. - TouchEvent processed_event(ui::ET_TOUCH_CANCELLED, - event->location(), - event->touch_id(), - event->time_stamp()); - return sequence->ProcessTouchEventForGesture( - processed_event, - ui::TOUCH_STATUS_UNKNOWN); - } - - return sequence->ProcessTouchEventForGesture( - *event, - processed ? ui::TOUCH_STATUS_CONTINUE : ui::TOUCH_STATUS_UNKNOWN); -} - -void GestureRecognizerAura::FlushTouchQueue(Window* window) { - if (window_sequence_.count(window)) { - delete window_sequence_[window]; - window_sequence_.erase(window); - } - - if (event_queue_.count(window)) { - delete event_queue_[window]; - event_queue_.erase(window); - } - - int touch_id = -1; - std::map<int, Window*>::iterator i; - for (i = touch_id_target_.begin(); i != touch_id_target_.end(); ++i) { - if (i->second == window) - touch_id = i->first; - } - - if (touch_id_target_.count(touch_id)) - touch_id_target_.erase(touch_id); - - for (i = touch_id_target_for_gestures_.begin(); - i != touch_id_target_for_gestures_.end(); - ++i) { - if (i->second == window) - touch_id = i->first; - } - - if (touch_id_target_for_gestures_.count(touch_id)) - touch_id_target_for_gestures_.erase(touch_id); -} - -// GestureRecognizer, static -GestureRecognizer* GestureRecognizer::Create() { - return new GestureRecognizerAura(); -} - -} // namespace aura diff --git a/ui/aura/gestures/gesture_recognizer_aura.h b/ui/aura/gestures/gesture_recognizer_aura.h deleted file mode 100644 index 8c134be..0000000 --- a/ui/aura/gestures/gesture_recognizer_aura.h +++ /dev/null @@ -1,74 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef UI_AURA_GESTURES_GESTURE_RECOGNIZER_AURA_H_ -#define UI_AURA_GESTURES_GESTURE_RECOGNIZER_AURA_H_ -#pragma once - -#include <map> -#include <queue> -#include <vector> - -#include "base/memory/linked_ptr.h" -#include "base/memory/scoped_ptr.h" -#include "ui/aura/aura_export.h" -#include "ui/aura/gestures/gesture_recognizer.h" -#include "ui/base/events.h" -#include "ui/gfx/point.h" - -namespace aura { -class TouchEvent; -class GestureEvent; -class GestureSequence; - -class AURA_EXPORT GestureRecognizerAura : public GestureRecognizer { - public: - GestureRecognizerAura(); - virtual ~GestureRecognizerAura(); - - // Checks if this finger is already down, if so, returns the current target. - // Otherwise, if the finger is within - // GestureConfiguration::max_separation_for_gesture_touches_in_pixels - // of another touch, returns the target of the closest touch. - // If there is no nearby touch, return null. - virtual Window* GetTargetForTouchEvent(TouchEvent* event) OVERRIDE; - - // Returns the target of the touches the gesture is composed of. - virtual Window* GetTargetForGestureEvent(GestureEvent* event) OVERRIDE; - - virtual Window* GetTargetForLocation(const gfx::Point& location) OVERRIDE; - - protected: - virtual GestureSequence* CreateSequence(RootWindow* root_window); - virtual GestureSequence* GetGestureSequenceForWindow(Window* window); - - private: - // Overridden from GestureRecognizer - virtual Gestures* ProcessTouchEventForGesture( - const TouchEvent& event, - ui::TouchStatus status, - Window* target) OVERRIDE; - virtual void QueueTouchEventForGesture(Window* window, - const TouchEvent& event) OVERRIDE; - virtual Gestures* AdvanceTouchQueue(Window* window, bool processed) OVERRIDE; - virtual void FlushTouchQueue(Window* window) OVERRIDE; - - typedef std::queue<TouchEvent*> TouchEventQueue; - std::map<Window*, TouchEventQueue*> event_queue_; - std::map<Window*, GestureSequence*> window_sequence_; - - // Both touch_id_target_ and touch_id_target_for_gestures_ - // map a touch-id to its target window. - // touch_ids are removed from touch_id_target_ on ET_TOUCH_RELEASE - // and ET_TOUCH_CANCEL. touch_id_target_for_gestures_ never has touch_ids - // removed. - std::map<int, Window*> touch_id_target_; - std::map<int, Window*> touch_id_target_for_gestures_; - - DISALLOW_COPY_AND_ASSIGN(GestureRecognizerAura); -}; - -} // namespace aura - -#endif // UI_AURA_GESTURES_GESTURE_RECOGNIZER_AURA_H_ diff --git a/ui/aura/gestures/gesture_recognizer_unittest.cc b/ui/aura/gestures/gesture_recognizer_unittest.cc index caf9ff7..355b55e 100644 --- a/ui/aura/gestures/gesture_recognizer_unittest.cc +++ b/ui/aura/gestures/gesture_recognizer_unittest.cc @@ -6,13 +6,14 @@ #include "base/timer.h" #include "testing/gtest/include/gtest/gtest.h" #include "ui/aura/event.h" -#include "ui/aura/gestures/gesture_configuration.h" -#include "ui/aura/gestures/gesture_recognizer_aura.h" -#include "ui/aura/gestures/gesture_sequence.h" #include "ui/aura/root_window.h" #include "ui/aura/test/aura_test_base.h" #include "ui/aura/test/test_window_delegate.h" #include "ui/aura/test/test_windows.h" +#include "ui/base/gestures/gesture_configuration.h" +#include "ui/base/gestures/gesture_recognizer_impl.h" +#include "ui/base/gestures/gesture_sequence.h" +#include "ui/base/gestures/gesture_types.h" #include "ui/base/hit_test.h" #include "ui/gfx/point.h" #include "ui/gfx/rect.h" @@ -247,7 +248,7 @@ class GestureEventSynthDelegate : public TestWindowDelegate { }; class TestOneShotGestureSequenceTimer - : public base::OneShotTimer<GestureSequence> { + : public base::OneShotTimer<ui::GestureSequence> { public: void ForceTimeout() { if (IsRunning()) { @@ -257,10 +258,10 @@ class TestOneShotGestureSequenceTimer } }; -class TimerTestGestureSequence : public GestureSequence { +class TimerTestGestureSequence : public ui::GestureSequence { public: - explicit TimerTestGestureSequence(RootWindow* root_window) - : GestureSequence(root_window) { + explicit TimerTestGestureSequence(ui::GestureEventHelper* helper) + : ui::GestureSequence(helper) { } void ForceTimeout() { @@ -268,30 +269,31 @@ class TimerTestGestureSequence : public GestureSequence { long_press_timer())->ForceTimeout(); } - base::OneShotTimer<GestureSequence>* CreateTimer() { + base::OneShotTimer<ui::GestureSequence>* CreateTimer() { return new TestOneShotGestureSequenceTimer(); } }; -class TestGestureRecognizer : public GestureRecognizerAura { - public: - TestGestureRecognizer() - : GestureRecognizerAura() { +class TestGestureRecognizer : public ui::GestureRecognizerAura { + public: + explicit TestGestureRecognizer(RootWindow* root_window) + : GestureRecognizerAura(root_window) { } - GestureSequence* GetGestureSequenceForTesting(Window* window) { - return GetGestureSequenceForWindow(window); + ui::GestureSequence* GetGestureSequenceForTesting(Window* window) { + return GetGestureSequenceForConsumer(window); } }; class TimerTestGestureRecognizer : public TestGestureRecognizer { public: - TimerTestGestureRecognizer() - : TestGestureRecognizer() { + explicit TimerTestGestureRecognizer(RootWindow* root_window) + : TestGestureRecognizer(root_window) { } - virtual GestureSequence* CreateSequence(RootWindow* root_window) OVERRIDE { - return new TimerTestGestureSequence(root_window); + virtual ui::GestureSequence* CreateSequence( + ui::GestureEventHelper* helper) OVERRIDE { + return new TimerTestGestureSequence(helper); } }; @@ -474,7 +476,7 @@ TEST_F(GestureRecognizerTest, GestureEventHorizontalRailFling) { // Get a high x velocity, while still staying on the rail SendScrollEvents(root_window(), 1, 1, press.time_stamp(), 100, 10, kTouchId, 1, - GestureConfiguration::points_buffered_for_velocity(), + ui::GestureConfiguration::points_buffered_for_velocity(), delegate.get()); delegate->Reset(); @@ -510,7 +512,7 @@ TEST_F(GestureRecognizerTest, GestureEventVerticalRailFling) { // Get a high y velocity, while still staying on the rail SendScrollEvents(root_window(), 1, 1, press.time_stamp(), 10, 100, kTouchId, 1, - GestureConfiguration::points_buffered_for_velocity(), + ui::GestureConfiguration::points_buffered_for_velocity(), delegate.get()); delegate->Reset(); @@ -544,7 +546,7 @@ TEST_F(GestureRecognizerTest, GestureEventNonRailFling) { SendScrollEvents(root_window(), 1, 1, press.time_stamp(), 10, 100, kTouchId, 1, - GestureConfiguration::points_buffered_for_velocity(), + ui::GestureConfiguration::points_buffered_for_velocity(), delegate.get()); delegate->Reset(); @@ -571,7 +573,7 @@ TEST_F(GestureRecognizerTest, GestureEventLongPress) { delegate->Reset(); TimerTestGestureRecognizer* gesture_recognizer = - new TimerTestGestureRecognizer(); + new TimerTestGestureRecognizer(root_window()); TimerTestGestureSequence* gesture_sequence = static_cast<TimerTestGestureSequence*>( gesture_recognizer->GetGestureSequenceForTesting(window.get())); @@ -612,7 +614,7 @@ TEST_F(GestureRecognizerTest, GestureEventLongPressCancelledByScroll) { delegate->Reset(); TimerTestGestureRecognizer* gesture_recognizer = - new TimerTestGestureRecognizer(); + new TimerTestGestureRecognizer(root_window()); TimerTestGestureSequence* gesture_sequence = static_cast<TimerTestGestureSequence*>( gesture_recognizer->GetGestureSequenceForTesting(window.get())); @@ -653,7 +655,7 @@ TEST_F(GestureRecognizerTest, GestureEventLongPressCancelledByPinch) { delegate.get(), -1234, bounds, NULL)); TimerTestGestureRecognizer* gesture_recognizer = - new TimerTestGestureRecognizer(); + new TimerTestGestureRecognizer(root_window()); TimerTestGestureSequence* gesture_sequence = static_cast<TimerTestGestureSequence*>( gesture_recognizer->GetGestureSequenceForTesting(window.get())); @@ -720,7 +722,7 @@ TEST_F(GestureRecognizerTest, GestureEventHorizontalRailScroll) { // and we can break the rail SendScrollEvents(root_window(), 1, 1, press.time_stamp(), 1, 100, kTouchId, 1, - GestureConfiguration::points_buffered_for_velocity(), + ui::GestureConfiguration::points_buffered_for_velocity(), delegate.get()); SendScrollEvent(root_window(), 0, 0, kTouchId, delegate.get()); @@ -762,7 +764,7 @@ TEST_F(GestureRecognizerTest, GestureEventVerticalRailScroll) { // and we can break the rail SendScrollEvents(root_window(), 1, 1, press.time_stamp(), 100, 1, kTouchId, 1, - GestureConfiguration::points_buffered_for_velocity(), + ui::GestureConfiguration::points_buffered_for_velocity(), delegate.get()); SendScrollEvent(root_window(), 0, 0, kTouchId, delegate.get()); @@ -1322,13 +1324,13 @@ TEST_F(GestureRecognizerTest, GestureEventPinchScrollOnlyWhenBothFingersMove) { SendScrollEvents(root_window(), 100, 100, press1.time_stamp(), 1, 10, kTouchId1, 1, - GestureConfiguration::points_buffered_for_velocity(), + ui::GestureConfiguration::points_buffered_for_velocity(), delegate.get()); SendScrollEvents(root_window(), 110, 110, press1.time_stamp() + base::TimeDelta::FromMilliseconds(1000), 1, 10, kTouchId2, 1, - GestureConfiguration::points_buffered_for_velocity(), + ui::GestureConfiguration::points_buffered_for_velocity(), delegate.get()); // At no point were both fingers moving at the same time, // so no scrolling should have occurred @@ -1351,17 +1353,18 @@ TEST_F(GestureRecognizerTest, GestureEventIgnoresDisconnectedEvents) { // Check that a touch is locked to the window of the closest current touch // within max_separation_for_gesture_touches_in_pixels TEST_F(GestureRecognizerTest, GestureEventTouchLockSelectsCorrectWindow) { - GestureRecognizer* gesture_recognizer = - new GestureRecognizerAura(); + ui::GestureRecognizer* gesture_recognizer = + new ui::GestureRecognizerAura(root_window()); root_window()->SetGestureRecognizerForTesting(gesture_recognizer); - Window* target; + ui::GestureConsumer* target; const int kNumWindows = 4; scoped_array<GestureEventConsumeDelegate*> delegates( new GestureEventConsumeDelegate*[kNumWindows]); - GestureConfiguration::set_max_separation_for_gesture_touches_in_pixels(499); + ui::GestureConfiguration:: + set_max_separation_for_gesture_touches_in_pixels(499); scoped_array<gfx::Rect*> window_bounds(new gfx::Rect*[kNumWindows]); window_bounds[0] = new gfx::Rect(0, 0, 1, 1); @@ -1383,7 +1386,7 @@ TEST_F(GestureRecognizerTest, GestureEventTouchLockSelectsCorrectWindow) { } // Touches should now be associated with the closest touch within - // GestureConfiguration::max_separation_for_gesture_touches_in_pixels + // ui::GestureConfiguration::max_separation_for_gesture_touches_in_pixels target = gesture_recognizer->GetTargetForLocation(gfx::Point(11, 11)); EXPECT_EQ(windows[0], target); target = gesture_recognizer->GetTargetForLocation(gfx::Point(511, 11)); @@ -1430,16 +1433,16 @@ TEST_F(GestureRecognizerTest, GestureEventTouchLockSelectsCorrectWindow) { // by the root window's gesture sequence. TEST_F(GestureRecognizerTest, GestureEventOutsideRootWindowTap) { TestGestureRecognizer* gesture_recognizer = - new TestGestureRecognizer(); + new TestGestureRecognizer(root_window()); root_window()->SetGestureRecognizerForTesting(gesture_recognizer); scoped_ptr<aura::Window> window(CreateTestWindowWithBounds( gfx::Rect(-100, -100, 2000, 2000), NULL)); - GestureSequence* window_gesture_sequence = + ui::GestureSequence* window_gesture_sequence = gesture_recognizer->GetGestureSequenceForTesting(window.get()); - GestureSequence* root_window_gesture_sequence = + ui::GestureSequence* root_window_gesture_sequence = gesture_recognizer->GetGestureSequenceForTesting(root_window()); gfx::Point pos1(-10, -10); diff --git a/ui/aura/gestures/gesture_sequence.cc b/ui/aura/gestures/gesture_sequence.cc deleted file mode 100644 index 1372735..0000000 --- a/ui/aura/gestures/gesture_sequence.cc +++ /dev/null @@ -1,584 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ui/aura/gestures/gesture_sequence.h" - -#include "base/logging.h" -#include "base/memory/scoped_ptr.h" -#include "base/time.h" -#include "ui/aura/event.h" -#include "ui/aura/root_window.h" -#include "ui/aura/gestures/gesture_configuration.h" -#include "ui/base/events.h" - -namespace aura { - -namespace { - -// ui::EventType is mapped to TouchState so it can fit into 3 bits of -// Signature. -enum TouchState { - TS_RELEASED, - TS_PRESSED, - TS_MOVED, - TS_STATIONARY, - TS_CANCELLED, - TS_UNKNOWN, -}; - -// Get equivalent TouchState from EventType |type|. -TouchState TouchEventTypeToTouchState(ui::EventType type) { - switch (type) { - case ui::ET_TOUCH_RELEASED: - return TS_RELEASED; - case ui::ET_TOUCH_PRESSED: - return TS_PRESSED; - case ui::ET_TOUCH_MOVED: - return TS_MOVED; - case ui::ET_TOUCH_STATIONARY: - return TS_STATIONARY; - case ui::ET_TOUCH_CANCELLED: - return TS_CANCELLED; - default: - VLOG(1) << "Unknown Touch Event type"; - } - return TS_UNKNOWN; -} - -// Gesture signature types for different values of combination (GestureState, -// touch_id, ui::EventType, touch_handled), see Signature for more info. -// -// Note: New addition of types should be placed as per their Signature value. -#define G(gesture_state, id, touch_state, handled) 1 + ( \ - (((touch_state) & 0x7) << 1) | \ - ((handled) ? (1 << 4) : 0) | \ - (((id) & 0xfff) << 5) | \ - ((gesture_state) << 17)) - -enum EdgeStateSignatureType { - GST_NO_GESTURE_FIRST_PRESSED = - G(GS_NO_GESTURE, 0, TS_PRESSED, false), - - GST_PENDING_SYNTHETIC_CLICK_FIRST_RELEASED = - G(GS_PENDING_SYNTHETIC_CLICK, 0, TS_RELEASED, false), - - GST_PENDING_SYNTHETIC_CLICK_FIRST_MOVED = - G(GS_PENDING_SYNTHETIC_CLICK, 0, TS_MOVED, false), - - GST_PENDING_SYNTHETIC_CLICK_FIRST_STATIONARY = - G(GS_PENDING_SYNTHETIC_CLICK, 0, TS_STATIONARY, false), - - GST_PENDING_SYNTHETIC_CLICK_FIRST_CANCELLED = - G(GS_PENDING_SYNTHETIC_CLICK, 0, TS_CANCELLED, false), - - GST_PENDING_SYNTHETIC_CLICK_SECOND_PRESSED = - G(GS_PENDING_SYNTHETIC_CLICK, 1, TS_PRESSED, false), - - GST_SCROLL_FIRST_RELEASED = - G(GS_SCROLL, 0, TS_RELEASED, false), - - GST_SCROLL_FIRST_MOVED = - G(GS_SCROLL, 0, TS_MOVED, false), - - GST_SCROLL_FIRST_CANCELLED = - G(GS_SCROLL, 0, TS_CANCELLED, false), - - GST_SCROLL_SECOND_PRESSED = - G(GS_SCROLL, 1, TS_PRESSED, false), - - GST_PINCH_FIRST_MOVED = - G(GS_PINCH, 0, TS_MOVED, false), - - GST_PINCH_SECOND_MOVED = - G(GS_PINCH, 1, TS_MOVED, false), - - GST_PINCH_FIRST_RELEASED = - G(GS_PINCH, 0, TS_RELEASED, false), - - GST_PINCH_SECOND_RELEASED = - G(GS_PINCH, 1, TS_RELEASED, false), - - GST_PINCH_FIRST_CANCELLED = - G(GS_PINCH, 0, TS_CANCELLED, false), - - GST_PINCH_SECOND_CANCELLED = - G(GS_PINCH, 1, TS_CANCELLED, false), -}; - -// Builds a signature. Signatures are assembled by joining together -// multiple bits. -// 1 LSB bit so that the computed signature is always greater than 0 -// 3 bits for the |type|. -// 1 bit for |touch_handled| -// 12 bits for |touch_id| -// 15 bits for the |gesture_state|. -EdgeStateSignatureType Signature(GestureState gesture_state, - unsigned int touch_id, - ui::EventType type, - bool touch_handled) { - CHECK((touch_id & 0xfff) == touch_id); - TouchState touch_state = TouchEventTypeToTouchState(type); - return static_cast<EdgeStateSignatureType> - (G(gesture_state, touch_id, touch_state, touch_handled)); -} -#undef G - -} // namespace - -//////////////////////////////////////////////////////////////////////////////// -// GestureSequence Public: - -GestureSequence::GestureSequence(RootWindow* root_window) - : state_(GS_NO_GESTURE), - flags_(0), - pinch_distance_start_(0.f), - pinch_distance_current_(0.f), - long_press_timer_(CreateTimer()), - point_count_(0), - root_window_(root_window) { -} - -GestureSequence::~GestureSequence() { -} - -GestureSequence::Gestures* GestureSequence::ProcessTouchEventForGesture( - const TouchEvent& event, - ui::TouchStatus status) { - if (status != ui::TOUCH_STATUS_UNKNOWN) - return NULL; // The event was consumed by a touch sequence. - - // Set a limit on the number of simultaneous touches in a gesture. - if (event.touch_id() >= kMaxGesturePoints) - return NULL; - - if (event.type() == ui::ET_TOUCH_PRESSED) { - if (point_count_ == kMaxGesturePoints) - return NULL; - GesturePoint* new_point = &points_[event.touch_id()]; - // We shouldn't be able to get two PRESSED events from the same - // finger without either a RELEASE or CANCEL in between. - DCHECK(!points_[event.touch_id()].in_use()); - new_point->set_point_id(point_count_++); - new_point->set_touch_id(event.touch_id()); - } - - GestureState last_state = state_; - - // NOTE: when modifying these state transitions, also update gestures.dot - scoped_ptr<Gestures> gestures(new Gestures()); - GesturePoint& point = GesturePointForEvent(event); - point.UpdateValues(event); - flags_ = event.flags(); - const int point_id = points_[event.touch_id()].point_id(); - if (point_id < 0) - return NULL; - switch (Signature(state_, point_id, event.type(), false)) { - case GST_NO_GESTURE_FIRST_PRESSED: - TouchDown(event, point, gestures.get()); - set_state(GS_PENDING_SYNTHETIC_CLICK); - break; - case GST_PENDING_SYNTHETIC_CLICK_FIRST_RELEASED: - if (Click(event, point, gestures.get())) - point.UpdateForTap(); - set_state(GS_NO_GESTURE); - break; - case GST_PENDING_SYNTHETIC_CLICK_FIRST_MOVED: - case GST_PENDING_SYNTHETIC_CLICK_FIRST_STATIONARY: - if (ScrollStart(event, point, gestures.get())) { - set_state(GS_SCROLL); - if (ScrollUpdate(event, point, gestures.get())) - point.UpdateForScroll(); - } - break; - case GST_PENDING_SYNTHETIC_CLICK_FIRST_CANCELLED: - NoGesture(event, point, gestures.get()); - break; - case GST_SCROLL_FIRST_MOVED: - if (scroll_type_ == ST_VERTICAL || - scroll_type_ == ST_HORIZONTAL) - BreakRailScroll(event, point, gestures.get()); - if (ScrollUpdate(event, point, gestures.get())) - point.UpdateForScroll(); - break; - case GST_SCROLL_FIRST_RELEASED: - case GST_SCROLL_FIRST_CANCELLED: - ScrollEnd(event, point, gestures.get()); - set_state(GS_NO_GESTURE); - break; - case GST_SCROLL_SECOND_PRESSED: - case GST_PENDING_SYNTHETIC_CLICK_SECOND_PRESSED: - PinchStart(event, point, gestures.get()); - set_state(GS_PINCH); - break; - case GST_PINCH_FIRST_MOVED: - case GST_PINCH_SECOND_MOVED: - if (PinchUpdate(event, point, gestures.get())) { - GetPointByPointId(0)->UpdateForScroll(); - GetPointByPointId(1)->UpdateForScroll(); - } - break; - case GST_PINCH_FIRST_RELEASED: - case GST_PINCH_SECOND_RELEASED: - case GST_PINCH_FIRST_CANCELLED: - case GST_PINCH_SECOND_CANCELLED: - PinchEnd(event, point, gestures.get()); - - // Once pinch ends, it should still be possible to scroll with the - // remaining finger on the screen. - scroll_type_ = ST_FREE; - set_state(GS_SCROLL); - break; - } - - if (state_ != last_state) - VLOG(4) << "Gesture Sequence" - << " State: " << state_ - << " touch id: " << event.touch_id(); - - if (last_state == GS_PENDING_SYNTHETIC_CLICK && state_ != last_state) - long_press_timer_->Stop(); - - // The set of point_ids must be contiguous and include 0. - // When a touch point is released, all points with ids greater than the - // released point must have their ids decremented, or the set of point_ids - // could end up with gaps. - if (event.type() == ui::ET_TOUCH_RELEASED || - event.type() == ui::ET_TOUCH_CANCELLED) { - GesturePoint& old_point = points_[event.touch_id()]; - for (int i = 0; i < kMaxGesturePoints; ++i) { - GesturePoint& point = points_[i]; - if (point.point_id() > old_point.point_id()) - point.set_point_id(point.point_id() - 1); - } - old_point.Reset(); - --point_count_; - } - - return gestures.release(); -} - -void GestureSequence::Reset() { - set_state(GS_NO_GESTURE); - for (int i = 0; i < kMaxGesturePoints; ++i) - points_[i].Reset(); -} - -//////////////////////////////////////////////////////////////////////////////// -// GestureSequence Protected: - -base::OneShotTimer<GestureSequence>* GestureSequence::CreateTimer() { - return new base::OneShotTimer<GestureSequence>(); -} - -//////////////////////////////////////////////////////////////////////////////// -// GestureSequence Private: - -GesturePoint& GestureSequence::GesturePointForEvent( - const TouchEvent& event) { - return points_[event.touch_id()]; -} - -GesturePoint* GestureSequence::GetPointByPointId(int point_id) { - DCHECK(0 <= point_id && point_id < kMaxGesturePoints); - for (int i = 0; i < kMaxGesturePoints; ++i) { - GesturePoint& point = points_[i]; - if (point.in_use() && point.point_id() == point_id) - return &point; - } - NOTREACHED(); - return NULL; -} - -void GestureSequence::AppendTapDownGestureEvent(const GesturePoint& point, - Gestures* gestures) { - gestures->push_back(linked_ptr<GestureEvent>(new GestureEvent( - ui::ET_GESTURE_TAP_DOWN, - point.first_touch_position().x(), - point.first_touch_position().y(), - flags_, - base::Time::FromDoubleT(point.last_touch_time()), - 0.f, 0.f, 1 << point.touch_id()))); -} - -void GestureSequence::AppendClickGestureEvent(const GesturePoint& point, - Gestures* gestures) { - gestures->push_back(linked_ptr<GestureEvent>(new GestureEvent( - ui::ET_GESTURE_TAP, - point.first_touch_position().x(), - point.first_touch_position().y(), - flags_, - base::Time::FromDoubleT(point.last_touch_time()), - 0.f, 0.f, 1 << point.touch_id()))); -} - -void GestureSequence::AppendDoubleClickGestureEvent(const GesturePoint& point, - Gestures* gestures) { - gestures->push_back(linked_ptr<GestureEvent>(new GestureEvent( - ui::ET_GESTURE_DOUBLE_TAP, - point.first_touch_position().x(), - point.first_touch_position().y(), - flags_, - base::Time::FromDoubleT(point.last_touch_time()), - 0.f, 0.f, 1 << point.touch_id()))); -} - -void GestureSequence::AppendScrollGestureBegin(const GesturePoint& point, - const gfx::Point& location, - Gestures* gestures) { - gestures->push_back(linked_ptr<GestureEvent>(new GestureEvent( - ui::ET_GESTURE_SCROLL_BEGIN, - location.x(), - location.y(), - flags_, - base::Time::FromDoubleT(point.last_touch_time()), - 0.f, 0.f, 1 << point.touch_id()))); -} - -void GestureSequence::AppendScrollGestureEnd(const GesturePoint& point, - const gfx::Point& location, - Gestures* gestures, - float x_velocity, - float y_velocity) { - float railed_x_velocity = x_velocity; - float railed_y_velocity = y_velocity; - - if (scroll_type_ == ST_HORIZONTAL) - railed_y_velocity = 0; - else if (scroll_type_ == ST_VERTICAL) - railed_x_velocity = 0; - - gestures->push_back(linked_ptr<GestureEvent>(new GestureEvent( - ui::ET_GESTURE_SCROLL_END, - location.x(), - location.y(), - flags_, - base::Time::FromDoubleT(point.last_touch_time()), - railed_x_velocity, railed_y_velocity, 1 << point.touch_id()))); -} - -void GestureSequence::AppendScrollGestureUpdate(const GesturePoint& point, - const gfx::Point& location, - Gestures* gestures) { - int dx = point.x_delta(); - int dy = point.y_delta(); - - if (scroll_type_ == ST_HORIZONTAL) - dy = 0; - else if (scroll_type_ == ST_VERTICAL) - dx = 0; - - gestures->push_back(linked_ptr<GestureEvent>(new GestureEvent( - ui::ET_GESTURE_SCROLL_UPDATE, - location.x(), - location.y(), - flags_, - base::Time::FromDoubleT(point.last_touch_time()), - dx, dy, 1 << point.touch_id()))); -} - -void GestureSequence::AppendPinchGestureBegin(const GesturePoint& p1, - const GesturePoint& p2, - Gestures* gestures) { - gfx::Point center = p1.last_touch_position().Middle(p2.last_touch_position()); - gestures->push_back(linked_ptr<GestureEvent>(new GestureEvent( - ui::ET_GESTURE_PINCH_BEGIN, - center.x(), - center.y(), - flags_, - base::Time::FromDoubleT(p1.last_touch_time()), - 0.f, 0.f, 1 << p1.touch_id() | 1 << p2.touch_id()))); -} - -void GestureSequence::AppendPinchGestureEnd(const GesturePoint& p1, - const GesturePoint& p2, - float scale, - Gestures* gestures) { - gfx::Point center = p1.last_touch_position().Middle(p2.last_touch_position()); - gestures->push_back(linked_ptr<GestureEvent>(new GestureEvent( - ui::ET_GESTURE_PINCH_END, - center.x(), - center.y(), - flags_, - base::Time::FromDoubleT(p1.last_touch_time()), - scale, 0.f, 1 << p1.touch_id() | 1 << p2.touch_id()))); -} - -void GestureSequence::AppendPinchGestureUpdate(const GesturePoint& p1, - const GesturePoint& p2, - float scale, - Gestures* gestures) { - // TODO(sad): Compute rotation and include it in delta_y. - // http://crbug.com/113145 - gfx::Point center = p1.last_touch_position().Middle(p2.last_touch_position()); - gestures->push_back(linked_ptr<GestureEvent>(new GestureEvent( - ui::ET_GESTURE_PINCH_UPDATE, - center.x(), - center.y(), - flags_, - base::Time::FromDoubleT(p1.last_touch_time()), - scale, 0.f, 1 << p1.touch_id() | 1 << p2.touch_id()))); -} - -bool GestureSequence::Click(const TouchEvent& event, - const GesturePoint& point, Gestures* gestures) { - DCHECK(state_ == GS_PENDING_SYNTHETIC_CLICK); - if (point.IsInClickWindow(event)) { - AppendClickGestureEvent(point, gestures); - if (point.IsInDoubleClickWindow(event)) - AppendDoubleClickGestureEvent(point, gestures); - return true; - } - return false; -} - -bool GestureSequence::ScrollStart(const TouchEvent& event, - GesturePoint& point, Gestures* gestures) { - DCHECK(state_ == GS_PENDING_SYNTHETIC_CLICK); - if (point.IsInClickWindow(event) || - !point.IsInScrollWindow(event) || - !point.HasEnoughDataToEstablishRail()) - return false; - AppendScrollGestureBegin(point, point.first_touch_position(), gestures); - if (point.IsInHorizontalRailWindow()) - scroll_type_ = ST_HORIZONTAL; - else if (point.IsInVerticalRailWindow()) - scroll_type_ = ST_VERTICAL; - else - scroll_type_ = ST_FREE; - return true; -} - -void GestureSequence::BreakRailScroll(const TouchEvent& event, - GesturePoint& point, Gestures* gestures) { - DCHECK(state_ == GS_SCROLL); - if (scroll_type_ == ST_HORIZONTAL && - point.BreaksHorizontalRail()) - scroll_type_ = ST_FREE; - else if (scroll_type_ == ST_VERTICAL && - point.BreaksVerticalRail()) - scroll_type_ = ST_FREE; -} - -bool GestureSequence::ScrollUpdate(const TouchEvent& event, - const GesturePoint& point, Gestures* gestures) { - DCHECK(state_ == GS_SCROLL); - if (!point.DidScroll(event, 0)) - return false; - AppendScrollGestureUpdate(point, point.last_touch_position(), gestures); - return true; -} - -bool GestureSequence::NoGesture(const TouchEvent&, - const GesturePoint& point, Gestures*) { - Reset(); - return false; -} - -bool GestureSequence::TouchDown(const TouchEvent& event, - const GesturePoint& point, Gestures* gestures) { - DCHECK(state_ == GS_NO_GESTURE); - AppendTapDownGestureEvent(point, gestures); - long_press_timer_->Start( - FROM_HERE, - base::TimeDelta::FromMilliseconds( - GestureConfiguration::long_press_time_in_seconds() * 1000), - this, - &GestureSequence::AppendLongPressGestureEvent); - return true; -} - -void GestureSequence::AppendLongPressGestureEvent() { - const GesturePoint* point = GetPointByPointId(0); - GestureEvent gesture( - ui::ET_GESTURE_LONG_PRESS, - point->first_touch_position().x(), - point->first_touch_position().y(), - flags_, - base::Time::FromDoubleT(point->last_touch_time()), - point->point_id(), 0.f, 1 << point->touch_id()); - root_window_->DispatchGestureEvent(&gesture); -} - -bool GestureSequence::ScrollEnd(const TouchEvent& event, - GesturePoint& point, Gestures* gestures) { - DCHECK(state_ == GS_SCROLL); - if (point.IsInFlickWindow(event)) { - AppendScrollGestureEnd(point, point.last_touch_position(), gestures, - point.XVelocity(), point.YVelocity()); - } else { - AppendScrollGestureEnd(point, point.last_touch_position(), gestures, - 0.f, 0.f); - } - return true; -} - -bool GestureSequence::PinchStart(const TouchEvent& event, - const GesturePoint& point, Gestures* gestures) { - DCHECK(state_ == GS_SCROLL || - state_ == GS_PENDING_SYNTHETIC_CLICK); - AppendTapDownGestureEvent(point, gestures); - - const GesturePoint* point1 = GetPointByPointId(0); - const GesturePoint* point2 = GetPointByPointId(1); - - pinch_distance_current_ = point1->Distance(*point2); - pinch_distance_start_ = pinch_distance_current_; - AppendPinchGestureBegin(*point1, *point2, gestures); - - if (state_ == GS_PENDING_SYNTHETIC_CLICK) { - gfx::Point center = point1->last_touch_position().Middle( - point2->last_touch_position()); - AppendScrollGestureBegin(point, center, gestures); - } - - return true; -} - -bool GestureSequence::PinchUpdate(const TouchEvent& event, - const GesturePoint& point, Gestures* gestures) { - DCHECK(state_ == GS_PINCH); - - const GesturePoint* point1 = GetPointByPointId(0); - const GesturePoint* point2 = GetPointByPointId(1); - - float distance = point1->Distance(*point2); - if (abs(distance - pinch_distance_current_) < - GestureConfiguration::min_pinch_update_distance_in_pixels()) { - // The fingers didn't move towards each other, or away from each other, - // enough to constitute a pinch. But perhaps they moved enough in the same - // direction to do a two-finger scroll. - if (!point1->DidScroll(event, - GestureConfiguration::min_distance_for_pinch_scroll_in_pixels()) || - !point2->DidScroll(event, - GestureConfiguration::min_distance_for_pinch_scroll_in_pixels())) - return false; - - gfx::Point center = point1->last_touch_position().Middle( - point2->last_touch_position()); - AppendScrollGestureUpdate(point, center, gestures); - } else { - AppendPinchGestureUpdate(*point1, *point2, - distance / pinch_distance_current_, gestures); - pinch_distance_current_ = distance; - } - return true; -} - -bool GestureSequence::PinchEnd(const TouchEvent& event, - const GesturePoint& point, Gestures* gestures) { - DCHECK(state_ == GS_PINCH); - - const GesturePoint* point1 = GetPointByPointId(0); - const GesturePoint* point2 = GetPointByPointId(1); - - float distance = point1->Distance(*point2); - AppendPinchGestureEnd(*point1, *point2, - distance / pinch_distance_start_, gestures); - - pinch_distance_start_ = 0; - pinch_distance_current_ = 0; - return true; -} - -} // namespace aura diff --git a/ui/aura/gestures/gesture_sequence.h b/ui/aura/gestures/gesture_sequence.h deleted file mode 100644 index 4f71934..0000000 --- a/ui/aura/gestures/gesture_sequence.h +++ /dev/null @@ -1,163 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef UI_AURA_GESTURES_GESTURE_SEQUENCE_H_ -#define UI_AURA_GESTURES_GESTURE_SEQUENCE_H_ -#pragma once - -#include "base/timer.h" -#include "ui/aura/gestures/gesture_point.h" -#include "ui/aura/gestures/gesture_recognizer.h" -#include "ui/base/events.h" - -namespace aura { -class TouchEvent; -class GestureEvent; - -// Gesture state. -enum GestureState { - GS_NO_GESTURE, - GS_PENDING_SYNTHETIC_CLICK, - GS_SCROLL, - GS_PINCH -}; - -enum ScrollType { - ST_FREE, - ST_HORIZONTAL, - ST_VERTICAL, -}; - -// A GestureSequence recognizes gestures from touch sequences. -class AURA_EXPORT GestureSequence { - public: - explicit GestureSequence(RootWindow* root_window); - virtual ~GestureSequence(); - - typedef GestureRecognizer::Gestures Gestures; - - // Invoked for each touch event that could contribute to the current gesture. - // Returns list of zero or more GestureEvents identified after processing - // TouchEvent. - // Caller would be responsible for freeing up Gestures. - virtual Gestures* ProcessTouchEventForGesture(const TouchEvent& event, - ui::TouchStatus status); - const GesturePoint* points() const { return points_; } - int point_count() const { return point_count_; } - - // Maximum number of points in a single gesture. - static const int kMaxGesturePoints = 12; - - protected: - virtual base::OneShotTimer<GestureSequence>* CreateTimer(); - base::OneShotTimer<GestureSequence>* long_press_timer() { - return long_press_timer_.get(); - } - - private: - void Reset(); - - GesturePoint& GesturePointForEvent(const TouchEvent& event); - - // Do a linear scan through points_ to find the GesturePoint - // with id |point_id|. - GesturePoint* GetPointByPointId(int point_id); - - // Functions to be called to add GestureEvents, after successful recognition. - - // Tap gestures. - void AppendTapDownGestureEvent(const GesturePoint& point, Gestures* gestures); - void AppendClickGestureEvent(const GesturePoint& point, Gestures* gestures); - void AppendDoubleClickGestureEvent(const GesturePoint& point, - Gestures* gestures); - void AppendLongPressGestureEvent(); - - // Scroll gestures. - void AppendScrollGestureBegin(const GesturePoint& point, - const gfx::Point& location, - Gestures* gestures); - void AppendScrollGestureEnd(const GesturePoint& point, - const gfx::Point& location, - Gestures* gestures, - float x_velocity, - float y_velocity); - void AppendScrollGestureUpdate(const GesturePoint& point, - const gfx::Point& location, - Gestures* gestures); - - // Pinch gestures. - void AppendPinchGestureBegin(const GesturePoint& p1, - const GesturePoint& p2, - Gestures* gestures); - void AppendPinchGestureEnd(const GesturePoint& p1, - const GesturePoint& p2, - float scale, - Gestures* gestures); - void AppendPinchGestureUpdate(const GesturePoint& p1, - const GesturePoint& p2, - float scale, - Gestures* gestures); - - void set_state(const GestureState state ) { state_ = state; } - - // Various GestureTransitionFunctions for a signature. - // There is, 1:many mapping from GestureTransitionFunction to Signature - // But a Signature have only one GestureTransitionFunction. - bool Click(const TouchEvent& event, - const GesturePoint& point, - Gestures* gestures); - bool ScrollStart(const TouchEvent& event, - GesturePoint& point, - Gestures* gestures); - void BreakRailScroll(const TouchEvent& event, - GesturePoint& point, - Gestures* gestures); - bool ScrollUpdate(const TouchEvent& event, - const GesturePoint& point, - Gestures* gestures); - bool NoGesture(const TouchEvent& event, - const GesturePoint& point, - Gestures* gestures); - bool TouchDown(const TouchEvent& event, - const GesturePoint& point, - Gestures* gestures); - bool ScrollEnd(const TouchEvent& event, - GesturePoint& point, - Gestures* gestures); - bool PinchStart(const TouchEvent& event, - const GesturePoint& point, - Gestures* gestures); - bool PinchUpdate(const TouchEvent& event, - const GesturePoint& point, - Gestures* gestures); - bool PinchEnd(const TouchEvent& event, - const GesturePoint& point, - Gestures* gestures); - - // Current state of gesture recognizer. - GestureState state_; - - // ui::EventFlags. - int flags_; - - // The distance between the two points at PINCH_START. - float pinch_distance_start_; - - // This distance is updated after each PINCH_UPDATE. - float pinch_distance_current_; - - ScrollType scroll_type_; - scoped_ptr<base::OneShotTimer<GestureSequence> > long_press_timer_; - - GesturePoint points_[kMaxGesturePoints]; - int point_count_; - - RootWindow* root_window_; - - DISALLOW_COPY_AND_ASSIGN(GestureSequence); -}; - -} // namespace aura - -#endif // UI_AURA_GESTURES_GESTURE_SEQUENCE_H_ diff --git a/ui/aura/gestures/gestures.dot b/ui/aura/gestures/gestures.dot deleted file mode 100644 index a095575..0000000 --- a/ui/aura/gestures/gestures.dot +++ /dev/null @@ -1,32 +0,0 @@ -// A diagram of the state machine found in gesture_sequence.cc -// To generate a pdf: -// dot -Tpdf -ooutput.pdf gestures.dot -// -// If you alter this diagram, please update: -// sites.google.com/a/chromium.org/dev/developers/design-documents/aura/gesture-recognizer - -digraph G { -ratio = 1; - -legend[label = "{ \ -M : Move \l\ -D : Down \l\ -S : Stationary \l\ -C : Cancel \l\ -R : Release \l}" -shape = record] - -subgraph none_pending { -GS_NO_GESTURE -> GS_PENDING_SYNTHETIC_CLICK [label= "D0"]; -GS_PENDING_SYNTHETIC_CLICK -> GS_SCROLL [label= "M0\n S0"]; -GS_PENDING_SYNTHETIC_CLICK -> GS_PENDING_SYNTHETIC_CLICK [label= "M0\n S0"]; -GS_PENDING_SYNTHETIC_CLICK -> GS_NO_GESTURE [label= "C0\n R0"]; -} - -GS_SCROLL -> GS_SCROLL [label= "M0"]; -GS_SCROLL -> GS_NO_GESTURE [label= "C0\n R0\n"]; -GS_PENDING_SYNTHETIC_CLICK -> GS_PINCH [label= "D1"]; -GS_SCROLL -> GS_PINCH [label= "D1"]; -GS_PINCH -> GS_PINCH [label= "M0\n M1"]; -GS_PINCH -> GS_SCROLL [label= "C0\n R0\n C1\n R1"]; -} diff --git a/ui/aura/gestures/velocity_calculator.cc b/ui/aura/gestures/velocity_calculator.cc deleted file mode 100644 index 7b475fd..0000000 --- a/ui/aura/gestures/velocity_calculator.cc +++ /dev/null @@ -1,109 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "ui/aura/gestures/velocity_calculator.h" - -namespace aura { - -VelocityCalculator::VelocityCalculator(int buffer_size) - : buffer_(new Point[buffer_size]) , - index_(0), - num_valid_entries_(0), - buffer_size_(buffer_size), - x_velocity_(0), - y_velocity_(0), - velocities_stale_(false) { -} - -VelocityCalculator::~VelocityCalculator() {} - -float VelocityCalculator::XVelocity() { - if (velocities_stale_) - UpdateVelocity(); - return x_velocity_; -} - -float VelocityCalculator::YVelocity() { - if (velocities_stale_) - UpdateVelocity(); - return y_velocity_; -} - -void VelocityCalculator::PointSeen(int x, int y, int64 time) { - buffer_[index_].x = x; - buffer_[index_].y = y; - buffer_[index_].time = time; - - index_ = (index_ + 1) % buffer_size_; - if (num_valid_entries_ < buffer_size_) - ++num_valid_entries_; - - velocities_stale_ = true; -} - -float VelocityCalculator::VelocitySquared() { - if (velocities_stale_) - UpdateVelocity(); - return x_velocity_ * x_velocity_ + y_velocity_ * y_velocity_; -} - -void VelocityCalculator::UpdateVelocity() { - // We don't have enough data to make a good estimate of the velocity. - if (num_valid_entries_ < buffer_size_) - return; - - // Where A_i = A[i] - mean(A) - // x velocity = sum_i(x_i * t_i) / sum_i(t_i * t_i) - // This is an Ordinary Least Squares Regression. - - float mean_x = 0; - float mean_y = 0; - int64 mean_time = 0; - - for (size_t i = 0; i < buffer_size_; ++i) { - mean_x += buffer_[i].x; - mean_y += buffer_[i].y; - mean_time += buffer_[i].time; - } - - // Minimize number of divides. - const float buffer_size_i = 1.0f / buffer_size_; - - mean_x *= buffer_size_i; - mean_y *= buffer_size_i; - - // The loss in accuracy due to rounding is insignificant compared to - // the error due to the resolution of the timer. - // Use integer division to avoid the cast to double, which would cause - // VelocityCalculatorTest.IsAccurateWithLargeTimes to fail. - mean_time /= buffer_size_; - - float xt = 0; // sum_i(x_i * t_i) - float yt = 0; // sum_i(y_i * t_i) - int64 tt = 0; // sum_i(t_i * t_i) - - int64 t_i; - - for (size_t i = 0; i < buffer_size_; ++i) { - t_i = (buffer_[i].time - mean_time); - xt += (buffer_[i].x - mean_x) * t_i; - yt += (buffer_[i].y - mean_y) * t_i; - tt += t_i * t_i; - } - - // Convert time from microseconds to seconds. - x_velocity_ = xt / (tt / 1000000.0f); - y_velocity_ = yt / (tt / 1000000.0f); - velocities_stale_ = false; -} - -void VelocityCalculator::ClearHistory() { - index_ = 0; - num_valid_entries_ = 0; - x_velocity_ = 0; - y_velocity_ = 0; - velocities_stale_ = false; -} - -} // namespace aura diff --git a/ui/aura/gestures/velocity_calculator.h b/ui/aura/gestures/velocity_calculator.h deleted file mode 100644 index 28df0d7..0000000 --- a/ui/aura/gestures/velocity_calculator.h +++ /dev/null @@ -1,51 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef UI_AURA_GESTURES_VELOCITY_CALCULATOR_H_ -#define UI_AURA_GESTURES_VELOCITY_CALCULATOR_H_ -#pragma once - -#include <vector> - -#include "base/basictypes.h" -#include "base/memory/scoped_ptr.h" -#include "ui/aura/aura_export.h" - -namespace aura { - -class AURA_EXPORT VelocityCalculator { - public: - explicit VelocityCalculator(int bufferSize); - ~VelocityCalculator(); - void PointSeen(int x, int y, int64 time); - float XVelocity(); - float YVelocity(); - float VelocitySquared(); - void ClearHistory(); - - private: - struct Point { - int x; - int y; - int64 time; - }; - - void UpdateVelocity(); - - typedef scoped_array<Point> HistoryBuffer; - HistoryBuffer buffer_; - - // index_ points directly after the last point added. - int index_; - size_t num_valid_entries_; - const size_t buffer_size_; - float x_velocity_; - float y_velocity_; - bool velocities_stale_; - DISALLOW_COPY_AND_ASSIGN(VelocityCalculator); -}; - -} // namespace aura - -#endif // UI_AURA_GESTURES_VELOCITY_CALCULATOR_H_ diff --git a/ui/aura/gestures/velocity_calculator_unittest.cc b/ui/aura/gestures/velocity_calculator_unittest.cc deleted file mode 100644 index 5df0987..0000000 --- a/ui/aura/gestures/velocity_calculator_unittest.cc +++ /dev/null @@ -1,146 +0,0 @@ -// Copyright (c) 2012 The Chromium Authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "base/basictypes.h" -#include "testing/gtest/include/gtest/gtest.h" -#include "ui/aura/gestures/velocity_calculator.h" -#include "ui/aura/test/aura_test_base.h" - -namespace aura { -namespace test { - -namespace { - -static void AddPoints(VelocityCalculator* velocity_calculator, - float x_increment, - float y_increment, - float time_increment_seconds, - int num_points) { - float x = 0; - float y = 0; - double time = 0; - - for (int i = 0; i < num_points; ++i) { - velocity_calculator->PointSeen(x, y, time); - x += x_increment; - y += y_increment; - time += time_increment_seconds * 1000000; - } -} - -} // namespace - -typedef AuraTestBase VelocityCalculatorTest; - -// Test that the velocity returned is reasonable -TEST_F(VelocityCalculatorTest, ReturnsReasonableVelocity) { - VelocityCalculator velocity_calculator(5); - AddPoints(&velocity_calculator, 10, -10, 1, 7); - - EXPECT_GT(velocity_calculator.XVelocity(), 9.9); - EXPECT_LT(velocity_calculator.XVelocity(), 10.1); - EXPECT_GT(velocity_calculator.YVelocity(), -10.1); - EXPECT_LT(velocity_calculator.YVelocity(), -9.9); - - velocity_calculator.PointSeen(9, -11, 5500000); - velocity_calculator.PointSeen(21, -19, 6000000); - velocity_calculator.PointSeen(30, -32, 6500000); - velocity_calculator.PointSeen(38, -40, 7000000); - velocity_calculator.PointSeen(50, -51, 7500000); - - EXPECT_GT(velocity_calculator.XVelocity(), 19); - EXPECT_LT(velocity_calculator.XVelocity(), 21); - EXPECT_GT(velocity_calculator.YVelocity(), -21); - EXPECT_LT(velocity_calculator.YVelocity(), -19); - - // Significantly larger difference in position - velocity_calculator.PointSeen(70, -70, 8000000); - - EXPECT_GT(velocity_calculator.XVelocity(), 20); - EXPECT_LT(velocity_calculator.XVelocity(), 25); - EXPECT_GT(velocity_calculator.YVelocity(), -25); - EXPECT_LT(velocity_calculator.YVelocity(), -20); -} - -TEST_F(VelocityCalculatorTest, IsAccurateWithLargeTimes) { - VelocityCalculator velocity_calculator(5); - int64 start_time = 0; - velocity_calculator.PointSeen(9, -11, start_time); - velocity_calculator.PointSeen(21, -19, start_time + 8); - velocity_calculator.PointSeen(30, -32, start_time + 16); - velocity_calculator.PointSeen(38, -40, start_time + 24); - velocity_calculator.PointSeen(50, -51, start_time + 32); - - EXPECT_GT(velocity_calculator.XVelocity(), 1230000); - EXPECT_LT(velocity_calculator.XVelocity(), 1260000); - EXPECT_GT(velocity_calculator.YVelocity(), -1270000); - EXPECT_LT(velocity_calculator.YVelocity(), -1240000); - - start_time = GG_LONGLONG(1223372036800000000); - velocity_calculator.PointSeen(9, -11, start_time); - velocity_calculator.PointSeen(21, -19, start_time + 8); - velocity_calculator.PointSeen(30, -32, start_time + 16); - velocity_calculator.PointSeen(38, -40, start_time + 24); - velocity_calculator.PointSeen(50, -51, start_time + 32); - - EXPECT_GT(velocity_calculator.XVelocity(), 1230000); - EXPECT_LT(velocity_calculator.XVelocity(), 1260000); - EXPECT_GT(velocity_calculator.YVelocity(), -1270000); - EXPECT_LT(velocity_calculator.YVelocity(), -124000); -} - -// Check that the velocity returned is 0 if the velocity calculator -// doesn't have enough data -TEST_F(VelocityCalculatorTest, RequiresEnoughData) { - VelocityCalculator velocity_calculator(5); - EXPECT_EQ(velocity_calculator.XVelocity(), 0); - EXPECT_EQ(velocity_calculator.YVelocity(), 0); - - AddPoints(&velocity_calculator, 10, 10, 1, 4); - - // We've only seen 4 points, the buffer size is 5 - // Since the buffer isn't full, return 0 - EXPECT_EQ(velocity_calculator.XVelocity(), 0); - EXPECT_EQ(velocity_calculator.YVelocity(), 0); - - AddPoints(&velocity_calculator, 10, 10, 1, 1); - - EXPECT_GT(velocity_calculator.XVelocity(), 9.9); - EXPECT_GT(velocity_calculator.YVelocity(), 9.9); -} - -// Ensures ClearHistory behaves correctly -TEST_F(VelocityCalculatorTest, ClearsHistory) { - VelocityCalculator velocity_calculator(5); - AddPoints(&velocity_calculator, 10, -10, 1, 7); - - EXPECT_GT(velocity_calculator.XVelocity(), 9.9); - EXPECT_LT(velocity_calculator.XVelocity(), 10.1); - EXPECT_GT(velocity_calculator.YVelocity(), -10.1); - EXPECT_LT(velocity_calculator.YVelocity(), -9.9); - - velocity_calculator.ClearHistory(); - - EXPECT_EQ(velocity_calculator.XVelocity(), 0); - EXPECT_EQ(velocity_calculator.YVelocity(), 0); -} - -// Ensure data older than the buffer size is ignored -TEST_F(VelocityCalculatorTest, IgnoresOldData) { - VelocityCalculator velocity_calculator(5); - AddPoints(&velocity_calculator, 10, -10, 1, 7); - - EXPECT_GT(velocity_calculator.XVelocity(), 9.9); - EXPECT_LT(velocity_calculator.XVelocity(), 10.1); - EXPECT_GT(velocity_calculator.YVelocity(), -10.1); - EXPECT_LT(velocity_calculator.YVelocity(), -9.9); - - AddPoints(&velocity_calculator, 0, 0, 1, 5); - - EXPECT_EQ(velocity_calculator.XVelocity(), 0); - EXPECT_EQ(velocity_calculator.YVelocity(), 0); -} - -} // namespace test -} // namespace aura |