Index: ui/chromeos/touch_exploration_controller.cc |
diff --git a/ui/chromeos/touch_exploration_controller.cc b/ui/chromeos/touch_exploration_controller.cc |
index 8b91009ce21777f02d766b1be1f78b34714dba6d..d54b5361d80596b3edfe3f00389413fed5478ba0 100644 |
--- a/ui/chromeos/touch_exploration_controller.cc |
+++ b/ui/chromeos/touch_exploration_controller.cc |
@@ -313,31 +313,46 @@ TouchExplorationController::InSingleTapOrTouchExploreReleased( |
return ui::EVENT_REWRITE_DISCARD; |
} |
if (type == ui::ET_TOUCH_PRESSED) { |
- // If there is no touch exploration yet, we can't send a click, so discard. |
+ // If there is no touch exploration yet, we can't send a click, so discard |
+ // and wait for no fingers. |
if (!last_touch_exploration_) { |
tap_timer_.Stop(); |
+ SET_STATE(WAIT_FOR_NO_FINGERS); |
return ui::EVENT_REWRITE_DISCARD; |
} |
- // This is the second tap in a double-tap (or double tap-hold). |
- // We set the tap timer. If it fires before the user lifts their finger, |
- // one-finger passthrough begins. Otherwise, there is a touch press and |
- // release at the location of the last touch exploration. |
- SET_STATE(DOUBLE_TAP_PENDING); |
- // The old tap timer (from the initial click) is stopped if it is still |
- // going, and the new one is set. |
- tap_timer_.Stop(); |
- StartTapTimer(); |
- // This will update as the finger moves before a possible passthrough, and |
- // will determine the offset. |
- last_unused_finger_event_.reset(new ui::TouchEvent(event)); |
- return ui::EVENT_REWRITE_DISCARD; |
- } else if (type == ui::ET_TOUCH_RELEASED && !last_touch_exploration_) { |
- // If the previous press was discarded, we need to also handle its |
- // release. |
- if (current_touch_ids_.size() == 0) { |
- SET_STATE(NO_FINGERS_DOWN); |
+ if (state_ == SINGLE_TAP_RELEASED) { |
dmazzoni
2014/08/15 15:34:01
This "if/else" block is now more than half of the
evy
2014/08/15 16:14:57
Done.
|
+ // This is the second tap in a double-tap (or double tap-hold). |
+ // We set the passthrough timer. If it fires before the user lifts their |
+ // finger, one-finger passthrough begins. Otherwise, there is a touch |
+ // press and release at the location of the last touch exploration. |
+ SET_STATE(DOUBLE_TAP_PENDING); |
+ // Initial press now holds the intial double tap press - this event. |
+ initial_press_.reset(new ui::TouchEvent(event)); |
+ // The old tap timer (from the initial click) is stopped if it is still |
+ // going, and the passthrough timer is set. |
+ tap_timer_.Stop(); |
+ passthrough_timer_.Start( |
+ FROM_HERE, |
+ gesture_detector_config_.longpress_timeout, |
+ this, |
+ &TouchExplorationController::OnPassthroughTimerFired); |
+ // This will update as the finger moves before a possible passthrough, and |
+ // will determine the offset. |
+ last_unused_finger_event_.reset(new ui::TouchEvent(event)); |
+ return ui::EVENT_REWRITE_DISCARD; |
+ } else if (state_ == TOUCH_EXPLORE_RELEASED) { |
+ // This is the initial "press" (location, time, and touch id) of a single |
+ // tap click. |
+ initial_press_.reset(new ui::TouchEvent(event)); |
+ rewritten_event->reset( |
+ new ui::TouchEvent(ui::ET_TOUCH_PRESSED, |
+ last_touch_exploration_->location(), |
+ initial_press_->touch_id(), |
+ event.time_stamp())); |
+ (*rewritten_event)->set_flags(event.flags()); |
+ SET_STATE(TOUCH_RELEASE_PENDING); |
+ return ui::EVENT_REWRITE_REWRITTEN; |
} |
- return ui::EVENT_REWRITE_DISCARD; |
} else if (type == ui::ET_TOUCH_MOVED) { |
return ui::EVENT_REWRITE_DISCARD; |
} |
@@ -356,14 +371,21 @@ ui::EventRewriteStatus TouchExplorationController::InDoubleTapPending( |
// the "slop" region, jump to passthrough mode early. |
float delta = (event.location() - initial_press_->location()).Length(); |
if (delta > gesture_detector_config_.touch_slop) { |
- tap_timer_.Stop(); |
- OnTapTimerFired(); |
+ passthrough_timer_.Stop(); |
+ if (VLOG_on_) |
+ VLOG(0) << "Finger left slop and is entering passthrough"; |
+ OnPassthroughTimerFired(); |
} |
return EVENT_REWRITE_DISCARD; |
} else if (type == ui::ET_TOUCH_RELEASED || type == ui::ET_TOUCH_CANCELLED) { |
if (current_touch_ids_.size() != 0) |
return EVENT_REWRITE_DISCARD; |
+ // Now it is recognized that the user was doing a double tap to click. |
+ // The passthrough timer is stopped and a touch press and release are |
+ // dispatched. |
+ passthrough_timer_.Stop(); |
+ |
scoped_ptr<ui::TouchEvent> touch_press; |
touch_press.reset(new ui::TouchEvent(ui::ET_TOUCH_PRESSED, |
last_touch_exploration_->location(), |
@@ -667,18 +689,6 @@ void TouchExplorationController::OnTapTimerFired() { |
SET_STATE(NO_FINGERS_DOWN); |
last_touch_exploration_.reset(new TouchEvent(*initial_press_)); |
return; |
- case DOUBLE_TAP_PENDING: { |
- SET_STATE(ONE_FINGER_PASSTHROUGH); |
- passthrough_offset_ = last_unused_finger_event_->location() - |
- last_touch_exploration_->location(); |
- scoped_ptr<ui::TouchEvent> passthrough_press( |
- new ui::TouchEvent(ui::ET_TOUCH_PRESSED, |
- last_touch_exploration_->location(), |
- last_unused_finger_event_->touch_id(), |
- Now())); |
- DispatchEvent(passthrough_press.get()); |
- return; |
- } |
case SINGLE_TAP_PRESSED: |
if (passthrough_timer_.IsRunning()) |
return; |
@@ -695,6 +705,7 @@ void TouchExplorationController::OnTapTimerFired() { |
SET_STATE(WAIT_FOR_NO_FINGERS); |
break; |
default: |
+ NOTREACHED() << "tap timer fired in unrecognized state"; |
return; |
} |
EnterTouchToMouseMode(); |
@@ -705,28 +716,52 @@ void TouchExplorationController::OnTapTimerFired() { |
} |
void TouchExplorationController::OnPassthroughTimerFired() { |
- // The passthrough timer will only fire if if the user has held a finger in |
- // one of the passthrough corners for the duration of the passthrough timeout. |
- |
- // Check that initial press isn't null. Also a check that if the initial |
- // corner press was released, then it should not be in corner passthrough. |
- if (!initial_press_ || |
- touch_locations_.find(initial_press_->touch_id()) != |
- touch_locations_.end()) { |
- LOG(ERROR) << "No initial press or the initial press has been released."; |
- } |
+ switch (state_) { |
+ case SINGLE_TAP_PRESSED: |
+ case TOUCH_EXPLORATION: |
+ case GESTURE_IN_PROGRESS: { |
+ // The timer will only fire in this state if if the user has held a finger |
+ // in one of the passthrough corners for the duration of the passthrough |
+ // timeout. |
+ |
+ // Check that initial press isn't null. Also a check that if the initial |
+ // corner press was released, then it should not be in corner passthrough. |
+ if (!initial_press_ || |
+ touch_locations_.find(initial_press_->touch_id()) != |
+ touch_locations_.end()) { |
+ LOG(ERROR) |
+ << "No initial press or the initial press has been released."; |
+ } |
- gfx::Point location = |
- ToRoundedPoint(touch_locations_[initial_press_->touch_id()]); |
- int corner = FindEdgesWithinBounds(location, kSlopDistanceFromEdge); |
- if (corner != BOTTOM_LEFT_CORNER && corner != BOTTOM_RIGHT_CORNER) |
- return; |
+ gfx::Point location = |
+ ToRoundedPoint(touch_locations_[initial_press_->touch_id()]); |
+ int corner = FindEdgesWithinBounds(location, kSlopDistanceFromEdge); |
+ if (corner != BOTTOM_LEFT_CORNER && corner != BOTTOM_RIGHT_CORNER) |
+ return; |
+ SET_STATE(CORNER_PASSTHROUGH); |
+ break; |
+ } |
+ case DOUBLE_TAP_PENDING: { |
+ // Enter one finger passthrough mode. |
+ SET_STATE(ONE_FINGER_PASSTHROUGH); |
+ passthrough_offset_ = last_unused_finger_event_->location() - |
+ last_touch_exploration_->location(); |
+ scoped_ptr<ui::TouchEvent> passthrough_press( |
+ new ui::TouchEvent(ui::ET_TOUCH_PRESSED, |
+ last_touch_exploration_->location(), |
+ last_unused_finger_event_->touch_id(), |
+ Now())); |
+ DispatchEvent(passthrough_press.get()); |
+ break; |
+ } |
+ default: |
+ NOTREACHED() << "passthrough timer fired in unrecognized state"; |
+ return; |
+ } |
if (sound_timer_.IsRunning()) |
sound_timer_.Stop(); |
delegate_->PlayPassthroughEarcon(); |
- SET_STATE(CORNER_PASSTHROUGH); |
- return; |
} |
void TouchExplorationController::DispatchEvent(ui::Event* event) { |