diff options
author | sschmitz@chromium.org <sschmitz@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-01-25 01:22:54 +0000 |
---|---|---|
committer | sschmitz@chromium.org <sschmitz@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2013-01-25 01:22:54 +0000 |
commit | 238a8ecfe67823c07675c5347fdfedd858cd23e3 (patch) | |
tree | 119b59409b1331d5c2e0e46d11d1ca4f04291fa3 | |
parent | 58d57eb7e554dd78a2c88b7de93d3e29d7d21edc (diff) | |
download | chromium_src-238a8ecfe67823c07675c5347fdfedd858cd23e3.zip chromium_src-238a8ecfe67823c07675c5347fdfedd858cd23e3.tar.gz chromium_src-238a8ecfe67823c07675c5347fdfedd858cd23e3.tar.bz2 |
context menu does not work if one already open
This improves how ChromeOS handles mouse button presses
outside of a context menu. On mouse button presses not
only is the context menu and is message loop exited, but
the event is processed with the same result as if the
context menu had not been present. For example, a window
may be activated, another context menu may be brought up,
a new tab button may be executed, etc. This CL does not
yet handle touch events (separate issue).
The behavior is now more similar to how it works on Windows.
BUG=151074, 162172
TEST=manual
Bring up various context menus, then click various mouse
buttons outside of it.
Review URL: https://chromiumcodereview.appspot.com/11761027
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@178717 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r-- | ui/base/events/event.cc | 12 | ||||
-rw-r--r-- | ui/views/controls/menu/menu_controller.cc | 29 | ||||
-rw-r--r-- | ui/views/controls/menu/menu_controller.h | 3 |
3 files changed, 39 insertions, 5 deletions
diff --git a/ui/base/events/event.cc b/ui/base/events/event.cc index eda682b..cffc21f 100644 --- a/ui/base/events/event.cc +++ b/ui/base/events/event.cc @@ -104,6 +104,14 @@ std::string EventTypeName(ui::EventType type) { return std::string(); } +bool IsX11SendEventTrue(const base::NativeEvent& event) { +#if defined(USE_X11) + if (event && event->xany.send_event) + return true; +#endif + return false; +} + } // namespace namespace ui { @@ -317,7 +325,9 @@ bool MouseEvent::IsRepeatedClickEvent( int MouseEvent::GetRepeatCount(const MouseEvent& event) { int click_count = 1; if (last_click_event_) { - if (IsRepeatedClickEvent(*last_click_event_, event)) + if (IsX11SendEventTrue(event.native_event())) + click_count = last_click_event_->GetClickCount(); + else if (IsRepeatedClickEvent(*last_click_event_, event)) click_count = last_click_event_->GetClickCount() + 1; delete last_click_event_; } diff --git a/ui/views/controls/menu/menu_controller.cc b/ui/views/controls/menu/menu_controller.cc index ea8e446..cdeb37b 100644 --- a/ui/views/controls/menu/menu_controller.cc +++ b/ui/views/controls/menu/menu_controller.cc @@ -34,6 +34,10 @@ #include "ui/aura/window.h" #endif +#if defined(USE_X11) +#include <X11/Xlib.h> +#endif + using base::Time; using base::TimeDelta; using ui::OSExchangeData; @@ -803,9 +807,8 @@ void MenuController::SetSelectionOnPointerDown(SubmenuView* source, // We're going to close and we own the mouse capture. We need to repost the // mouse down, otherwise the window the user clicked on won't get the // event. -#if defined(OS_WIN) && !defined(USE_AURA) +#if (defined(OS_WIN) && !defined(USE_AURA)) || defined(USE_X11) RepostEvent(source, event); - // NOTE: not reposting on linux seems fine. #endif // And close. @@ -1974,7 +1977,27 @@ void MenuController::RepostEvent(SubmenuView* source, } } } -#endif // defined(OS_WIN) +#elif defined(USE_X11) +void MenuController::RepostEvent(SubmenuView* source, + const ui::LocatedEvent& event) { + if (!state_.item) { + // We some times get an event after closing all the menus. Ignore it. + // Make sure the menu is in fact not visible. If the menu is visible, then + // we're in a bad state where we think the menu isn't visibile but it is. + DCHECK(!source->GetWidget()->IsVisible()); + return; + } + if (!event.native_event()) + return; + // We putback the X11 event. We set the "send_event" field in the + // XEvent. Otherwise a mouse click would generate a double click + // event. The field "send_event" is in the same place for all event + // types so we can use "xany" regardless of type. + XEvent xevent = *event.native_event(); + xevent.xany.send_event = True; + XPutBackEvent(xevent.xany.display, &xevent); +} +#endif void MenuController::SetDropMenuItem( MenuItemView* new_target, diff --git a/ui/views/controls/menu/menu_controller.h b/ui/views/controls/menu/menu_controller.h index 891026f..1e5985c3 100644 --- a/ui/views/controls/menu/menu_controller.h +++ b/ui/views/controls/menu/menu_controller.h @@ -412,9 +412,10 @@ class VIEWS_EXPORT MenuController // the title. Returns true if a match was selected and the menu should exit. bool SelectByChar(char16 key); -#if defined(OS_WIN) && !defined(USE_AURA) +#if (defined(OS_WIN) && !defined(USE_AURA)) || defined(USE_X11) // If there is a window at the location of the event, a new mouse event is // generated and posted to it at the given location. + // For Chromeos this applies also to the desktop background window. void RepostEvent(SubmenuView* source, const ui::LocatedEvent& event); #endif |