summaryrefslogtreecommitdiffstats
path: root/ui
diff options
context:
space:
mode:
authorsadrul@chromium.org <sadrul@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2012-04-05 19:43:37 +0000
committersadrul@chromium.org <sadrul@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2012-04-05 19:43:37 +0000
commit435b212e562f37e94926df26d564efadaca81f78 (patch)
tree8f8684e0b20d50f45ff7cf40100e3ebd24eaca17 /ui
parent77a3bbbbc746fdad0ba0206e7661e4fed8a4090e (diff)
downloadchromium_src-435b212e562f37e94926df26d564efadaca81f78.zip
chromium_src-435b212e562f37e94926df26d564efadaca81f78.tar.gz
chromium_src-435b212e562f37e94926df26d564efadaca81f78.tar.bz2
Touches outside the Root Window contribute to system level gestures.
A new event filter has been added, SystemGestureEventFilter, which will handle system level gesture events. It currently consumes system level gesture events, but does nothing with them. Touches outside the root window are targeted at the root window, and touches targeted at the root window are consumed by the SystemGestureEventFilter. BUG=119498 TEST=SystemGestureEventFilterTest.*, GestureRecognizerTest.GestureEventOutsideRootWindowTap Review URL: https://chromiumcodereview.appspot.com/9837015 Patch from Tim Dresser <tdresser@chromium.org>. git-svn-id: svn://svn.chromium.org/chrome/trunk/src@130990 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'ui')
-rw-r--r--ui/aura/gestures/gesture_recognizer_unittest.cc51
-rw-r--r--ui/aura/gestures/gesture_sequence.h1
-rw-r--r--ui/aura/root_window.cc43
3 files changed, 74 insertions, 21 deletions
diff --git a/ui/aura/gestures/gesture_recognizer_unittest.cc b/ui/aura/gestures/gesture_recognizer_unittest.cc
index 350806e..34e05ff 100644
--- a/ui/aura/gestures/gesture_recognizer_unittest.cc
+++ b/ui/aura/gestures/gesture_recognizer_unittest.cc
@@ -274,7 +274,7 @@ class TimerTestGestureSequence : public GestureSequence {
};
class TestGestureRecognizer : public GestureRecognizerAura {
- public:
+ public:
TestGestureRecognizer()
: GestureRecognizerAura() {
}
@@ -282,6 +282,13 @@ class TestGestureRecognizer : public GestureRecognizerAura {
GestureSequence* GetGestureSequenceForTesting(Window* window) {
return GetGestureSequenceForWindow(window);
}
+};
+
+class TimerTestGestureRecognizer : public TestGestureRecognizer {
+ public:
+ TimerTestGestureRecognizer()
+ : TestGestureRecognizer() {
+ }
virtual GestureSequence* CreateSequence(RootWindow* root_window) OVERRIDE {
return new TimerTestGestureSequence(root_window);
@@ -563,8 +570,8 @@ TEST_F(GestureRecognizerTest, GestureEventLongPress) {
delegate->Reset();
- TestGestureRecognizer* gesture_recognizer =
- new TestGestureRecognizer();
+ TimerTestGestureRecognizer* gesture_recognizer =
+ new TimerTestGestureRecognizer();
TimerTestGestureSequence* gesture_sequence =
static_cast<TimerTestGestureSequence*>(
gesture_recognizer->GetGestureSequenceForTesting(window.get()));
@@ -604,8 +611,8 @@ TEST_F(GestureRecognizerTest, GestureEventLongPressCancelledByScroll) {
delegate->Reset();
- TestGestureRecognizer* gesture_recognizer =
- new TestGestureRecognizer();
+ TimerTestGestureRecognizer* gesture_recognizer =
+ new TimerTestGestureRecognizer();
TimerTestGestureSequence* gesture_sequence =
static_cast<TimerTestGestureSequence*>(
gesture_recognizer->GetGestureSequenceForTesting(window.get()));
@@ -645,8 +652,8 @@ TEST_F(GestureRecognizerTest, GestureEventLongPressCancelledByPinch) {
scoped_ptr<aura::Window> window(CreateTestWindowWithDelegate(
delegate.get(), -1234, bounds, NULL));
- TestGestureRecognizer* gesture_recognizer =
- new TestGestureRecognizer();
+ TimerTestGestureRecognizer* gesture_recognizer =
+ new TimerTestGestureRecognizer();
TimerTestGestureSequence* gesture_sequence =
static_cast<TimerTestGestureSequence*>(
gesture_recognizer->GetGestureSequenceForTesting(window.get()));
@@ -1419,6 +1426,36 @@ TEST_F(GestureRecognizerTest, GestureEventTouchLockSelectsCorrectWindow) {
EXPECT_EQ(windows[2], target);
}
+// Check that touch events outside the root window are still handled
+// by the root window's gesture sequence.
+TEST_F(GestureRecognizerTest, GestureEventOutsideRootWindowTap) {
+ TestGestureRecognizer* gesture_recognizer =
+ new TestGestureRecognizer();
+ root_window()->SetGestureRecognizerForTesting(gesture_recognizer);
+
+ scoped_ptr<aura::Window> window(CreateTestWindowWithBounds(
+ gfx::Rect(-100, -100, 2000, 2000), NULL));
+
+ GestureSequence* window_gesture_sequence =
+ gesture_recognizer->GetGestureSequenceForTesting(window.get());
+
+ GestureSequence* root_window_gesture_sequence =
+ gesture_recognizer->GetGestureSequenceForTesting(root_window());
+
+ gfx::Point pos1(-10, -10);
+ TouchEvent press1(ui::ET_TOUCH_PRESSED, pos1, 0);
+ root_window()->DispatchTouchEvent(&press1);
+
+ gfx::Point pos2(1000, 1000);
+ TouchEvent press2(ui::ET_TOUCH_PRESSED, pos2, 1);
+ root_window()->DispatchTouchEvent(&press2);
+
+ // As these presses were outside the root window, they should be
+ // associated with the root window.
+ EXPECT_EQ(0, window_gesture_sequence->point_count());
+ EXPECT_EQ(2, root_window_gesture_sequence->point_count());
+}
+
TEST_F(GestureRecognizerTest, NoTapWithPreventDefaultedRelease) {
scoped_ptr<QueueTouchEventDelegate> delegate(
new QueueTouchEventDelegate(root_window()));
diff --git a/ui/aura/gestures/gesture_sequence.h b/ui/aura/gestures/gesture_sequence.h
index db82174..4f71934 100644
--- a/ui/aura/gestures/gesture_sequence.h
+++ b/ui/aura/gestures/gesture_sequence.h
@@ -44,6 +44,7 @@ class AURA_EXPORT GestureSequence {
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;
diff --git a/ui/aura/root_window.cc b/ui/aura/root_window.cc
index 188c77c..1fd6a4a 100644
--- a/ui/aura/root_window.cc
+++ b/ui/aura/root_window.cc
@@ -266,21 +266,30 @@ bool RootWindow::DispatchTouchEvent(TouchEvent* event) {
event->UpdateForRootTransform(layer()->transform());
bool handled = false;
Window* target = capture_window_;
- if (!target)
- target = gesture_recognizer_->GetTargetForTouchEvent(event);
- if (!target)
- target = GetEventHandlerForPoint(event->location());
- if (!target)
- return false;
ui::TouchStatus status = ui::TOUCH_STATUS_UNKNOWN;
- TouchEvent translated_event(*event, this, target);
- status = ProcessTouchEvent(target, &translated_event);
- handled = status != ui::TOUCH_STATUS_UNKNOWN;
- if (status == ui::TOUCH_STATUS_QUEUED ||
- status == ui::TOUCH_STATUS_QUEUED_END)
- gesture_recognizer_->QueueTouchEventForGesture(target, *event);
+ if (!target)
+ target = gesture_recognizer_->GetTargetForTouchEvent(event);
+
+ if (!target && !bounds().Contains(event->location())) {
+ // If the touch is outside the root window, set its target to the
+ // root window.
+ target = this;
+ } else {
+ if (!target)
+ target = GetEventHandlerForPoint(event->location());
+ if (!target)
+ return false;
+
+ TouchEvent translated_event(*event, this, target);
+ status = ProcessTouchEvent(target, &translated_event);
+ handled = status != ui::TOUCH_STATUS_UNKNOWN;
+
+ if (status == ui::TOUCH_STATUS_QUEUED ||
+ status == ui::TOUCH_STATUS_QUEUED_END)
+ gesture_recognizer_->QueueTouchEventForGesture(target, *event);
+ }
// Get the list of GestureEvents from GestureRecognizer.
scoped_ptr<GestureRecognizer::Gestures> gestures;
@@ -560,6 +569,8 @@ bool RootWindow::ProcessMouseEvent(Window* target, MouseEvent* event) {
return true;
}
+ if (!target->delegate())
+ return false;
return target->delegate()->OnMouseEvent(event);
}
@@ -613,7 +624,10 @@ ui::GestureStatus RootWindow::ProcessGestureEvent(Window* target,
return ui::GESTURE_STATUS_UNKNOWN;
EventFilters filters;
- GetEventFiltersToNotify(target->parent(), &filters);
+ if (target == this)
+ GetEventFiltersToNotify(target, &filters);
+ else
+ GetEventFiltersToNotify(target->parent(), &filters);
ui::GestureStatus status = ui::GESTURE_STATUS_UNKNOWN;
for (EventFilters::const_reverse_iterator it = filters.rbegin(),
rend = filters.rend();
@@ -623,7 +637,8 @@ ui::GestureStatus RootWindow::ProcessGestureEvent(Window* target,
return status;
}
- status = target->delegate()->OnGestureEvent(event);
+ if (target->delegate())
+ status = target->delegate()->OnGestureEvent(event);
if (status == ui::GESTURE_STATUS_UNKNOWN) {
// The gesture was unprocessed. Generate corresponding mouse events here
// (e.g. tap to click).