| 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/aura/window_event_dispatcher.h" | 5 #include "ui/aura/window_event_dispatcher.h" |
| 6 | 6 |
| 7 #include <stddef.h> | 7 #include <stddef.h> |
| 8 | 8 |
| 9 #include "base/bind.h" | 9 #include "base/bind.h" |
| 10 #include "base/logging.h" | 10 #include "base/logging.h" |
| (...skipping 208 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 219 gfx::Point location = Env::GetInstance()->last_mouse_location(); | 219 gfx::Point location = Env::GetInstance()->last_mouse_location(); |
| 220 client::ScreenPositionClient* client = | 220 client::ScreenPositionClient* client = |
| 221 client::GetScreenPositionClient(window()); | 221 client::GetScreenPositionClient(window()); |
| 222 if (client) | 222 if (client) |
| 223 client->ConvertPointFromScreen(window(), &location); | 223 client->ConvertPointFromScreen(window(), &location); |
| 224 return location; | 224 return location; |
| 225 } | 225 } |
| 226 | 226 |
| 227 void WindowEventDispatcher::OnHostLostMouseGrab() { | 227 void WindowEventDispatcher::OnHostLostMouseGrab() { |
| 228 mouse_pressed_handler_ = NULL; | 228 mouse_pressed_handler_ = NULL; |
| 229 LOG(ERROR) << "mouse_moved_handler_ = NULL (was " << mouse_moved_handler_ |
| 230 << ")"; |
| 229 mouse_moved_handler_ = NULL; | 231 mouse_moved_handler_ = NULL; |
| 230 } | 232 } |
| 231 | 233 |
| 232 void WindowEventDispatcher::OnCursorMovedToRootLocation( | 234 void WindowEventDispatcher::OnCursorMovedToRootLocation( |
| 233 const gfx::Point& root_location) { | 235 const gfx::Point& root_location) { |
| 234 Env::GetInstance()->env_controller()->SetLastMouseLocation(window(), | 236 Env::GetInstance()->env_controller()->SetLastMouseLocation(window(), |
| 235 root_location); | 237 root_location); |
| 236 | 238 |
| 237 // Synthesize a mouse move in case the cursor's location in root coordinates | 239 // Synthesize a mouse move in case the cursor's location in root coordinates |
| 238 // changed but its position in WindowTreeHost coordinates did not. | 240 // changed but its position in WindowTreeHost coordinates did not. |
| (...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 320 } | 322 } |
| 321 return details; | 323 return details; |
| 322 } | 324 } |
| 323 | 325 |
| 324 void WindowEventDispatcher::OnWindowHidden(Window* invisible, | 326 void WindowEventDispatcher::OnWindowHidden(Window* invisible, |
| 325 WindowHiddenReason reason) { | 327 WindowHiddenReason reason) { |
| 326 // If the window the mouse was pressed in becomes invisible, it should no | 328 // If the window the mouse was pressed in becomes invisible, it should no |
| 327 // longer receive mouse events. | 329 // longer receive mouse events. |
| 328 if (invisible->Contains(mouse_pressed_handler_)) | 330 if (invisible->Contains(mouse_pressed_handler_)) |
| 329 mouse_pressed_handler_ = NULL; | 331 mouse_pressed_handler_ = NULL; |
| 330 if (invisible->Contains(mouse_moved_handler_)) | 332 if (invisible->Contains(mouse_moved_handler_)) { |
| 333 LOG(ERROR) << "mouse_moved_handler_ = NULL (was " << mouse_moved_handler_ |
| 334 << ")"; |
| 331 mouse_moved_handler_ = NULL; | 335 mouse_moved_handler_ = NULL; |
| 336 } |
| 332 | 337 |
| 333 // If events are being dispatched from a nested message-loop, and the target | 338 // If events are being dispatched from a nested message-loop, and the target |
| 334 // of the outer loop is hidden or moved to another dispatcher during | 339 // of the outer loop is hidden or moved to another dispatcher during |
| 335 // dispatching events in the inner loop, then reset the target for the outer | 340 // dispatching events in the inner loop, then reset the target for the outer |
| 336 // loop. | 341 // loop. |
| 337 if (invisible->Contains(old_dispatch_target_)) | 342 if (invisible->Contains(old_dispatch_target_)) |
| 338 old_dispatch_target_ = NULL; | 343 old_dispatch_target_ = NULL; |
| 339 | 344 |
| 340 invisible->CleanupGestureState(); | 345 invisible->CleanupGestureState(); |
| 341 | 346 |
| (...skipping 27 matching lines...) Expand all Loading... |
| 369 } | 374 } |
| 370 | 375 |
| 371 //////////////////////////////////////////////////////////////////////////////// | 376 //////////////////////////////////////////////////////////////////////////////// |
| 372 // WindowEventDispatcher, aura::client::CaptureDelegate implementation: | 377 // WindowEventDispatcher, aura::client::CaptureDelegate implementation: |
| 373 | 378 |
| 374 void WindowEventDispatcher::UpdateCapture(Window* old_capture, | 379 void WindowEventDispatcher::UpdateCapture(Window* old_capture, |
| 375 Window* new_capture) { | 380 Window* new_capture) { |
| 376 // |mouse_moved_handler_| may have been set to a Window in a different root | 381 // |mouse_moved_handler_| may have been set to a Window in a different root |
| 377 // (see below). Clear it here to ensure we don't end up referencing a stale | 382 // (see below). Clear it here to ensure we don't end up referencing a stale |
| 378 // Window. | 383 // Window. |
| 379 if (mouse_moved_handler_ && !window()->Contains(mouse_moved_handler_)) | 384 if (mouse_moved_handler_ && !window()->Contains(mouse_moved_handler_)) { |
| 385 LOG(ERROR) << "mouse_moved_handler_ = NULL (was " << mouse_moved_handler_ |
| 386 << ")"; |
| 380 mouse_moved_handler_ = NULL; | 387 mouse_moved_handler_ = NULL; |
| 388 } |
| 381 | 389 |
| 382 if (old_capture && old_capture->GetRootWindow() == window() && | 390 if (old_capture && old_capture->GetRootWindow() == window() && |
| 383 old_capture->delegate()) { | 391 old_capture->delegate()) { |
| 384 // Send a capture changed event with bogus location data. | 392 // Send a capture changed event with bogus location data. |
| 385 ui::MouseEvent event(ui::ET_MOUSE_CAPTURE_CHANGED, gfx::Point(), | 393 ui::MouseEvent event(ui::ET_MOUSE_CAPTURE_CHANGED, gfx::Point(), |
| 386 gfx::Point(), ui::EventTimeForNow(), 0, 0); | 394 gfx::Point(), ui::EventTimeForNow(), 0, 0); |
| 387 | 395 |
| 388 DispatchDetails details = DispatchEvent(old_capture, &event); | 396 DispatchDetails details = DispatchEvent(old_capture, &event); |
| 389 if (details.dispatcher_destroyed) | 397 if (details.dispatcher_destroyed) |
| 390 return; | 398 return; |
| 391 | 399 |
| 392 if (!details.target_destroyed) | 400 if (!details.target_destroyed) |
| 393 old_capture->delegate()->OnCaptureLost(); | 401 old_capture->delegate()->OnCaptureLost(); |
| 394 } | 402 } |
| 395 | 403 |
| 396 if (new_capture) { | 404 if (new_capture) { |
| 397 // Make all subsequent mouse events go to the capture window. We shouldn't | 405 // Make all subsequent mouse events go to the capture window. We shouldn't |
| 398 // need to send an event here as OnCaptureLost() should take care of that. | 406 // need to send an event here as OnCaptureLost() should take care of that. |
| 399 if (mouse_moved_handler_ || Env::GetInstance()->IsMouseButtonDown()) | 407 if (mouse_moved_handler_ || Env::GetInstance()->IsMouseButtonDown()) { |
| 408 LOG(ERROR) << "mouse_moved_handler_ = " << new_capture << " (was " |
| 409 << mouse_moved_handler_ << ")"; |
| 400 mouse_moved_handler_ = new_capture; | 410 mouse_moved_handler_ = new_capture; |
| 411 } |
| 401 } else { | 412 } else { |
| 402 // Make sure mouse_moved_handler gets updated. | 413 // Make sure mouse_moved_handler gets updated. |
| 403 DispatchDetails details = SynthesizeMouseMoveEvent(); | 414 DispatchDetails details = SynthesizeMouseMoveEvent(); |
| 404 if (details.dispatcher_destroyed) | 415 if (details.dispatcher_destroyed) |
| 405 return; | 416 return; |
| 406 } | 417 } |
| 407 mouse_pressed_handler_ = NULL; | 418 mouse_pressed_handler_ = NULL; |
| 408 } | 419 } |
| 409 | 420 |
| 410 void WindowEventDispatcher::OnOtherRootGotCapture() { | 421 void WindowEventDispatcher::OnOtherRootGotCapture() { |
| 411 // Windows provides the TrackMouseEvents API which allows us to rely on the | 422 // Windows provides the TrackMouseEvents API which allows us to rely on the |
| 412 // OS to send us the mouse exit events (WM_MOUSELEAVE). Additionally on | 423 // OS to send us the mouse exit events (WM_MOUSELEAVE). Additionally on |
| 413 // desktop Windows, every top level window could potentially have its own | 424 // desktop Windows, every top level window could potentially have its own |
| 414 // root window, in which case this function will get called whenever those | 425 // root window, in which case this function will get called whenever those |
| 415 // windows grab mouse capture. Sending mouse exit messages in these cases | 426 // windows grab mouse capture. Sending mouse exit messages in these cases |
| 416 // causes subtle bugs like (crbug.com/394672). | 427 // causes subtle bugs like (crbug.com/394672). |
| 417 #if !defined(OS_WIN) | 428 #if !defined(OS_WIN) |
| 418 if (mouse_moved_handler_) { | 429 if (mouse_moved_handler_) { |
| 419 // Dispatch a mouse exit to reset any state associated with hover. This is | 430 // Dispatch a mouse exit to reset any state associated with hover. This is |
| 420 // important when going from no window having capture to a window having | 431 // important when going from no window having capture to a window having |
| 421 // capture because we do not dispatch ET_MOUSE_CAPTURE_CHANGED in this case. | 432 // capture because we do not dispatch ET_MOUSE_CAPTURE_CHANGED in this case. |
| 422 DispatchDetails details = | 433 DispatchDetails details = |
| 423 DispatchMouseExitAtPoint(nullptr, GetLastMouseLocationInRoot()); | 434 DispatchMouseExitAtPoint(nullptr, GetLastMouseLocationInRoot()); |
| 424 if (details.dispatcher_destroyed) | 435 if (details.dispatcher_destroyed) |
| 425 return; | 436 return; |
| 426 } | 437 } |
| 427 #endif | 438 #endif |
| 428 | 439 |
| 440 LOG(ERROR) << "mouse_moved_handler_ = NULL (was " << mouse_moved_handler_ |
| 441 << ")"; |
| 429 mouse_moved_handler_ = NULL; | 442 mouse_moved_handler_ = NULL; |
| 430 mouse_pressed_handler_ = NULL; | 443 mouse_pressed_handler_ = NULL; |
| 431 } | 444 } |
| 432 | 445 |
| 433 void WindowEventDispatcher::SetNativeCapture() { | 446 void WindowEventDispatcher::SetNativeCapture() { |
| 434 host_->SetCapture(); | 447 host_->SetCapture(); |
| 435 } | 448 } |
| 436 | 449 |
| 437 void WindowEventDispatcher::ReleaseNativeCapture() { | 450 void WindowEventDispatcher::ReleaseNativeCapture() { |
| 438 host_->ReleaseCapture(); | 451 host_->ReleaseCapture(); |
| (...skipping 364 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 803 return DispatchDetails(); | 816 return DispatchDetails(); |
| 804 } | 817 } |
| 805 | 818 |
| 806 DispatchDetails WindowEventDispatcher::PreDispatchMouseEvent( | 819 DispatchDetails WindowEventDispatcher::PreDispatchMouseEvent( |
| 807 Window* target, | 820 Window* target, |
| 808 ui::MouseEvent* event) { | 821 ui::MouseEvent* event) { |
| 809 client::CursorClient* cursor_client = client::GetCursorClient(window()); | 822 client::CursorClient* cursor_client = client::GetCursorClient(window()); |
| 810 // We allow synthesized mouse exit events through even if mouse events are | 823 // We allow synthesized mouse exit events through even if mouse events are |
| 811 // disabled. This ensures that hover state, etc on controls like buttons is | 824 // disabled. This ensures that hover state, etc on controls like buttons is |
| 812 // cleared. | 825 // cleared. |
| 826 if (cursor_client) |
| 827 LOG(ERROR) << cursor_client->IsMouseEventsEnabled(); |
| 813 if (cursor_client && | 828 if (cursor_client && |
| 814 !cursor_client->IsMouseEventsEnabled() && | 829 !cursor_client->IsMouseEventsEnabled() && |
| 815 (event->flags() & ui::EF_IS_SYNTHESIZED) && | 830 (event->flags() & ui::EF_IS_SYNTHESIZED) && |
| 816 (event->type() != ui::ET_MOUSE_EXITED)) { | 831 (event->type() != ui::ET_MOUSE_EXITED)) { |
| 832 LOG(ERROR) << "drop"; |
| 817 event->SetHandled(); | 833 event->SetHandled(); |
| 818 return DispatchDetails(); | 834 return DispatchDetails(); |
| 819 } | 835 } |
| 820 | 836 |
| 821 Env::GetInstance()->env_controller()->UpdateStateForMouseEvent(window(), | 837 Env::GetInstance()->env_controller()->UpdateStateForMouseEvent(window(), |
| 822 *event); | 838 *event); |
| 823 | 839 |
| 824 if (IsEventCandidateForHold(*event) && !dispatching_held_event_) { | 840 if (IsEventCandidateForHold(*event) && !dispatching_held_event_) { |
| 825 if (move_hold_count_) { | 841 if (move_hold_count_) { |
| 826 held_move_event_.reset(new ui::MouseEvent(*event, target, window())); | 842 held_move_event_.reset(new ui::MouseEvent(*event, target, window())); |
| 843 LOG(ERROR) << "drop"; |
| 827 event->SetHandled(); | 844 event->SetHandled(); |
| 828 return DispatchDetails(); | 845 return DispatchDetails(); |
| 829 } else { | 846 } else { |
| 830 // We may have a held event for a period between the time move_hold_count_ | 847 // We may have a held event for a period between the time move_hold_count_ |
| 831 // fell to 0 and the DispatchHeldEvents executes. Since we're going to | 848 // fell to 0 and the DispatchHeldEvents executes. Since we're going to |
| 832 // dispatch the new event directly below, we can reset the old one. | 849 // dispatch the new event directly below, we can reset the old one. |
| 833 held_move_event_.reset(); | 850 held_move_event_.reset(); |
| 834 } | 851 } |
| 835 } | 852 } |
| 836 | 853 |
| 837 switch (event->type()) { | 854 switch (event->type()) { |
| 838 case ui::ET_MOUSE_EXITED: | 855 case ui::ET_MOUSE_EXITED: |
| 839 if (!target || target == window()) { | 856 if (!target || target == window()) { |
| 840 DispatchDetails details = | 857 DispatchDetails details = |
| 841 DispatchMouseEnterOrExit(target, *event, ui::ET_MOUSE_EXITED); | 858 DispatchMouseEnterOrExit(target, *event, ui::ET_MOUSE_EXITED); |
| 842 if (details.dispatcher_destroyed) { | 859 if (details.dispatcher_destroyed) { |
| 843 event->SetHandled(); | 860 event->SetHandled(); |
| 844 return details; | 861 return details; |
| 845 } | 862 } |
| 863 LOG(ERROR) << "mouse_moved_handler_ = NULL (was " |
| 864 << mouse_moved_handler_ << ")"; |
| 846 mouse_moved_handler_ = NULL; | 865 mouse_moved_handler_ = NULL; |
| 847 } | 866 } |
| 848 break; | 867 break; |
| 849 case ui::ET_MOUSE_MOVED: | 868 case ui::ET_MOUSE_MOVED: |
| 850 // Send an exit to the current |mouse_moved_handler_| and an enter to | 869 // Send an exit to the current |mouse_moved_handler_| and an enter to |
| 851 // |target|. Take care that both us and |target| aren't destroyed during | 870 // |target|. Take care that both us and |target| aren't destroyed during |
| 852 // dispatch. | 871 // dispatch. |
| 853 if (target != mouse_moved_handler_) { | 872 if (target != mouse_moved_handler_) { |
| 854 aura::Window* old_mouse_moved_handler = mouse_moved_handler_; | 873 aura::Window* old_mouse_moved_handler = mouse_moved_handler_; |
| 855 WindowTracker live_window; | 874 WindowTracker live_window; |
| 856 live_window.Add(target); | 875 live_window.Add(target); |
| 857 DispatchDetails details = | 876 DispatchDetails details = |
| 858 DispatchMouseEnterOrExit(target, *event, ui::ET_MOUSE_EXITED); | 877 DispatchMouseEnterOrExit(target, *event, ui::ET_MOUSE_EXITED); |
| 859 // |details| contains information about |mouse_moved_handler_| being | 878 // |details| contains information about |mouse_moved_handler_| being |
| 860 // destroyed which is not our |target|. Return value of this function | 879 // destroyed which is not our |target|. Return value of this function |
| 861 // should be about our |target|. | 880 // should be about our |target|. |
| 862 DispatchDetails target_details = details; | 881 DispatchDetails target_details = details; |
| 863 target_details.target_destroyed = !live_window.Contains(target); | 882 target_details.target_destroyed = !live_window.Contains(target); |
| 864 if (details.dispatcher_destroyed) { | 883 if (details.dispatcher_destroyed) { |
| 884 LOG(ERROR) << "drop"; |
| 865 event->SetHandled(); | 885 event->SetHandled(); |
| 866 return target_details; | 886 return target_details; |
| 867 } | 887 } |
| 868 // If the |mouse_moved_handler_| changes out from under us, assume a | 888 // If the |mouse_moved_handler_| changes out from under us, assume a |
| 869 // nested run loop ran and we don't need to do anything. | 889 // nested run loop ran and we don't need to do anything. |
| 870 if (mouse_moved_handler_ != old_mouse_moved_handler) { | 890 if (mouse_moved_handler_ != old_mouse_moved_handler) { |
| 891 LOG(ERROR) << "drop"; |
| 871 event->SetHandled(); | 892 event->SetHandled(); |
| 872 return target_details; | 893 return target_details; |
| 873 } | 894 } |
| 874 if (details.target_destroyed || target_details.target_destroyed) { | 895 if (details.target_destroyed || target_details.target_destroyed) { |
| 896 LOG(ERROR) << "mouse_moved_handler_ = NULL (was " |
| 897 << mouse_moved_handler_ << ")"; |
| 875 mouse_moved_handler_ = NULL; | 898 mouse_moved_handler_ = NULL; |
| 876 event->SetHandled(); | 899 event->SetHandled(); |
| 877 return target_details; | 900 return target_details; |
| 878 } | 901 } |
| 879 live_window.Remove(target); | 902 live_window.Remove(target); |
| 880 | 903 |
| 904 LOG(ERROR) << "mouse_moved_handler_ = " << target << " (was " |
| 905 << mouse_moved_handler_ << ")"; |
| 881 mouse_moved_handler_ = target; | 906 mouse_moved_handler_ = target; |
| 882 details = | 907 details = |
| 883 DispatchMouseEnterOrExit(target, *event, ui::ET_MOUSE_ENTERED); | 908 DispatchMouseEnterOrExit(target, *event, ui::ET_MOUSE_ENTERED); |
| 884 if (details.dispatcher_destroyed || details.target_destroyed) { | 909 if (details.dispatcher_destroyed || details.target_destroyed) { |
| 885 event->SetHandled(); | 910 event->SetHandled(); |
| 886 return details; | 911 return details; |
| 887 } | 912 } |
| 888 } | 913 } |
| 889 break; | 914 break; |
| 890 case ui::ET_MOUSE_PRESSED: | 915 case ui::ET_MOUSE_PRESSED: |
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 937 ui::KeyEvent* event) { | 962 ui::KeyEvent* event) { |
| 938 if (skip_ime_ || !host_->has_input_method() || | 963 if (skip_ime_ || !host_->has_input_method() || |
| 939 (event->flags() & ui::EF_IS_SYNTHESIZED)) | 964 (event->flags() & ui::EF_IS_SYNTHESIZED)) |
| 940 return ui::EventDispatchDetails(); | 965 return ui::EventDispatchDetails(); |
| 941 host_->GetInputMethod()->DispatchKeyEvent(event); | 966 host_->GetInputMethod()->DispatchKeyEvent(event); |
| 942 event->StopPropagation(); | 967 event->StopPropagation(); |
| 943 return ui::EventDispatchDetails(); | 968 return ui::EventDispatchDetails(); |
| 944 } | 969 } |
| 945 | 970 |
| 946 } // namespace aura | 971 } // namespace aura |
| OLD | NEW |