Index: ash/wm/sticky_keys.cc |
diff --git a/ash/wm/sticky_keys.cc b/ash/wm/sticky_keys.cc |
deleted file mode 100644 |
index 9e2cc2a92de76c9cf80d06fed44f589dadbf21d9..0000000000000000000000000000000000000000 |
--- a/ash/wm/sticky_keys.cc |
+++ /dev/null |
@@ -1,445 +0,0 @@ |
-// Copyright 2013 The Chromium Authors. All rights reserved. |
-// Use of this source code is governed by a BSD-style license that can be |
-// found in the LICENSE file. |
- |
-#include "ash/wm/sticky_keys.h" |
- |
-#if defined(USE_X11) |
-#include <X11/extensions/XInput2.h> |
-#include <X11/Xlib.h> |
-#undef RootWindow |
-#endif |
- |
-#include "base/basictypes.h" |
-#include "base/debug/stack_trace.h" |
-#include "ui/aura/root_window.h" |
-#include "ui/aura/window.h" |
-#include "ui/aura/window_tracker.h" |
-#include "ui/events/event.h" |
-#include "ui/events/keycodes/keyboard_code_conversion.h" |
- |
-namespace ash { |
- |
-namespace { |
- |
-// Returns true if the type of mouse event should be modified by sticky keys. |
-bool ShouldModifyMouseEvent(ui::MouseEvent* event) { |
- ui::EventType type = event->type(); |
- return type == ui::ET_MOUSE_PRESSED || type == ui::ET_MOUSE_RELEASED || |
- type == ui::ET_MOUSEWHEEL; |
-} |
- |
-// An implementation of StickyKeysHandler::StickyKeysHandlerDelegate. |
-class StickyKeysHandlerDelegateImpl : |
- public StickyKeysHandler::StickyKeysHandlerDelegate { |
- public: |
- StickyKeysHandlerDelegateImpl(); |
- virtual ~StickyKeysHandlerDelegateImpl(); |
- |
- // StickyKeysHandlerDelegate overrides. |
- virtual void DispatchKeyEvent(ui::KeyEvent* event, |
- aura::Window* target) OVERRIDE; |
- |
- virtual void DispatchMouseEvent(ui::MouseEvent* event, |
- aura::Window* target) OVERRIDE; |
- |
- virtual void DispatchScrollEvent(ui::ScrollEvent* event, |
- aura::Window* target) OVERRIDE; |
- private: |
- DISALLOW_COPY_AND_ASSIGN(StickyKeysHandlerDelegateImpl); |
-}; |
- |
-StickyKeysHandlerDelegateImpl::StickyKeysHandlerDelegateImpl() { |
-} |
- |
-StickyKeysHandlerDelegateImpl::~StickyKeysHandlerDelegateImpl() { |
-} |
- |
-void StickyKeysHandlerDelegateImpl::DispatchKeyEvent(ui::KeyEvent* event, |
- aura::Window* target) { |
- DCHECK(target); |
- target->GetDispatcher()->AsRootWindowHostDelegate()->OnHostKeyEvent(event); |
-} |
- |
-void StickyKeysHandlerDelegateImpl::DispatchMouseEvent(ui::MouseEvent* event, |
- aura::Window* target) { |
- DCHECK(target); |
- // We need to send a new, untransformed mouse event to the host. |
- if (event->IsMouseWheelEvent()) { |
- ui::MouseWheelEvent new_event(*static_cast<ui::MouseWheelEvent*>(event)); |
- target->GetDispatcher()->AsRootWindowHostDelegate() |
- ->OnHostMouseEvent(&new_event); |
- } else { |
- ui::MouseEvent new_event(*event, target, target->GetRootWindow()); |
- target->GetDispatcher()->AsRootWindowHostDelegate() |
- ->OnHostMouseEvent(&new_event); |
- } |
-} |
- |
-void StickyKeysHandlerDelegateImpl::DispatchScrollEvent( |
- ui::ScrollEvent* event, |
- aura::Window* target) { |
- DCHECK(target); |
- target->GetDispatcher()->AsRootWindowHostDelegate() |
- ->OnHostScrollEvent(event); |
-} |
- |
-} // namespace |
- |
-/////////////////////////////////////////////////////////////////////////////// |
-// StickyKeys |
-StickyKeys::StickyKeys() |
- : enabled_(false), |
- shift_sticky_key_( |
- new StickyKeysHandler(ui::EF_SHIFT_DOWN, |
- new StickyKeysHandlerDelegateImpl())), |
- alt_sticky_key_( |
- new StickyKeysHandler(ui::EF_ALT_DOWN, |
- new StickyKeysHandlerDelegateImpl())), |
- ctrl_sticky_key_( |
- new StickyKeysHandler(ui::EF_CONTROL_DOWN, |
- new StickyKeysHandlerDelegateImpl())) { |
-} |
- |
-StickyKeys::~StickyKeys() { |
-} |
- |
-void StickyKeys::Enable(bool enabled) { |
- if (enabled_ != enabled) { |
- enabled_ = enabled; |
- |
- // Reset key handlers when activating sticky keys to ensure all |
- // the handlers' states are reset. |
- if (enabled_) { |
- shift_sticky_key_.reset( |
- new StickyKeysHandler(ui::EF_SHIFT_DOWN, |
- new StickyKeysHandlerDelegateImpl())); |
- alt_sticky_key_.reset( |
- new StickyKeysHandler(ui::EF_ALT_DOWN, |
- new StickyKeysHandlerDelegateImpl())); |
- ctrl_sticky_key_.reset( |
- new StickyKeysHandler(ui::EF_CONTROL_DOWN, |
- new StickyKeysHandlerDelegateImpl())); |
- } |
- } |
-} |
- |
-bool StickyKeys::HandleKeyEvent(ui::KeyEvent* event) { |
- return shift_sticky_key_->HandleKeyEvent(event) || |
- alt_sticky_key_->HandleKeyEvent(event) || |
- ctrl_sticky_key_->HandleKeyEvent(event); |
- return ctrl_sticky_key_->HandleKeyEvent(event); |
-} |
- |
-bool StickyKeys::HandleMouseEvent(ui::MouseEvent* event) { |
- return shift_sticky_key_->HandleMouseEvent(event) || |
- alt_sticky_key_->HandleMouseEvent(event) || |
- ctrl_sticky_key_->HandleMouseEvent(event); |
-} |
- |
-bool StickyKeys::HandleScrollEvent(ui::ScrollEvent* event) { |
- return shift_sticky_key_->HandleScrollEvent(event) || |
- alt_sticky_key_->HandleScrollEvent(event) || |
- ctrl_sticky_key_->HandleScrollEvent(event); |
-} |
- |
-void StickyKeys::OnKeyEvent(ui::KeyEvent* event) { |
- // Do not consume a translated key event which is generated by an IME. |
- if (event->type() == ui::ET_TRANSLATED_KEY_PRESS || |
- event->type() == ui::ET_TRANSLATED_KEY_RELEASE) { |
- return; |
- } |
- |
- if (enabled_ && HandleKeyEvent(event)) |
- event->StopPropagation(); |
-} |
- |
-void StickyKeys::OnMouseEvent(ui::MouseEvent* event) { |
- if (enabled_ && HandleMouseEvent(event)) |
- event->StopPropagation(); |
-} |
- |
-void StickyKeys::OnScrollEvent(ui::ScrollEvent* event) { |
- if (enabled_ && HandleScrollEvent(event)) |
- event->StopPropagation(); |
-} |
- |
-/////////////////////////////////////////////////////////////////////////////// |
-// StickyKeysHandler |
-StickyKeysHandler::StickyKeysHandler(ui::EventFlags target_modifier_flag, |
- StickyKeysHandlerDelegate* delegate) |
- : modifier_flag_(target_modifier_flag), |
- current_state_(DISABLED), |
- event_from_myself_(false), |
- preparing_to_enable_(false), |
- scroll_delta_(0), |
- delegate_(delegate) { |
-} |
- |
-StickyKeysHandler::~StickyKeysHandler() { |
-} |
- |
-StickyKeysHandler::StickyKeysHandlerDelegate::StickyKeysHandlerDelegate() { |
-} |
- |
-StickyKeysHandler::StickyKeysHandlerDelegate::~StickyKeysHandlerDelegate() { |
-} |
- |
-bool StickyKeysHandler::HandleKeyEvent(ui::KeyEvent* event) { |
- if (event_from_myself_) |
- return false; // Do not handle self-generated key event. |
- switch (current_state_) { |
- case DISABLED: |
- return HandleDisabledState(event); |
- case ENABLED: |
- return HandleEnabledState(event); |
- case LOCKED: |
- return HandleLockedState(event); |
- } |
- NOTREACHED(); |
- return false; |
-} |
- |
-bool StickyKeysHandler::HandleMouseEvent(ui::MouseEvent* event) { |
- preparing_to_enable_ = false; |
- if (event_from_myself_ || current_state_ == DISABLED |
- || !ShouldModifyMouseEvent(event)) { |
- return false; |
- } |
- DCHECK(current_state_ == ENABLED || current_state_ == LOCKED); |
- |
- AppendModifier(event); |
- // Only disable on the mouse released event in normal, non-locked mode. |
- if (current_state_ == ENABLED && event->type() != ui::ET_MOUSE_PRESSED) { |
- current_state_ = DISABLED; |
- DispatchEventAndReleaseModifier(event); |
- return true; |
- } |
- |
- return false; |
-} |
- |
-bool StickyKeysHandler::HandleScrollEvent(ui::ScrollEvent* event) { |
- preparing_to_enable_ = false; |
- if (event_from_myself_ || current_state_ == DISABLED) |
- return false; |
- DCHECK(current_state_ == ENABLED || current_state_ == LOCKED); |
- |
- // We detect a direction change if the current |scroll_delta_| is assigned |
- // and the offset of the current scroll event has the opposing sign. |
- bool direction_changed = false; |
- if (current_state_ == ENABLED && event->type() == ui::ET_SCROLL) { |
- int offset = event->y_offset(); |
- if (scroll_delta_) |
- direction_changed = offset * scroll_delta_ <= 0; |
- scroll_delta_ = offset; |
- } |
- |
- if (!direction_changed) |
- AppendModifier(event); |
- |
- // We want to modify all the scroll events in the scroll sequence, which ends |
- // with a fling start event. We also stop when the scroll sequence changes |
- // direction. |
- if (current_state_ == ENABLED && |
- (event->type() == ui::ET_SCROLL_FLING_START || direction_changed)) { |
- current_state_ = DISABLED; |
- scroll_delta_ = 0; |
- DispatchEventAndReleaseModifier(event); |
- return true; |
- } |
- |
- return false; |
-} |
- |
-StickyKeysHandler::KeyEventType |
- StickyKeysHandler::TranslateKeyEvent(ui::KeyEvent* event) { |
- bool is_target_key = false; |
- if (event->key_code() == ui::VKEY_SHIFT || |
- event->key_code() == ui::VKEY_LSHIFT || |
- event->key_code() == ui::VKEY_RSHIFT) { |
- is_target_key = (modifier_flag_ == ui::EF_SHIFT_DOWN); |
- } else if (event->key_code() == ui::VKEY_CONTROL || |
- event->key_code() == ui::VKEY_LCONTROL || |
- event->key_code() == ui::VKEY_RCONTROL) { |
- is_target_key = (modifier_flag_ == ui::EF_CONTROL_DOWN); |
- } else if (event->key_code() == ui::VKEY_MENU || |
- event->key_code() == ui::VKEY_LMENU || |
- event->key_code() == ui::VKEY_RMENU) { |
- is_target_key = (modifier_flag_ == ui::EF_ALT_DOWN); |
- } else { |
- return event->type() == ui::ET_KEY_PRESSED ? |
- NORMAL_KEY_DOWN : NORMAL_KEY_UP; |
- } |
- |
- if (is_target_key) { |
- return event->type() == ui::ET_KEY_PRESSED ? |
- TARGET_MODIFIER_DOWN : TARGET_MODIFIER_UP; |
- } |
- return event->type() == ui::ET_KEY_PRESSED ? |
- OTHER_MODIFIER_DOWN : OTHER_MODIFIER_UP; |
-} |
- |
-bool StickyKeysHandler::HandleDisabledState(ui::KeyEvent* event) { |
- switch (TranslateKeyEvent(event)) { |
- case TARGET_MODIFIER_UP: |
- if (preparing_to_enable_) { |
- preparing_to_enable_ = false; |
- scroll_delta_ = 0; |
- current_state_ = ENABLED; |
- modifier_up_event_.reset(new ui::KeyEvent(*event)); |
- return true; |
- } |
- return false; |
- case TARGET_MODIFIER_DOWN: |
- preparing_to_enable_ = true; |
- return false; |
- case NORMAL_KEY_DOWN: |
- preparing_to_enable_ = false; |
- return false; |
- case NORMAL_KEY_UP: |
- case OTHER_MODIFIER_DOWN: |
- case OTHER_MODIFIER_UP: |
- return false; |
- } |
- NOTREACHED(); |
- return false; |
-} |
- |
-bool StickyKeysHandler::HandleEnabledState(ui::KeyEvent* event) { |
- switch (TranslateKeyEvent(event)) { |
- case NORMAL_KEY_UP: |
- case TARGET_MODIFIER_DOWN: |
- return true; |
- case TARGET_MODIFIER_UP: |
- current_state_ = LOCKED; |
- modifier_up_event_.reset(); |
- return true; |
- case NORMAL_KEY_DOWN: { |
- current_state_ = DISABLED; |
- AppendModifier(event); |
- DispatchEventAndReleaseModifier(event); |
- return true; |
- } |
- case OTHER_MODIFIER_DOWN: |
- case OTHER_MODIFIER_UP: |
- return false; |
- } |
- NOTREACHED(); |
- return false; |
-} |
- |
-bool StickyKeysHandler::HandleLockedState(ui::KeyEvent* event) { |
- switch (TranslateKeyEvent(event)) { |
- case TARGET_MODIFIER_DOWN: |
- return true; |
- case TARGET_MODIFIER_UP: |
- current_state_ = DISABLED; |
- return false; |
- case NORMAL_KEY_DOWN: |
- case NORMAL_KEY_UP: |
- AppendModifier(event); |
- return false; |
- case OTHER_MODIFIER_DOWN: |
- case OTHER_MODIFIER_UP: |
- return false; |
- } |
- NOTREACHED(); |
- return false; |
-} |
- |
-void StickyKeysHandler::DispatchEventAndReleaseModifier(ui::Event* event) { |
- DCHECK(event->IsKeyEvent() || |
- event->IsMouseEvent() || |
- event->IsScrollEvent()); |
- DCHECK(modifier_up_event_.get()); |
- aura::Window* target = static_cast<aura::Window*>(event->target()); |
- DCHECK(target); |
- aura::Window* root_window = target->GetRootWindow(); |
- DCHECK(root_window); |
- |
- aura::WindowTracker window_tracker; |
- window_tracker.Add(target); |
- |
- event_from_myself_ = true; |
- if (event->IsKeyEvent()) { |
- delegate_->DispatchKeyEvent(static_cast<ui::KeyEvent*>(event), target); |
- } else if (event->IsMouseEvent()) { |
- delegate_->DispatchMouseEvent(static_cast<ui::MouseEvent*>(event), target); |
- } else { |
- delegate_->DispatchScrollEvent( |
- static_cast<ui::ScrollEvent*>(event), target); |
- } |
- |
- // The action triggered above may have destroyed the event target, in which |
- // case we will dispatch the modifier up event to the root window instead. |
- aura::Window* modifier_up_target = |
- window_tracker.Contains(target) ? target : root_window; |
- delegate_->DispatchKeyEvent(modifier_up_event_.get(), modifier_up_target); |
- event_from_myself_ = false; |
-} |
- |
-void StickyKeysHandler::AppendNativeEventMask(unsigned int* state) { |
- unsigned int& state_ref = *state; |
- switch (modifier_flag_) { |
- case ui::EF_CONTROL_DOWN: |
- state_ref |= ControlMask; |
- break; |
- case ui::EF_ALT_DOWN: |
- state_ref |= Mod1Mask; |
- break; |
- case ui::EF_SHIFT_DOWN: |
- state_ref |= ShiftMask; |
- break; |
- default: |
- NOTREACHED(); |
- } |
-} |
- |
-void StickyKeysHandler::AppendModifier(ui::KeyEvent* event) { |
-#if defined(USE_X11) |
- XEvent* xev = event->native_event(); |
- if (xev) { |
- XKeyEvent* xkey = &(xev->xkey); |
- AppendNativeEventMask(&xkey->state); |
- } |
-#elif defined(USE_OZONE) |
- NOTIMPLEMENTED() << "Modifier key is not handled"; |
-#endif |
- event->set_flags(event->flags() | modifier_flag_); |
- event->set_character(ui::GetCharacterFromKeyCode(event->key_code(), |
- event->flags())); |
- event->NormalizeFlags(); |
-} |
- |
-void StickyKeysHandler::AppendModifier(ui::MouseEvent* event) { |
-#if defined(USE_X11) |
- XEvent* xev = event->native_event(); |
- if (xev) { |
- XButtonEvent* xkey = &(xev->xbutton); |
- AppendNativeEventMask(&xkey->state); |
- } |
-#elif defined(USE_OZONE) |
- NOTIMPLEMENTED() << "Modifier key is not handled"; |
-#endif |
- event->set_flags(event->flags() | modifier_flag_); |
-} |
- |
-void StickyKeysHandler::AppendModifier(ui::ScrollEvent* event) { |
-#if defined(USE_X11) |
- XEvent* xev = event->native_event(); |
- if (xev) { |
- XIDeviceEvent* xievent = |
- static_cast<XIDeviceEvent*>(xev->xcookie.data); |
- if (xievent) { |
- AppendNativeEventMask(reinterpret_cast<unsigned int*>( |
- &xievent->mods.effective)); |
- } |
- } |
-#elif defined(USE_OZONE) |
- NOTIMPLEMENTED() << "Modifier key is not handled"; |
-#endif |
- event->set_flags(event->flags() | modifier_flag_); |
-} |
- |
-} // namespace ash |