Chromium Code Reviews| 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/macros.h" | 9 #include "base/macros.h" |
| 10 #include "base/strings/utf_string_conversions.h" | 10 #include "base/strings/utf_string_conversions.h" |
| (...skipping 345 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 356 | 356 |
| 357 // If there are multiple matches this is the index of the item after the | 357 // If there are multiple matches this is the index of the item after the |
| 358 // currently selected item whose mnemonic matches. This may remain -1 even | 358 // currently selected item whose mnemonic matches. This may remain -1 even |
| 359 // though there are matches. | 359 // though there are matches. |
| 360 int next_match; | 360 int next_match; |
| 361 }; | 361 }; |
| 362 | 362 |
| 363 // MenuController:State ------------------------------------------------------ | 363 // MenuController:State ------------------------------------------------------ |
| 364 | 364 |
| 365 MenuController::State::State() | 365 MenuController::State::State() |
| 366 : item(NULL), | 366 : item(nullptr), |
| 367 hot_button(nullptr), | |
| 367 submenu_open(false), | 368 submenu_open(false), |
| 368 anchor(MENU_ANCHOR_TOPLEFT), | 369 anchor(MENU_ANCHOR_TOPLEFT), |
| 369 context_menu(false) { | 370 context_menu(false) { |
| 370 } | 371 } |
| 371 | 372 |
| 372 MenuController::State::State(const State& other) = default; | 373 MenuController::State::State(const State& other) = default; |
| 373 | 374 |
| 374 MenuController::State::~State() {} | 375 MenuController::State::~State() {} |
| 375 | 376 |
| 376 // MenuController ------------------------------------------------------------ | 377 // MenuController ------------------------------------------------------------ |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 417 } | 418 } |
| 418 } | 419 } |
| 419 } | 420 } |
| 420 | 421 |
| 421 bool nested_menu = showing_; | 422 bool nested_menu = showing_; |
| 422 if (showing_) { | 423 if (showing_) { |
| 423 // Only support nesting of blocking_run menus, nesting of | 424 // Only support nesting of blocking_run menus, nesting of |
| 424 // blocking/non-blocking shouldn't be needed. | 425 // blocking/non-blocking shouldn't be needed. |
| 425 DCHECK(blocking_run_); | 426 DCHECK(blocking_run_); |
| 426 | 427 |
| 428 state_.hot_button = hot_button_; | |
| 429 hot_button_ = nullptr; | |
| 427 // We're already showing, push the current state. | 430 // We're already showing, push the current state. |
| 428 menu_stack_.push_back( | 431 menu_stack_.push_back( |
| 429 std::make_pair(state_, make_linked_ptr(pressed_lock_.release()))); | 432 std::make_pair(state_, make_linked_ptr(pressed_lock_.release()))); |
| 430 | 433 |
| 431 // The context menu should be owned by the same parent. | 434 // The context menu should be owned by the same parent. |
| 432 DCHECK_EQ(owner_, parent); | 435 DCHECK_EQ(owner_, parent); |
| 433 } else { | 436 } else { |
| 434 showing_ = true; | 437 showing_ = true; |
| 435 | 438 |
| 436 #if defined(USE_AURA) | 439 #if defined(USE_AURA) |
| (...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 551 | 554 |
| 552 current_mouse_pressed_state_ |= event.changed_button_flags(); | 555 current_mouse_pressed_state_ |= event.changed_button_flags(); |
| 553 | 556 |
| 554 if (forward_to_root) { | 557 if (forward_to_root) { |
| 555 ui::MouseEvent event_for_root(event); | 558 ui::MouseEvent event_for_root(event); |
| 556 // Reset hot-tracking if a different view is getting a mouse press. | 559 // Reset hot-tracking if a different view is getting a mouse press. |
| 557 ConvertLocatedEventForRootView(source, forward_to_root, &event_for_root); | 560 ConvertLocatedEventForRootView(source, forward_to_root, &event_for_root); |
| 558 View* view = | 561 View* view = |
| 559 forward_to_root->GetEventHandlerForPoint(event_for_root.location()); | 562 forward_to_root->GetEventHandlerForPoint(event_for_root.location()); |
| 560 CustomButton* button = CustomButton::AsCustomButton(view); | 563 CustomButton* button = CustomButton::AsCustomButton(view); |
| 561 if (hot_button_ && hot_button_ != button) | 564 if (hot_button_ != button) |
| 562 SetHotTrackedButton(nullptr); | 565 SetHotTrackedButton(button); |
| 563 | 566 |
| 564 // Empty menu items are always handled by the menu controller. | 567 // Empty menu items are always handled by the menu controller. |
| 565 if (!view || view->id() != MenuItemView::kEmptyMenuItemViewID) { | 568 if (!view || view->id() != MenuItemView::kEmptyMenuItemViewID) { |
| 566 bool processed = forward_to_root->ProcessMousePressed(event_for_root); | 569 bool processed = forward_to_root->ProcessMousePressed(event_for_root); |
| 567 // If the event was processed, the root view becomes our current mouse | 570 // If the event was processed, the root view becomes our current mouse |
| 568 // handler... | 571 // handler... |
| 569 if (processed && !current_mouse_event_target_) { | 572 if (processed && !current_mouse_event_target_) { |
| 570 current_mouse_event_target_ = forward_to_root; | 573 current_mouse_event_target_ = forward_to_root; |
| 571 } | 574 } |
| 572 | 575 |
| (...skipping 254 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 827 | 830 |
| 828 void MenuController::ViewHierarchyChanged( | 831 void MenuController::ViewHierarchyChanged( |
| 829 SubmenuView* source, | 832 SubmenuView* source, |
| 830 const View::ViewHierarchyChangedDetails& details) { | 833 const View::ViewHierarchyChangedDetails& details) { |
| 831 if (!details.is_add) { | 834 if (!details.is_add) { |
| 832 // If the current mouse handler is removed, remove it as the handler. | 835 // If the current mouse handler is removed, remove it as the handler. |
| 833 if (details.child == current_mouse_event_target_) { | 836 if (details.child == current_mouse_event_target_) { |
| 834 current_mouse_event_target_ = nullptr; | 837 current_mouse_event_target_ = nullptr; |
| 835 current_mouse_pressed_state_ = 0; | 838 current_mouse_pressed_state_ = 0; |
| 836 } | 839 } |
| 837 // Update |hot_button_| if it gets removed while a menu is up. | 840 // Update |hot_button_| (both in |this| and in |menu_stack_| if it gets |
| 838 if (details.child == hot_button_) | 841 // removed while a menu is up. |
| 842 if (details.child == hot_button_) { | |
| 839 hot_button_ = nullptr; | 843 hot_button_ = nullptr; |
| 844 for (auto nested_state : menu_stack_) { | |
| 845 State& state = nested_state.first; | |
| 846 if (details.child == state.hot_button) | |
| 847 state.hot_button = nullptr; | |
| 848 } | |
| 849 } | |
| 840 } | 850 } |
| 841 } | 851 } |
| 842 | 852 |
| 843 bool MenuController::GetDropFormats( | 853 bool MenuController::GetDropFormats( |
| 844 SubmenuView* source, | 854 SubmenuView* source, |
| 845 int* formats, | 855 int* formats, |
| 846 std::set<ui::Clipboard::FormatType>* format_types) { | 856 std::set<ui::Clipboard::FormatType>* format_types) { |
| 847 return source->GetMenuItem()->GetDelegate()->GetDropFormats( | 857 return source->GetMenuItem()->GetDelegate()->GetDropFormats( |
| 848 source->GetMenuItem(), formats, format_types); | 858 source->GetMenuItem(), formats, format_types); |
| 849 } | 859 } |
| (...skipping 1692 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2542 #endif | 2552 #endif |
| 2543 | 2553 |
| 2544 linked_ptr<MenuButton::PressedLock> nested_pressed_lock; | 2554 linked_ptr<MenuButton::PressedLock> nested_pressed_lock; |
| 2545 bool nested_menu = !menu_stack_.empty(); | 2555 bool nested_menu = !menu_stack_.empty(); |
| 2546 if (nested_menu) { | 2556 if (nested_menu) { |
| 2547 DCHECK(!menu_stack_.empty()); | 2557 DCHECK(!menu_stack_.empty()); |
| 2548 // We're running from within a menu, restore the previous state. | 2558 // We're running from within a menu, restore the previous state. |
| 2549 // The menus are already showing, so we don't have to show them. | 2559 // The menus are already showing, so we don't have to show them. |
| 2550 state_ = menu_stack_.back().first; | 2560 state_ = menu_stack_.back().first; |
| 2551 pending_state_ = menu_stack_.back().first; | 2561 pending_state_ = menu_stack_.back().first; |
| 2562 hot_button_ = state_.hot_button; | |
| 2552 nested_pressed_lock = menu_stack_.back().second; | 2563 nested_pressed_lock = menu_stack_.back().second; |
| 2553 menu_stack_.pop_back(); | 2564 menu_stack_.pop_back(); |
| 2554 // Even though the menus are nested, there may not be nested delegates. | 2565 // Even though the menus are nested, there may not be nested delegates. |
| 2555 if (delegate_stack_.size() > 1) { | 2566 if (delegate_stack_.size() > 1) { |
| 2556 delegate_stack_.pop_back(); | 2567 delegate_stack_.pop_back(); |
| 2557 delegate_ = delegate_stack_.back().first; | 2568 delegate_ = delegate_stack_.back().first; |
| 2558 async_run_ = delegate_stack_.back().second; | 2569 async_run_ = delegate_stack_.back().second; |
| 2559 } | 2570 } |
| 2560 } else { | 2571 } else { |
| 2561 #if defined(USE_AURA) | 2572 #if defined(USE_AURA) |
| (...skipping 19 matching lines...) Expand all Loading... | |
| 2581 SetSelection(nullptr, SELECTION_UPDATE_IMMEDIATELY | SELECTION_EXIT); | 2592 SetSelection(nullptr, SELECTION_UPDATE_IMMEDIATELY | SELECTION_EXIT); |
| 2582 | 2593 |
| 2583 // Set exit_all_, which makes sure all nested loops exit immediately. | 2594 // Set exit_all_, which makes sure all nested loops exit immediately. |
| 2584 if (exit_type_ != EXIT_DESTROYED) | 2595 if (exit_type_ != EXIT_DESTROYED) |
| 2585 SetExitType(EXIT_ALL); | 2596 SetExitType(EXIT_ALL); |
| 2586 } else { | 2597 } else { |
| 2587 TerminateNestedMessageLoopIfNecessary(); | 2598 TerminateNestedMessageLoopIfNecessary(); |
| 2588 } | 2599 } |
| 2589 } | 2600 } |
| 2590 | 2601 |
| 2591 // Reset our pressed lock to the previous state's, if there was one. | 2602 // Reset our pressed lock and hot-tracked state to the previous state's, if |
| 2592 // The lock handles the case if the button was destroyed. | 2603 // they were active. The lock handles the case if the button was destroyed. |
| 2593 pressed_lock_.reset(nested_pressed_lock.release()); | 2604 pressed_lock_.reset(nested_pressed_lock.release()); |
| 2605 if (hot_button_) | |
| 2606 hot_button_->SetHotTracked(true); | |
|
jonross
2016/03/24 18:48:18
Is it possible for this hot_button_ to no longer b
sky
2016/03/24 19:12:56
In looking at it, this method is confusingly named
| |
| 2594 | 2607 |
| 2595 return result; | 2608 return result; |
| 2596 } | 2609 } |
| 2597 | 2610 |
| 2598 void MenuController::HandleMouseLocation(SubmenuView* source, | 2611 void MenuController::HandleMouseLocation(SubmenuView* source, |
| 2599 const gfx::Point& mouse_location) { | 2612 const gfx::Point& mouse_location) { |
| 2600 if (showing_submenu_) | 2613 if (showing_submenu_) |
| 2601 return; | 2614 return; |
| 2602 | 2615 |
| 2603 // Ignore mouse events if we're closing the menu. | 2616 // Ignore mouse events if we're closing the menu. |
| (...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2646 return; | 2659 return; |
| 2647 } | 2660 } |
| 2648 if (hot_button_) | 2661 if (hot_button_) |
| 2649 hot_button_->SetHotTracked(false); | 2662 hot_button_->SetHotTracked(false); |
| 2650 hot_button_ = hot_button; | 2663 hot_button_ = hot_button; |
| 2651 if (hot_button) | 2664 if (hot_button) |
| 2652 hot_button->SetHotTracked(true); | 2665 hot_button->SetHotTracked(true); |
| 2653 } | 2666 } |
| 2654 | 2667 |
| 2655 } // namespace views | 2668 } // namespace views |
| OLD | NEW |