OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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/i18n/case_conversion.h" | 7 #include "base/i18n/case_conversion.h" |
8 #include "base/i18n/rtl.h" | 8 #include "base/i18n/rtl.h" |
9 #include "base/run_loop.h" | 9 #include "base/run_loop.h" |
10 #include "base/time.h" | 10 #include "base/time.h" |
(...skipping 254 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
265 MenuController* MenuController::GetActiveInstance() { | 265 MenuController* MenuController::GetActiveInstance() { |
266 return active_instance_; | 266 return active_instance_; |
267 } | 267 } |
268 | 268 |
269 MenuItemView* MenuController::Run(Widget* parent, | 269 MenuItemView* MenuController::Run(Widget* parent, |
270 MenuButton* button, | 270 MenuButton* button, |
271 MenuItemView* root, | 271 MenuItemView* root, |
272 const gfx::Rect& bounds, | 272 const gfx::Rect& bounds, |
273 MenuItemView::AnchorPosition position, | 273 MenuItemView::AnchorPosition position, |
274 bool context_menu, | 274 bool context_menu, |
275 int* result_mouse_event_flags) { | 275 int* result_event_flags) { |
276 exit_type_ = EXIT_NONE; | 276 exit_type_ = EXIT_NONE; |
277 possible_drag_ = false; | 277 possible_drag_ = false; |
278 drag_in_progress_ = false; | 278 drag_in_progress_ = false; |
279 | 279 |
280 bool nested_menu = showing_; | 280 bool nested_menu = showing_; |
281 if (showing_) { | 281 if (showing_) { |
282 // Only support nesting of blocking_run menus, nesting of | 282 // Only support nesting of blocking_run menus, nesting of |
283 // blocking/non-blocking shouldn't be needed. | 283 // blocking/non-blocking shouldn't be needed. |
284 DCHECK(blocking_run_); | 284 DCHECK(blocking_run_); |
285 | 285 |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
344 menu_stack_.pop_back(); | 344 menu_stack_.pop_back(); |
345 } else { | 345 } else { |
346 showing_ = false; | 346 showing_ = false; |
347 did_capture_ = false; | 347 did_capture_ = false; |
348 } | 348 } |
349 | 349 |
350 MenuItemView* result = result_; | 350 MenuItemView* result = result_; |
351 // In case we're nested, reset result_. | 351 // In case we're nested, reset result_. |
352 result_ = NULL; | 352 result_ = NULL; |
353 | 353 |
354 if (result_mouse_event_flags) | 354 if (result_event_flags) |
355 *result_mouse_event_flags = result_mouse_event_flags_; | 355 *result_event_flags = accept_event_flags_; |
356 | 356 |
357 if (exit_type_ == EXIT_OUTERMOST) { | 357 if (exit_type_ == EXIT_OUTERMOST) { |
358 SetExitType(EXIT_NONE); | 358 SetExitType(EXIT_NONE); |
359 } else { | 359 } else { |
360 if (nested_menu && result) { | 360 if (nested_menu && result) { |
361 // We're nested and about to return a value. The caller might enter | 361 // We're nested and about to return a value. The caller might enter |
362 // another blocking loop. We need to make sure all menus are hidden | 362 // another blocking loop. We need to make sure all menus are hidden |
363 // before that happens otherwise the menus will stay on screen. | 363 // before that happens otherwise the menus will stay on screen. |
364 CloseAllNestedMenus(); | 364 CloseAllNestedMenus(); |
365 SetSelection(NULL, SELECTION_UPDATE_IMMEDIATELY | SELECTION_EXIT); | 365 SetSelection(NULL, SELECTION_UPDATE_IMMEDIATELY | SELECTION_EXIT); |
(...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
517 } else if (event->type() == ui::ET_GESTURE_LONG_PRESS) { | 517 } else if (event->type() == ui::ET_GESTURE_LONG_PRESS) { |
518 if (part.type == MenuPart::MENU_ITEM && part.menu) { | 518 if (part.type == MenuPart::MENU_ITEM && part.menu) { |
519 if (ShowContextMenu(part.menu, source, *event)) | 519 if (ShowContextMenu(part.menu, source, *event)) |
520 event->StopPropagation(); | 520 event->StopPropagation(); |
521 } | 521 } |
522 } else if (event->type() == ui::ET_GESTURE_TAP) { | 522 } else if (event->type() == ui::ET_GESTURE_TAP) { |
523 if (!part.is_scroll() && part.menu && | 523 if (!part.is_scroll() && part.menu && |
524 !(part.menu->HasSubmenu())) { | 524 !(part.menu->HasSubmenu())) { |
525 if (part.menu->GetDelegate()->IsTriggerableEvent( | 525 if (part.menu->GetDelegate()->IsTriggerableEvent( |
526 part.menu, *event)) { | 526 part.menu, *event)) { |
527 Accept(part.menu, 0); | 527 Accept(part.menu, event->flags()); |
528 } | 528 } |
529 event->StopPropagation(); | 529 event->StopPropagation(); |
530 } else if (part.type == MenuPart::MENU_ITEM) { | 530 } else if (part.type == MenuPart::MENU_ITEM) { |
531 // User either tapped on empty space, or a menu that has children. | 531 // User either tapped on empty space, or a menu that has children. |
532 SetSelection(part.menu ? part.menu : state_.item, | 532 SetSelection(part.menu ? part.menu : state_.item, |
533 SELECTION_OPEN_SUBMENU | SELECTION_UPDATE_IMMEDIATELY); | 533 SELECTION_OPEN_SUBMENU | SELECTION_UPDATE_IMMEDIATELY); |
534 event->StopPropagation(); | 534 event->StopPropagation(); |
535 } | 535 } |
536 } | 536 } |
537 if (event->stopped_propagation()) | 537 if (event->stopped_propagation()) |
(...skipping 512 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1050 } | 1050 } |
1051 | 1051 |
1052 MenuController::MenuController(ui::NativeTheme* theme, | 1052 MenuController::MenuController(ui::NativeTheme* theme, |
1053 bool blocking, | 1053 bool blocking, |
1054 internal::MenuControllerDelegate* delegate) | 1054 internal::MenuControllerDelegate* delegate) |
1055 : blocking_run_(blocking), | 1055 : blocking_run_(blocking), |
1056 showing_(false), | 1056 showing_(false), |
1057 exit_type_(EXIT_NONE), | 1057 exit_type_(EXIT_NONE), |
1058 did_capture_(false), | 1058 did_capture_(false), |
1059 result_(NULL), | 1059 result_(NULL), |
1060 result_mouse_event_flags_(0), | 1060 accept_event_flags_(0), |
1061 drop_target_(NULL), | 1061 drop_target_(NULL), |
1062 drop_position_(MenuDelegate::DROP_UNKNOWN), | 1062 drop_position_(MenuDelegate::DROP_UNKNOWN), |
1063 owner_(NULL), | 1063 owner_(NULL), |
1064 possible_drag_(false), | 1064 possible_drag_(false), |
1065 drag_in_progress_(false), | 1065 drag_in_progress_(false), |
1066 valid_drop_coordinates_(false), | 1066 valid_drop_coordinates_(false), |
1067 last_drop_operation_(MenuDelegate::DROP_UNKNOWN), | 1067 last_drop_operation_(MenuDelegate::DROP_UNKNOWN), |
1068 showing_submenu_(false), | 1068 showing_submenu_(false), |
1069 menu_button_(NULL), | 1069 menu_button_(NULL), |
1070 active_mouse_view_(NULL), | 1070 active_mouse_view_(NULL), |
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1129 // Use the monitor area if the work area doesn't contain the bounds. This | 1129 // Use the monitor area if the work area doesn't contain the bounds. This |
1130 // handles showing a menu from the launcher. | 1130 // handles showing a menu from the launcher. |
1131 gfx::Rect monitor_area = GetScreen()->GetDisplayNearestPoint( | 1131 gfx::Rect monitor_area = GetScreen()->GetDisplayNearestPoint( |
1132 bounds.origin()).bounds(); | 1132 bounds.origin()).bounds(); |
1133 if (monitor_area.Contains(bounds)) | 1133 if (monitor_area.Contains(bounds)) |
1134 pending_state_.monitor_bounds = monitor_area; | 1134 pending_state_.monitor_bounds = monitor_area; |
1135 } | 1135 } |
1136 #endif | 1136 #endif |
1137 } | 1137 } |
1138 | 1138 |
1139 void MenuController::Accept(MenuItemView* item, int mouse_event_flags) { | 1139 void MenuController::Accept(MenuItemView* item, int event_flags) { |
1140 DCHECK(IsBlockingRun()); | 1140 DCHECK(IsBlockingRun()); |
1141 result_ = item; | 1141 result_ = item; |
1142 if (item && !menu_stack_.empty() && | 1142 if (item && !menu_stack_.empty() && |
1143 !item->GetDelegate()->ShouldCloseAllMenusOnExecute(item->GetCommand())) { | 1143 !item->GetDelegate()->ShouldCloseAllMenusOnExecute(item->GetCommand())) { |
1144 SetExitType(EXIT_OUTERMOST); | 1144 SetExitType(EXIT_OUTERMOST); |
1145 } else { | 1145 } else { |
1146 SetExitType(EXIT_ALL); | 1146 SetExitType(EXIT_ALL); |
1147 } | 1147 } |
1148 result_mouse_event_flags_ = mouse_event_flags; | 1148 accept_event_flags_ = event_flags; |
1149 } | 1149 } |
1150 | 1150 |
1151 bool MenuController::ShowSiblingMenu(SubmenuView* source, | 1151 bool MenuController::ShowSiblingMenu(SubmenuView* source, |
1152 const gfx::Point& mouse_location) { | 1152 const gfx::Point& mouse_location) { |
1153 if (!menu_stack_.empty() || !menu_button_) | 1153 if (!menu_stack_.empty() || !menu_button_) |
1154 return false; | 1154 return false; |
1155 | 1155 |
1156 View* source_view = source->GetScrollViewContainer(); | 1156 View* source_view = source->GetScrollViewContainer(); |
1157 if (mouse_location.x() >= 0 && | 1157 if (mouse_location.x() >= 0 && |
1158 mouse_location.x() < source_view->width() && | 1158 mouse_location.x() < source_view->width() && |
(...skipping 977 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2136 (!pending_state_.item->HasSubmenu() || | 2136 (!pending_state_.item->HasSubmenu() || |
2137 !pending_state_.item->GetSubmenu()->IsShowing())) { | 2137 !pending_state_.item->GetSubmenu()->IsShowing())) { |
2138 // On exit if the user hasn't selected an item with a submenu, move the | 2138 // On exit if the user hasn't selected an item with a submenu, move the |
2139 // selection back to the parent menu item. | 2139 // selection back to the parent menu item. |
2140 SetSelection(pending_state_.item->GetParentMenuItem(), | 2140 SetSelection(pending_state_.item->GetParentMenuItem(), |
2141 SELECTION_OPEN_SUBMENU); | 2141 SELECTION_OPEN_SUBMENU); |
2142 } | 2142 } |
2143 } | 2143 } |
2144 | 2144 |
2145 } // namespace views | 2145 } // namespace views |
OLD | NEW |