| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "ui/views/controls/menu/menu_controller.h" | 5 #include "ui/views/controls/menu/menu_controller.h" |
| 6 | 6 |
| 7 #include "base/callback.h" | 7 #include "base/callback.h" |
| 8 #include "base/logging.h" | 8 #include "base/logging.h" |
| 9 #include "base/macros.h" | 9 #include "base/macros.h" |
| 10 #include "base/message_loop/message_loop.h" | 10 #include "base/message_loop/message_loop.h" |
| (...skipping 136 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 147 } | 147 } |
| 148 } | 148 } |
| 149 | 149 |
| 150 int outstanding_touches() const { return outstanding_touches_; } | 150 int outstanding_touches() const { return outstanding_touches_; } |
| 151 | 151 |
| 152 private: | 152 private: |
| 153 int outstanding_touches_; | 153 int outstanding_touches_; |
| 154 DISALLOW_COPY_AND_ASSIGN(TestEventHandler); | 154 DISALLOW_COPY_AND_ASSIGN(TestEventHandler); |
| 155 }; | 155 }; |
| 156 | 156 |
| 157 // A test widget that counts gesture events. |
| 158 class GestureTestWidget : public Widget { |
| 159 public: |
| 160 GestureTestWidget() : gesture_count_(0) {} |
| 161 |
| 162 void OnGestureEvent(ui::GestureEvent* event) override { gesture_count_++; } |
| 163 |
| 164 int gesture_count() const { return gesture_count_; } |
| 165 |
| 166 private: |
| 167 int gesture_count_; |
| 168 DISALLOW_COPY_AND_ASSIGN(GestureTestWidget); |
| 169 }; |
| 170 |
| 157 #if defined(USE_AURA) | 171 #if defined(USE_AURA) |
| 158 // A DragDropClient which does not trigger a nested run loop. Instead a | 172 // A DragDropClient which does not trigger a nested run loop. Instead a |
| 159 // callback is triggered during StartDragAndDrop in order to allow testing. | 173 // callback is triggered during StartDragAndDrop in order to allow testing. |
| 160 class TestDragDropClient : public aura::client::DragDropClient { | 174 class TestDragDropClient : public aura::client::DragDropClient { |
| 161 public: | 175 public: |
| 162 explicit TestDragDropClient(const base::Closure& callback) | 176 explicit TestDragDropClient(const base::Closure& callback) |
| 163 : start_drag_and_drop_callback_(callback), drag_in_progress_(false) {} | 177 : start_drag_and_drop_callback_(callback), drag_in_progress_(false) {} |
| 164 ~TestDragDropClient() override {} | 178 ~TestDragDropClient() override {} |
| 165 | 179 |
| 166 // aura::client::DragDropClient: | 180 // aura::client::DragDropClient: |
| (...skipping 289 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 456 | 470 |
| 457 // Causes the |menu_controller_| to begin dragging. Use TestDragDropClient to | 471 // Causes the |menu_controller_| to begin dragging. Use TestDragDropClient to |
| 458 // avoid nesting message loops. | 472 // avoid nesting message loops. |
| 459 void StartDrag() { | 473 void StartDrag() { |
| 460 const gfx::Point location; | 474 const gfx::Point location; |
| 461 menu_controller_->state_.item = menu_item()->GetSubmenu()->GetMenuItemAt(0); | 475 menu_controller_->state_.item = menu_item()->GetSubmenu()->GetMenuItemAt(0); |
| 462 menu_controller_->StartDrag( | 476 menu_controller_->StartDrag( |
| 463 menu_item()->GetSubmenu()->GetMenuItemAt(0)->CreateSubmenu(), location); | 477 menu_item()->GetSubmenu()->GetMenuItemAt(0)->CreateSubmenu(), location); |
| 464 } | 478 } |
| 465 | 479 |
| 466 Widget* owner() { return owner_.get(); } | 480 GestureTestWidget* owner() { return owner_.get(); } |
| 467 ui::test::EventGenerator* event_generator() { return event_generator_.get(); } | 481 ui::test::EventGenerator* event_generator() { return event_generator_.get(); } |
| 468 TestMenuItemViewShown* menu_item() { return menu_item_.get(); } | 482 TestMenuItemViewShown* menu_item() { return menu_item_.get(); } |
| 469 TestMenuDelegate* menu_delegate() { return menu_delegate_.get(); } | 483 TestMenuDelegate* menu_delegate() { return menu_delegate_.get(); } |
| 470 TestMenuControllerDelegate* menu_controller_delegate() { | 484 TestMenuControllerDelegate* menu_controller_delegate() { |
| 471 return menu_controller_delegate_.get(); | 485 return menu_controller_delegate_.get(); |
| 472 } | 486 } |
| 473 MenuController* menu_controller() { return menu_controller_; } | 487 MenuController* menu_controller() { return menu_controller_; } |
| 474 const MenuItemView* pending_state_item() const { | 488 const MenuItemView* pending_state_item() const { |
| 475 return menu_controller_->pending_state_.item; | 489 return menu_controller_->pending_state_.item; |
| 476 } | 490 } |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 513 | 527 |
| 514 if (!owner_->IsClosed()) | 528 if (!owner_->IsClosed()) |
| 515 owner_->RemoveObserver(menu_controller_); | 529 owner_->RemoveObserver(menu_controller_); |
| 516 | 530 |
| 517 menu_controller_->showing_ = false; | 531 menu_controller_->showing_ = false; |
| 518 menu_controller_->owner_ = nullptr; | 532 menu_controller_->owner_ = nullptr; |
| 519 delete menu_controller_; | 533 delete menu_controller_; |
| 520 menu_controller_ = nullptr; | 534 menu_controller_ = nullptr; |
| 521 } | 535 } |
| 522 | 536 |
| 537 int CountOwnerOnGestureEvent() { return owner_->gesture_count(); } |
| 538 |
| 523 private: | 539 private: |
| 524 void Init() { | 540 void Init() { |
| 525 owner_.reset(new Widget); | 541 owner_ = base::MakeUnique<GestureTestWidget>(); |
| 526 Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP); | 542 Widget::InitParams params = CreateParams(Widget::InitParams::TYPE_POPUP); |
| 527 params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; | 543 params.ownership = Widget::InitParams::WIDGET_OWNS_NATIVE_WIDGET; |
| 528 owner_->Init(params); | 544 owner_->Init(params); |
| 529 event_generator_.reset( | 545 event_generator_.reset( |
| 530 new ui::test::EventGenerator(owner_->GetNativeWindow())); | 546 new ui::test::EventGenerator(owner_->GetNativeWindow())); |
| 531 owner_->Show(); | 547 owner_->Show(); |
| 532 | 548 |
| 533 SetupMenuItem(); | 549 SetupMenuItem(); |
| 534 SetupMenuController(); | 550 SetupMenuController(); |
| 535 } | 551 } |
| (...skipping 14 matching lines...) Expand all Loading... |
| 550 menu_controller_->owner_ = owner_.get(); | 566 menu_controller_->owner_ = owner_.get(); |
| 551 menu_controller_->showing_ = true; | 567 menu_controller_->showing_ = true; |
| 552 menu_controller_->SetSelection( | 568 menu_controller_->SetSelection( |
| 553 menu_item_.get(), MenuController::SELECTION_UPDATE_IMMEDIATELY); | 569 menu_item_.get(), MenuController::SELECTION_UPDATE_IMMEDIATELY); |
| 554 menu_item_->SetController(menu_controller_); | 570 menu_item_->SetController(menu_controller_); |
| 555 } | 571 } |
| 556 | 572 |
| 557 // Not owned. | 573 // Not owned. |
| 558 DestructingTestViewsDelegate* test_views_delegate_; | 574 DestructingTestViewsDelegate* test_views_delegate_; |
| 559 | 575 |
| 560 std::unique_ptr<Widget> owner_; | 576 std::unique_ptr<GestureTestWidget> owner_; |
| 561 std::unique_ptr<ui::test::EventGenerator> event_generator_; | 577 std::unique_ptr<ui::test::EventGenerator> event_generator_; |
| 562 std::unique_ptr<TestMenuItemViewShown> menu_item_; | 578 std::unique_ptr<TestMenuItemViewShown> menu_item_; |
| 563 std::unique_ptr<TestMenuControllerDelegate> menu_controller_delegate_; | 579 std::unique_ptr<TestMenuControllerDelegate> menu_controller_delegate_; |
| 564 std::unique_ptr<TestMenuDelegate> menu_delegate_; | 580 std::unique_ptr<TestMenuDelegate> menu_delegate_; |
| 565 MenuController* menu_controller_; | 581 MenuController* menu_controller_; |
| 566 | 582 |
| 567 DISALLOW_COPY_AND_ASSIGN(MenuControllerTest); | 583 DISALLOW_COPY_AND_ASSIGN(MenuControllerTest); |
| 568 }; | 584 }; |
| 569 | 585 |
| 570 #if defined(OS_LINUX) && defined(USE_X11) | 586 #if defined(OS_LINUX) && defined(USE_X11) |
| (...skipping 533 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1104 // Nested run | 1120 // Nested run |
| 1105 controller->AddNestedDelegate(nested_delegate.get()); | 1121 controller->AddNestedDelegate(nested_delegate.get()); |
| 1106 controller->Run(owner(), nullptr, menu_item(), gfx::Rect(), | 1122 controller->Run(owner(), nullptr, menu_item(), gfx::Rect(), |
| 1107 MENU_ANCHOR_TOPLEFT, false, false); | 1123 MENU_ANCHOR_TOPLEFT, false, false); |
| 1108 | 1124 |
| 1109 controller->CancelAll(); | 1125 controller->CancelAll(); |
| 1110 EXPECT_EQ(1, delegate->on_menu_closed_called()); | 1126 EXPECT_EQ(1, delegate->on_menu_closed_called()); |
| 1111 EXPECT_EQ(1, nested_delegate->on_menu_closed_called()); | 1127 EXPECT_EQ(1, nested_delegate->on_menu_closed_called()); |
| 1112 } | 1128 } |
| 1113 | 1129 |
| 1130 #if !defined(OS_MACOSX) |
| 1131 TEST_F(MenuControllerTest, PreserveGestureForOwner) { |
| 1132 MenuController* controller = menu_controller(); |
| 1133 MenuItemView* item = menu_item(); |
| 1134 controller->Run(owner(), nullptr, item, gfx::Rect(), |
| 1135 MENU_ANCHOR_FIXED_BOTTOMCENTER, false, false); |
| 1136 SubmenuView* sub_menu = item->GetSubmenu(); |
| 1137 sub_menu->ShowAt(owner(), gfx::Rect(0, 0, 100, 100), true); |
| 1138 |
| 1139 gfx::Point location(sub_menu->bounds().bottom_left().x(), |
| 1140 sub_menu->bounds().bottom_left().y() + 10); |
| 1141 ui::GestureEvent event(location.x(), location.y(), 0, ui::EventTimeForNow(), |
| 1142 ui::GestureEventDetails(ui::ET_GESTURE_SCROLL_BEGIN)); |
| 1143 |
| 1144 // Gesture events should not be forwarded if the flag is not set. |
| 1145 EXPECT_EQ(CountOwnerOnGestureEvent(), 0); |
| 1146 EXPECT_FALSE(controller->send_gesture_events_to_owner()); |
| 1147 controller->OnGestureEvent(sub_menu, &event); |
| 1148 EXPECT_EQ(CountOwnerOnGestureEvent(), 0); |
| 1149 |
| 1150 // The menu's owner should receive gestures triggered outside the menu. |
| 1151 controller->set_send_gesture_events_to_owner(true); |
| 1152 controller->OnGestureEvent(sub_menu, &event); |
| 1153 EXPECT_EQ(CountOwnerOnGestureEvent(), 1); |
| 1154 |
| 1155 ui::GestureEvent event2(location.x(), location.y(), 0, ui::EventTimeForNow(), |
| 1156 ui::GestureEventDetails(ui::ET_GESTURE_END)); |
| 1157 |
| 1158 controller->OnGestureEvent(sub_menu, &event2); |
| 1159 EXPECT_EQ(CountOwnerOnGestureEvent(), 2); |
| 1160 |
| 1161 // ET_GESTURE_END resets the |send_gesture_events_to_owner_| flag, so futher |
| 1162 // gesture events should not be sent to the owner. |
| 1163 controller->OnGestureEvent(sub_menu, &event2); |
| 1164 EXPECT_EQ(CountOwnerOnGestureEvent(), 2); |
| 1165 } |
| 1166 #endif // !defined(OS_MACOSX) |
| 1167 |
| 1114 // Tests that a nested menu does not crash when trying to repost events that | 1168 // Tests that a nested menu does not crash when trying to repost events that |
| 1115 // occur outside of the bounds of the menu. Instead a proper shutdown should | 1169 // occur outside of the bounds of the menu. Instead a proper shutdown should |
| 1116 // occur. | 1170 // occur. |
| 1117 TEST_F(MenuControllerTest, AsynchronousRepostEvent) { | 1171 TEST_F(MenuControllerTest, AsynchronousRepostEvent) { |
| 1118 MenuController* controller = menu_controller(); | 1172 MenuController* controller = menu_controller(); |
| 1119 TestMenuControllerDelegate* delegate = menu_controller_delegate(); | 1173 TestMenuControllerDelegate* delegate = menu_controller_delegate(); |
| 1120 std::unique_ptr<TestMenuControllerDelegate> nested_delegate( | 1174 std::unique_ptr<TestMenuControllerDelegate> nested_delegate( |
| 1121 new TestMenuControllerDelegate()); | 1175 new TestMenuControllerDelegate()); |
| 1122 | 1176 |
| 1123 controller->AddNestedDelegate(nested_delegate.get()); | 1177 controller->AddNestedDelegate(nested_delegate.get()); |
| (...skipping 336 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1460 ui::MouseEvent release_event(ui::ET_MOUSE_RELEASED, release_location, | 1514 ui::MouseEvent release_event(ui::ET_MOUSE_RELEASED, release_location, |
| 1461 release_location, ui::EventTimeForNow(), | 1515 release_location, ui::EventTimeForNow(), |
| 1462 ui::EF_LEFT_MOUSE_BUTTON, 0); | 1516 ui::EF_LEFT_MOUSE_BUTTON, 0); |
| 1463 ProcessMouseReleased(sub_menu, release_event); | 1517 ProcessMouseReleased(sub_menu, release_event); |
| 1464 } | 1518 } |
| 1465 | 1519 |
| 1466 #endif // defined(USE_AURA) | 1520 #endif // defined(USE_AURA) |
| 1467 | 1521 |
| 1468 } // namespace test | 1522 } // namespace test |
| 1469 } // namespace views | 1523 } // namespace views |
| OLD | NEW |