| Index: ui/events/gestures/motion_event_impl.cc
|
| diff --git a/ui/events/gestures/motion_event_impl.cc b/ui/events/gestures/motion_event_impl.cc
|
| index fd6fa6a2b758f8dc45ab6001ac9023bb3e62b1e5..505ac6cfc472f2a70669f543600937e4645a2282 100644
|
| --- a/ui/events/gestures/motion_event_impl.cc
|
| +++ b/ui/events/gestures/motion_event_impl.cc
|
| @@ -2,83 +2,77 @@
|
| // Use of this source code is governed by a BSD-style license that can be
|
| // found in the LICENSE file.
|
|
|
| -// MSVC++ requires this to be set before any other includes to get M_PI.
|
| -#define _USE_MATH_DEFINES
|
| -
|
| #include "ui/events/gestures/motion_event_impl.h"
|
|
|
| -#include <cmath>
|
| -
|
| #include "base/logging.h"
|
| -#include "ui/events/gestures/gesture_configuration.h"
|
| +#include "ui/events/gesture_detection/gesture_configuration.h"
|
|
|
| namespace ui {
|
| +namespace {
|
| +
|
| +PointerProperties GetPointerPropertiesFromTouchEvent(const TouchEvent& touch) {
|
| + PointerProperties pointer_properties;
|
| + pointer_properties.x = touch.x();
|
| + pointer_properties.y = touch.y();
|
| + pointer_properties.raw_x = touch.root_location_f().x();
|
| + pointer_properties.raw_y = touch.root_location_f().y();
|
| + pointer_properties.id = touch.touch_id();
|
| + pointer_properties.pressure = touch.force();
|
| + pointer_properties.source_device_id = touch.source_device_id();
|
| +
|
| + pointer_properties.SetAxesAndOrientation(touch.radius_x(), touch.radius_y(),
|
| + touch.rotation_angle());
|
| + if (!pointer_properties.touch_major) {
|
| + pointer_properties.touch_major =
|
| + 2.f * GestureConfiguration::GetInstance()->default_radius();
|
| + pointer_properties.touch_minor =
|
| + 2.f * GestureConfiguration::GetInstance()->default_radius();
|
| + pointer_properties.orientation = 0;
|
| + }
|
|
|
| -MotionEventImpl::MotionEventImpl()
|
| - : pointer_count_(0), cached_action_index_(-1) {
|
| + // TODO(jdduke): Plumb tool type from the platform, crbug.com/404128.
|
| + pointer_properties.tool_type = MotionEvent::TOOL_TYPE_UNKNOWN;
|
| +
|
| + return pointer_properties;
|
| }
|
|
|
| -MotionEventImpl::MotionEventImpl(
|
| - size_t pointer_count,
|
| - const base::TimeTicks& last_touch_time,
|
| - Action cached_action,
|
| - int cached_action_index,
|
| - int flags,
|
| - const PointData (&active_touches)[MotionEvent::MAX_TOUCH_POINT_COUNT])
|
| - : pointer_count_(pointer_count),
|
| - last_touch_time_(last_touch_time),
|
| - cached_action_(cached_action),
|
| - cached_action_index_(cached_action_index),
|
| - flags_(flags) {
|
| - DCHECK(pointer_count_);
|
| - for (size_t i = 0; i < pointer_count; ++i)
|
| - active_touches_[i] = active_touches[i];
|
| +} // namespace
|
| +
|
| +MotionEventImpl::MotionEventImpl() {
|
| + set_action_index(-1);
|
| }
|
|
|
| -MotionEventImpl::~MotionEventImpl() {}
|
| +MotionEventImpl::~MotionEventImpl() {
|
| +}
|
|
|
| -MotionEventImpl::PointData MotionEventImpl::GetPointDataFromTouchEvent(
|
| - const TouchEvent& touch) {
|
| - PointData point_data;
|
| - point_data.x = touch.x();
|
| - point_data.y = touch.y();
|
| - point_data.raw_x = touch.root_location_f().x();
|
| - point_data.raw_y = touch.root_location_f().y();
|
| - point_data.touch_id = touch.touch_id();
|
| - point_data.pressure = touch.force();
|
| - point_data.source_device_id = touch.source_device_id();
|
| +bool MotionEventImpl::OnTouch(const TouchEvent& touch) {
|
| + int index = FindPointerIndexOfId(touch.touch_id());
|
| + bool pointer_id_is_active = index != -1;
|
|
|
| - float radius_x = touch.radius_x();
|
| - float radius_y = touch.radius_y();
|
| - float rotation_angle_rad = touch.rotation_angle() * M_PI / 180.f;
|
| - DCHECK_GE(radius_x, 0) << "Unexpected x-radius < 0";
|
| - DCHECK_GE(radius_y, 0) << "Unexpected y-radius < 0";
|
| - DCHECK(0 <= rotation_angle_rad && rotation_angle_rad <= M_PI_2)
|
| - << "Unexpected touch rotation angle";
|
| + if (touch.type() == ET_TOUCH_PRESSED && pointer_id_is_active) {
|
| + // TODO(tdresser): This should return false (or NOTREACHED()), and
|
| + // ignore the touch; however, there is at least one case where we
|
| + // need to allow a touch press from a currently used touch id. See
|
| + // crbug.com/446852 for details.
|
|
|
| - if (radius_x > radius_y) {
|
| - // The case radius_x == radius_y is omitted from here on purpose: for
|
| - // circles, we want to pass the angle (which could be any value in such
|
| - // cases but always seem to be set to zero) unchanged.
|
| - point_data.touch_major = 2.f * radius_x;
|
| - point_data.touch_minor = 2.f * radius_y;
|
| - point_data.orientation = rotation_angle_rad - M_PI_2;
|
| - } else {
|
| - point_data.touch_major = 2.f * radius_y;
|
| - point_data.touch_minor = 2.f * radius_x;
|
| - point_data.orientation = rotation_angle_rad;
|
| + // Cancel the existing touch, before handling the touch press.
|
| + TouchEvent cancel(ET_TOUCH_CANCELLED, touch.location(), touch.touch_id(),
|
| + touch.time_stamp());
|
| + OnTouch(cancel);
|
| + CleanupRemovedTouchPoints(cancel);
|
| + DCHECK_EQ(-1, FindPointerIndexOfId(touch.touch_id()));
|
| + } else if (touch.type() != ET_TOUCH_PRESSED && !pointer_id_is_active) {
|
| + // We could have an active touch stream transfered to us, resulting in touch
|
| + // move or touch up events without associated touch down events. Ignore
|
| + // them.
|
| + return false;
|
| }
|
|
|
| - if (!point_data.touch_major) {
|
| - point_data.touch_major = 2.f * GestureConfiguration::default_radius();
|
| - point_data.touch_minor = 2.f * GestureConfiguration::default_radius();
|
| - point_data.orientation = 0;
|
| + if (touch.type() == ET_TOUCH_MOVED && touch.x() == GetX(index) &&
|
| + touch.y() == GetY(index)) {
|
| + return false;
|
| }
|
|
|
| - return point_data;
|
| -}
|
| -
|
| -void MotionEventImpl::OnTouch(const TouchEvent& touch) {
|
| switch (touch.type()) {
|
| case ET_TOUCH_PRESSED:
|
| AddTouch(touch);
|
| @@ -95,107 +89,14 @@ void MotionEventImpl::OnTouch(const TouchEvent& touch) {
|
| break;
|
| default:
|
| NOTREACHED();
|
| - break;
|
| + return false;
|
| }
|
|
|
| UpdateCachedAction(touch);
|
| - flags_ = touch.flags();
|
| - last_touch_time_ = touch.time_stamp() + base::TimeTicks();
|
| -}
|
| -
|
| -int MotionEventImpl::GetId() const {
|
| - return GetPointerId(0);
|
| -}
|
| -
|
| -MotionEvent::Action MotionEventImpl::GetAction() const {
|
| - return cached_action_;
|
| -}
|
| -
|
| -int MotionEventImpl::GetActionIndex() const {
|
| - DCHECK(cached_action_ == ACTION_POINTER_DOWN ||
|
| - cached_action_ == ACTION_POINTER_UP);
|
| - DCHECK_GE(cached_action_index_, 0);
|
| - DCHECK_LT(cached_action_index_, static_cast<int>(pointer_count_));
|
| - return cached_action_index_;
|
| -}
|
| -
|
| -size_t MotionEventImpl::GetPointerCount() const { return pointer_count_; }
|
| -
|
| -int MotionEventImpl::GetPointerId(size_t pointer_index) const {
|
| - DCHECK_LT(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].touch_id;
|
| -}
|
| -
|
| -float MotionEventImpl::GetX(size_t pointer_index) const {
|
| - DCHECK_LT(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].x;
|
| -}
|
| -
|
| -float MotionEventImpl::GetY(size_t pointer_index) const {
|
| - DCHECK_LT(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].y;
|
| -}
|
| -
|
| -float MotionEventImpl::GetRawX(size_t pointer_index) const {
|
| - DCHECK_LT(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].raw_x;
|
| -}
|
| -
|
| -float MotionEventImpl::GetRawY(size_t pointer_index) const {
|
| - DCHECK_LT(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].raw_y;
|
| -}
|
| -
|
| -float MotionEventImpl::GetTouchMajor(size_t pointer_index) const {
|
| - DCHECK_LT(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].touch_major;
|
| -}
|
| -
|
| -float MotionEventImpl::GetTouchMinor(size_t pointer_index) const {
|
| - DCHECK_LE(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].touch_minor;
|
| -}
|
| -
|
| -float MotionEventImpl::GetOrientation(size_t pointer_index) const {
|
| - DCHECK_LE(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].orientation;
|
| -}
|
| -
|
| -float MotionEventImpl::GetPressure(size_t pointer_index) const {
|
| - DCHECK_LT(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].pressure;
|
| -}
|
| -
|
| -MotionEvent::ToolType MotionEventImpl::GetToolType(size_t pointer_index) const {
|
| - // TODO(jdduke): Plumb tool type from the platform, crbug.com/404128.
|
| - DCHECK_LT(pointer_index, pointer_count_);
|
| - return MotionEvent::TOOL_TYPE_UNKNOWN;
|
| -}
|
| -
|
| -int MotionEventImpl::GetButtonState() const {
|
| - NOTIMPLEMENTED();
|
| - return 0;
|
| -}
|
| -
|
| -int MotionEventImpl::GetFlags() const {
|
| - return flags_;
|
| -}
|
| -
|
| -base::TimeTicks MotionEventImpl::GetEventTime() const {
|
| - return last_touch_time_;
|
| -}
|
| -
|
| -scoped_ptr<MotionEvent> MotionEventImpl::Clone() const {
|
| - return scoped_ptr<MotionEvent>(new MotionEventImpl(pointer_count_,
|
| - last_touch_time_,
|
| - cached_action_,
|
| - cached_action_index_,
|
| - flags_,
|
| - active_touches_));
|
| -}
|
| -scoped_ptr<MotionEvent> MotionEventImpl::Cancel() const {
|
| - return scoped_ptr<MotionEvent>(new MotionEventImpl(
|
| - pointer_count_, last_touch_time_, ACTION_CANCEL, -1, 0, active_touches_));
|
| + set_unique_event_id(touch.unique_event_id());
|
| + set_flags(touch.flags());
|
| + set_event_time(touch.time_stamp() + base::TimeTicks());
|
| + return true;
|
| }
|
|
|
| void MotionEventImpl::CleanupRemovedTouchPoints(const TouchEvent& event) {
|
| @@ -204,70 +105,54 @@ void MotionEventImpl::CleanupRemovedTouchPoints(const TouchEvent& event) {
|
| return;
|
| }
|
|
|
| - int index_to_delete = static_cast<int>(GetIndexFromId(event.touch_id()));
|
| - pointer_count_--;
|
| - active_touches_[index_to_delete] = active_touches_[pointer_count_];
|
| -}
|
| -
|
| -MotionEventImpl::PointData::PointData()
|
| - : x(0),
|
| - y(0),
|
| - raw_x(0),
|
| - raw_y(0),
|
| - touch_id(0),
|
| - pressure(0),
|
| - source_device_id(0),
|
| - touch_major(0),
|
| - touch_minor(0),
|
| - orientation(0) {
|
| + DCHECK(GetPointerCount());
|
| + int index_to_delete = GetIndexFromId(event.touch_id());
|
| + set_action_index(0);
|
| + pointer(index_to_delete) = pointer(GetPointerCount() - 1);
|
| + PopPointer();
|
| }
|
|
|
| int MotionEventImpl::GetSourceDeviceId(size_t pointer_index) const {
|
| - DCHECK_LT(pointer_index, pointer_count_);
|
| - return active_touches_[pointer_index].source_device_id;
|
| + DCHECK_LT(pointer_index, GetPointerCount());
|
| + return pointer(pointer_index).source_device_id;
|
| }
|
|
|
| void MotionEventImpl::AddTouch(const TouchEvent& touch) {
|
| - if (pointer_count_ == MotionEvent::MAX_TOUCH_POINT_COUNT)
|
| + if (GetPointerCount() == MotionEvent::MAX_TOUCH_POINT_COUNT)
|
| return;
|
|
|
| - active_touches_[pointer_count_] = GetPointDataFromTouchEvent(touch);
|
| - pointer_count_++;
|
| + PushPointer(GetPointerPropertiesFromTouchEvent(touch));
|
| }
|
|
|
| -
|
| void MotionEventImpl::UpdateTouch(const TouchEvent& touch) {
|
| - active_touches_[GetIndexFromId(touch.touch_id())] =
|
| - GetPointDataFromTouchEvent(touch);
|
| + pointer(GetIndexFromId(touch.touch_id())) =
|
| + GetPointerPropertiesFromTouchEvent(touch);
|
| }
|
|
|
| void MotionEventImpl::UpdateCachedAction(const TouchEvent& touch) {
|
| - DCHECK(pointer_count_);
|
| + DCHECK(GetPointerCount());
|
| switch (touch.type()) {
|
| case ET_TOUCH_PRESSED:
|
| - if (pointer_count_ == 1) {
|
| - cached_action_ = ACTION_DOWN;
|
| + if (GetPointerCount() == 1) {
|
| + set_action(ACTION_DOWN);
|
| } else {
|
| - cached_action_ = ACTION_POINTER_DOWN;
|
| - cached_action_index_ =
|
| - static_cast<int>(GetIndexFromId(touch.touch_id()));
|
| + set_action(ACTION_POINTER_DOWN);
|
| + set_action_index(GetIndexFromId(touch.touch_id()));
|
| }
|
| break;
|
| case ET_TOUCH_RELEASED:
|
| - if (pointer_count_ == 1) {
|
| - cached_action_ = ACTION_UP;
|
| + if (GetPointerCount() == 1) {
|
| + set_action(ACTION_UP);
|
| } else {
|
| - cached_action_ = ACTION_POINTER_UP;
|
| - cached_action_index_ =
|
| - static_cast<int>(GetIndexFromId(touch.touch_id()));
|
| - DCHECK_LT(cached_action_index_, static_cast<int>(pointer_count_));
|
| + set_action(ACTION_POINTER_UP);
|
| + set_action_index(GetIndexFromId(touch.touch_id()));
|
| }
|
| break;
|
| case ET_TOUCH_CANCELLED:
|
| - cached_action_ = ACTION_CANCEL;
|
| + set_action(ACTION_CANCEL);
|
| break;
|
| case ET_TOUCH_MOVED:
|
| - cached_action_ = ACTION_MOVE;
|
| + set_action(ACTION_MOVE);
|
| break;
|
| default:
|
| NOTREACHED();
|
| @@ -275,13 +160,11 @@ void MotionEventImpl::UpdateCachedAction(const TouchEvent& touch) {
|
| }
|
| }
|
|
|
| -size_t MotionEventImpl::GetIndexFromId(int id) const {
|
| - for (size_t i = 0; i < pointer_count_; ++i) {
|
| - if (active_touches_[i].touch_id == id)
|
| - return i;
|
| - }
|
| - NOTREACHED();
|
| - return 0;
|
| +int MotionEventImpl::GetIndexFromId(int id) const {
|
| + int index = FindPointerIndexOfId(id);
|
| + DCHECK_GE(index, 0);
|
| + DCHECK_LT(index, static_cast<int>(GetPointerCount()));
|
| + return index;
|
| }
|
|
|
| } // namespace ui
|
|
|