diff options
-rw-r--r-- | ash/ash.gyp | 3 | ||||
-rw-r--r-- | ash/ash_touch_exploration_manager_chromeos.cc | 78 | ||||
-rw-r--r-- | ash/ash_touch_exploration_manager_chromeos.h | 52 | ||||
-rw-r--r-- | ash/ash_touch_exploration_manager_chromeos_unittest.cc | 39 | ||||
-rw-r--r-- | ash/root_window_controller.cc | 56 | ||||
-rw-r--r-- | ash/root_window_controller.h | 4 | ||||
-rw-r--r-- | chrome/browser/ui/ash/volume_controller_chromeos.cc | 2 | ||||
-rw-r--r-- | chromeos/audio/cras_audio_handler.cc | 2 | ||||
-rw-r--r-- | chromeos/audio/cras_audio_handler.h | 2 | ||||
-rw-r--r-- | ui/chromeos/touch_exploration_controller.cc | 189 | ||||
-rw-r--r-- | ui/chromeos/touch_exploration_controller.h | 93 | ||||
-rw-r--r-- | ui/chromeos/touch_exploration_controller_unittest.cc | 254 |
12 files changed, 73 insertions, 701 deletions
diff --git a/ash/ash.gyp b/ash/ash.gyp index 554564a..1f1e85f 100644 --- a/ash/ash.gyp +++ b/ash/ash.gyp @@ -42,8 +42,6 @@ 'ash_constants.h', 'ash_switches.cc', 'ash_switches.h', - 'ash_touch_exploration_manager_chromeos.cc', - 'ash_touch_exploration_manager_chromeos.h', 'cancel_mode.cc', 'cancel_mode.h', 'debug.cc', @@ -755,7 +753,6 @@ 'accelerators/accelerator_table_unittest.cc', 'accelerators/magnifier_key_scroller_unittest.cc', 'accelerators/spoken_feedback_toggler_unittest.cc', - 'ash_touch_exploration_manager_chromeos_unittest.cc', 'autoclick/autoclick_unittest.cc', 'desktop_background/desktop_background_controller_unittest.cc', 'desktop_background/wallpaper_resizer_unittest.cc', diff --git a/ash/ash_touch_exploration_manager_chromeos.cc b/ash/ash_touch_exploration_manager_chromeos.cc deleted file mode 100644 index f5e212b..0000000 --- a/ash/ash_touch_exploration_manager_chromeos.cc +++ /dev/null @@ -1,78 +0,0 @@ -// Copyright 2014 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/ash_touch_exploration_manager_chromeos.h" - -#include "ash/accessibility_delegate.h" -#include "ash/audio/sounds.h" -#include "ash/root_window_controller.h" -#include "ash/shell.h" -#include "ash/system/tray/system_tray_notifier.h" -#include "base/command_line.h" -#include "chromeos/audio/chromeos_sounds.h" -#include "chromeos/audio/cras_audio_handler.h" -#include "chromeos/chromeos_switches.h" -#include "ui/chromeos/touch_exploration_controller.h" - -namespace ash { - -AshTouchExplorationManager::AshTouchExplorationManager( - RootWindowController* root_window_controller) - : root_window_controller_(root_window_controller), - audio_handler_(chromeos::CrasAudioHandler::Get()) { - Shell::GetInstance()->system_tray_notifier()->AddAccessibilityObserver(this); - UpdateTouchExplorationState(); -} - -AshTouchExplorationManager::~AshTouchExplorationManager() { - SystemTrayNotifier* system_tray_notifier = - Shell::GetInstance()->system_tray_notifier(); - if (system_tray_notifier) - system_tray_notifier->RemoveAccessibilityObserver(this); -} - -void AshTouchExplorationManager::OnAccessibilityModeChanged( - AccessibilityNotificationVisibility notify) { - UpdateTouchExplorationState(); -} - -void AshTouchExplorationManager::PlayVolumeAdjustSound() { - if (!VolumeAdjustSoundEnabled()) - return; - if ((!audio_handler_->IsOutputMuted()) || - !(audio_handler_->GetOutputVolumePercent() == 100)) - PlaySystemSoundIfSpokenFeedback(chromeos::SOUND_VOLUME_ADJUST); -} - -void AshTouchExplorationManager::SetOutputLevel(int volume) { - if (volume > 0) { - if (audio_handler_->IsOutputMuted()) { - audio_handler_->SetOutputMute(false); - } - } - audio_handler_->SetOutputVolumePercent(volume); - // Avoid negative volume. - if (audio_handler_->IsOutputVolumeBelowDefaultMuteLevel()) - audio_handler_->SetOutputMute(true); -} - -void AshTouchExplorationManager::UpdateTouchExplorationState() { - AccessibilityDelegate* delegate = - Shell::GetInstance()->accessibility_delegate(); - bool enabled = delegate->IsSpokenFeedbackEnabled(); - - if (enabled && !touch_exploration_controller_.get()) { - touch_exploration_controller_.reset(new ui::TouchExplorationController( - root_window_controller_->GetRootWindow(), this)); - } else if (!enabled) { - touch_exploration_controller_.reset(); - } -} - -bool AshTouchExplorationManager::VolumeAdjustSoundEnabled() { - return !CommandLine::ForCurrentProcess()->HasSwitch( - chromeos::switches::kDisableVolumeAdjustSound); -} - -} // namespace ash diff --git a/ash/ash_touch_exploration_manager_chromeos.h b/ash/ash_touch_exploration_manager_chromeos.h deleted file mode 100644 index fc9cbc1..0000000 --- a/ash/ash_touch_exploration_manager_chromeos.h +++ /dev/null @@ -1,52 +0,0 @@ -// Copyright 2014 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. - -#ifndef ASH_TOUCH_EXPLORATION_MANAGER_CHROMEOS_H_ -#define ASH_TOUCH_EXPLORATION_MANAGER_CHROMEOS_H_ - -#include "ash/ash_export.h" -#include "ash/system/tray_accessibility.h" -#include "ui/chromeos/touch_exploration_controller.h" - -namespace chromeos { -class CrasAudioHandler; -} - -namespace ash { -class RootWindowController; - -// Responsible for initializing TouchExplorationController when spoken -// feedback is on for ChromeOS only. This class implements -// TouchExplorationControllerDelegate which allows touch gestures to manipulate -// the system. -class ASH_EXPORT AshTouchExplorationManager - : public ash::AccessibilityObserver, - public ui::TouchExplorationControllerDelegate { - public: - explicit AshTouchExplorationManager( - RootWindowController* root_window_controller); - virtual ~AshTouchExplorationManager(); - - // AccessibilityObserver overrides: - virtual void OnAccessibilityModeChanged( - AccessibilityNotificationVisibility notify) OVERRIDE; - - // TouchExplorationControllerDelegate overrides: - virtual void PlayVolumeAdjustSound() OVERRIDE; - virtual void SetOutputLevel(int volume) OVERRIDE; - - private: - void UpdateTouchExplorationState(); - bool VolumeAdjustSoundEnabled(); - - scoped_ptr<ui::TouchExplorationController> touch_exploration_controller_; - RootWindowController* root_window_controller_; - chromeos::CrasAudioHandler* audio_handler_; - - DISALLOW_COPY_AND_ASSIGN(AshTouchExplorationManager); -}; - -} // namespace ash - -#endif // ASH_TOUCH_EXPLORATION_MANAGER_CHROMEOS_H_ diff --git a/ash/ash_touch_exploration_manager_chromeos_unittest.cc b/ash/ash_touch_exploration_manager_chromeos_unittest.cc deleted file mode 100644 index 4262cbf..0000000 --- a/ash/ash_touch_exploration_manager_chromeos_unittest.cc +++ /dev/null @@ -1,39 +0,0 @@ -// Copyright 2014 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/ash_touch_exploration_manager_chromeos.h" - -#include "ash/root_window_controller.h" -#include "ash/shell.h" -#include "ash/test/ash_test_base.h" -#include "chromeos/audio/cras_audio_handler.h" - -namespace ash { - -typedef test::AshTestBase AshTouchExplorationManagerTest; - -TEST_F(AshTouchExplorationManagerTest, AdjustSound) { - RootWindowController* controller = Shell::GetPrimaryRootWindowController(); - AshTouchExplorationManager touch_exploration_manager(controller); - chromeos::CrasAudioHandler* audio_handler = - chromeos::CrasAudioHandler::Get(); - - touch_exploration_manager.SetOutputLevel(10); - EXPECT_EQ(audio_handler->GetOutputVolumePercent(), 10); - EXPECT_FALSE(audio_handler->IsOutputMuted()); - - touch_exploration_manager.SetOutputLevel(100); - EXPECT_EQ(audio_handler->GetOutputVolumePercent(), 100); - EXPECT_FALSE(audio_handler->IsOutputMuted()); - - touch_exploration_manager.SetOutputLevel(0); - EXPECT_EQ(audio_handler->GetOutputVolumePercent(), 0); - EXPECT_TRUE(audio_handler->IsOutputMuted()); - - touch_exploration_manager.SetOutputLevel(-10); - EXPECT_EQ(audio_handler->GetOutputVolumePercent(), 0); - EXPECT_TRUE(audio_handler->IsOutputMuted()); -} - -} // namespace ash diff --git a/ash/root_window_controller.cc b/ash/root_window_controller.cc index 0e07dbe..26b925c0 100644 --- a/ash/root_window_controller.cc +++ b/ash/root_window_controller.cc @@ -76,7 +76,7 @@ #include "ui/wm/public/window_types.h" #if defined(OS_CHROMEOS) -#include "ash/ash_touch_exploration_manager_chromeos.h" +#include "ash/system/tray_accessibility.h" #include "ash/wm/boot_splash_screen_chromeos.h" #include "ui/chromeos/touch_exploration_controller.h" #endif @@ -261,6 +261,54 @@ class EmptyWindowDelegate : public aura::WindowDelegate { DISALLOW_COPY_AND_ASSIGN(EmptyWindowDelegate); }; +#if defined(OS_CHROMEOS) +// Responsible for initializing TouchExplorationController when spoken +// feedback is on. +class CrosAccessibilityObserver : public AccessibilityObserver { + public: + explicit CrosAccessibilityObserver( + RootWindowController* root_window_controller) + : root_window_controller_(root_window_controller) { + Shell::GetInstance()->system_tray_notifier()-> + AddAccessibilityObserver(this); + UpdateTouchExplorationState(); + } + + virtual ~CrosAccessibilityObserver() { + SystemTrayNotifier* system_tray_notifier = + Shell::GetInstance()->system_tray_notifier(); + if (system_tray_notifier) + system_tray_notifier->RemoveAccessibilityObserver(this); + } + + private: + void UpdateTouchExplorationState() { + AccessibilityDelegate* delegate = + Shell::GetInstance()->accessibility_delegate(); + bool enabled = delegate->IsSpokenFeedbackEnabled(); + + if (enabled && !touch_exploration_controller_.get()) { + touch_exploration_controller_.reset( + new ui::TouchExplorationController( + root_window_controller_->GetRootWindow())); + } else if (!enabled) { + touch_exploration_controller_.reset(); + } + } + + // Overridden from AccessibilityObserver. + virtual void OnAccessibilityModeChanged( + AccessibilityNotificationVisibility notify) OVERRIDE { + UpdateTouchExplorationState(); + } + + scoped_ptr<ui::TouchExplorationController> touch_exploration_controller_; + RootWindowController* root_window_controller_; + + DISALLOW_COPY_AND_ASSIGN(CrosAccessibilityObserver); +}; +#endif // OS_CHROMEOS + } // namespace void RootWindowController::CreateForPrimaryDisplay(AshWindowTreeHost* host) { @@ -348,8 +396,8 @@ void RootWindowController::Shutdown() { shell->RemoveShellObserver(this); #if defined(OS_CHROMEOS) - if (touch_exploration_manager_) { - touch_exploration_manager_.reset(); + if (cros_accessibility_observer_) { + cros_accessibility_observer_.reset(); } #endif @@ -759,7 +807,7 @@ void RootWindowController::Init(RootWindowType root_window_type, #if defined(OS_CHROMEOS) if (!CommandLine::ForCurrentProcess()->HasSwitch( switches::kAshDisableTouchExplorationMode)) { - touch_exploration_manager_.reset(new AshTouchExplorationManager(this)); + cros_accessibility_observer_.reset(new CrosAccessibilityObserver(this)); } #endif } diff --git a/ash/root_window_controller.h b/ash/root_window_controller.h index 014aadc..5c91f56 100644 --- a/ash/root_window_controller.h +++ b/ash/root_window_controller.h @@ -68,7 +68,7 @@ class WorkspaceController; #if defined(OS_CHROMEOS) class BootSplashScreen; -class AshTouchExplorationManager; +class AccessibilityObserver; #endif // This class maintains the per root window state for ash. This class @@ -298,7 +298,7 @@ class ASH_EXPORT RootWindowController : public ShellObserver { scoped_ptr<BootSplashScreen> boot_splash_screen_; // Responsible for initializing TouchExplorationController when spoken // feedback is on. - scoped_ptr<AshTouchExplorationManager> touch_exploration_manager_; + scoped_ptr<AccessibilityObserver> cros_accessibility_observer_; #endif scoped_ptr<ScreenDimmer> screen_dimmer_; diff --git a/chrome/browser/ui/ash/volume_controller_chromeos.cc b/chrome/browser/ui/ash/volume_controller_chromeos.cc index 10a4114..8acade0 100644 --- a/chrome/browser/ui/ash/volume_controller_chromeos.cc +++ b/chrome/browser/ui/ash/volume_controller_chromeos.cc @@ -67,7 +67,7 @@ bool VolumeController::HandleVolumeDown(const ui::Accelerator& accelerator) { audio_handler->SetOutputVolumePercent(0); } else { audio_handler->AdjustOutputVolumeByPercent(-kStepPercentage); - if (audio_handler->IsOutputVolumeBelowDefaultMuteLevel()) + if (audio_handler->IsOutputVolumeBelowDefaultMuteLvel()) audio_handler->SetOutputMute(true); else PlayVolumeAdjustSound(); diff --git a/chromeos/audio/cras_audio_handler.cc b/chromeos/audio/cras_audio_handler.cc index 1714b85..16805d6 100644 --- a/chromeos/audio/cras_audio_handler.cc +++ b/chromeos/audio/cras_audio_handler.cc @@ -116,7 +116,7 @@ bool CrasAudioHandler::IsOutputMutedForDevice(uint64 device_id) { return audio_pref_handler_->GetMuteValue(*device); } -bool CrasAudioHandler::IsOutputVolumeBelowDefaultMuteLevel() { +bool CrasAudioHandler::IsOutputVolumeBelowDefaultMuteLvel() { return output_volume_ <= kMuteThresholdPercent; } diff --git a/chromeos/audio/cras_audio_handler.h b/chromeos/audio/cras_audio_handler.h index fe4cee2..cc28c50 100644 --- a/chromeos/audio/cras_audio_handler.h +++ b/chromeos/audio/cras_audio_handler.h @@ -97,7 +97,7 @@ class CHROMEOS_EXPORT CrasAudioHandler : public CrasAudioClient::Observer, virtual bool IsInputMutedForDevice(uint64 device_id); // Returns true if the output volume is below the default mute volume level. - virtual bool IsOutputVolumeBelowDefaultMuteLevel(); + virtual bool IsOutputVolumeBelowDefaultMuteLvel(); // Returns volume level in 0-100% range at which the volume should be muted. virtual int GetOutputDefaultVolumeMuteThreshold(); diff --git a/ui/chromeos/touch_exploration_controller.cc b/ui/chromeos/touch_exploration_controller.cc index 6bc08c7..1a3b8fa 100644 --- a/ui/chromeos/touch_exploration_controller.cc +++ b/ui/chromeos/touch_exploration_controller.cc @@ -4,6 +4,7 @@ #include "ui/chromeos/touch_exploration_controller.h" +#include "base/logging.h" #include "base/strings/string_number_conversions.h" #include "ui/aura/client/cursor_client.h" #include "ui/aura/window.h" @@ -11,7 +12,6 @@ #include "ui/aura/window_tree_host.h" #include "ui/events/event.h" #include "ui/events/event_processor.h" -#include "ui/gfx/geometry/rect.h" #define VLOG_STATE() if (VLOG_IS_ON(0)) VlogState(__func__) #define VLOG_EVENT(event) if (VLOG_IS_ON(0)) VlogEvent(event, __func__) @@ -19,19 +19,13 @@ namespace ui { namespace { - -// Delay between adjustment sounds. -const base::TimeDelta kSoundDelay = base::TimeDelta::FromMilliseconds(150); - // In ChromeOS, VKEY_LWIN is synonymous for the search key. const ui::KeyboardCode kChromeOSSearchKey = ui::VKEY_LWIN; } // namespace TouchExplorationController::TouchExplorationController( - aura::Window* root_window, - TouchExplorationControllerDelegate* delegate) + aura::Window* root_window) : root_window_(root_window), - delegate_(delegate), state_(NO_FINGERS_DOWN), event_handler_for_testing_(NULL), gesture_provider_(this), @@ -83,15 +77,6 @@ ui::EventRewriteStatus TouchExplorationController::RewriteEvent( current_touch_ids_.push_back(touch_id); touch_locations_.insert(std::pair<int, gfx::PointF>(touch_id, location)); } else if (type == ui::ET_TOUCH_RELEASED || type == ui::ET_TOUCH_CANCELLED) { - // In order to avoid accidentally double tapping when moving off the edge of - // the screen, the state will be rewritten to NoFingersDown. - TouchEvent touch_event = static_cast<const TouchEvent&>(event); - if (FindEdgesWithinBounds(touch_event.location(), kLeavingScreenEdge) != - NO_EDGE) { - if (current_touch_ids_.size() == 0) - ResetToNoFingersDown(); - } - std::vector<int>::iterator it = std::find( current_touch_ids_.begin(), current_touch_ids_.end(), touch_id); @@ -136,8 +121,6 @@ ui::EventRewriteStatus TouchExplorationController::RewriteEvent( return InPassthrough(touch_event, rewritten_event); case WAIT_FOR_RELEASE: return InWaitForRelease(touch_event, rewritten_event); - case SLIDE_GESTURE: - return InSlideGesture(touch_event, rewritten_event); } NOTREACHED(); return ui::EVENT_REWRITE_CONTINUE; @@ -208,14 +191,6 @@ ui::EventRewriteStatus TouchExplorationController::InSingleTapPressed( << "\n Minimum swipe velocity: " << gesture_detector_config_.minimum_swipe_velocity; - // Change to slide gesture if the slide occurred at the right edge. - int edge = FindEdgesWithinBounds(event.location(), kMaxDistanceFromEdge); - if (edge & RIGHT_EDGE) { - state_ = SLIDE_GESTURE; - VLOG_STATE(); - return InSlideGesture(event, rewritten_event); - } - // If the user moves fast enough from the initial touch location, start // gesture detection. Otherwise, jump to the touch exploration mode early. if (velocity > gesture_detector_config_.minimum_swipe_velocity) { @@ -522,69 +497,6 @@ ui::EventRewriteStatus TouchExplorationController::InWaitForRelease( return EVENT_REWRITE_DISCARD; } -void TouchExplorationController::PlaySoundForTimer() { - delegate_->PlayVolumeAdjustSound(); -} - -ui::EventRewriteStatus TouchExplorationController::InSlideGesture( - const ui::TouchEvent& event, - scoped_ptr<ui::Event>* rewritten_event) { - // The timer should not fire when sliding. - if (tap_timer_.IsRunning()) - tap_timer_.Stop(); - - ui::EventType type = event.type(); - // If additional fingers are added before a swipe gesture has been registered, - // then wait until all fingers have been lifted. - if (type == ui::ET_TOUCH_PRESSED || - event.touch_id() != initial_press_->touch_id()) { - if (sound_timer_.IsRunning()) - sound_timer_.Stop(); - // Discard any pending gestures. - ignore_result(gesture_provider_.GetAndResetPendingGestures()); - state_ = WAIT_FOR_RELEASE; - return EVENT_REWRITE_DISCARD; - } - - // Allows user to return to the edge to adjust the sound if they have left the - // boundaries. - int edge = FindEdgesWithinBounds(event.location(), kSlopDistanceFromEdge); - if (!(edge & RIGHT_EDGE) && (type != ui::ET_TOUCH_RELEASED)) { - if (sound_timer_.IsRunning()) { - sound_timer_.Stop(); - } - return EVENT_REWRITE_DISCARD; - } - - // This can occur if the user leaves the screen edge and then returns to it to - // continue adjusting the sound. - if (!sound_timer_.IsRunning()) { - sound_timer_.Start(FROM_HERE, - kSoundDelay, - this, - &ui::TouchExplorationController::PlaySoundForTimer); - delegate_->PlayVolumeAdjustSound(); - } - - // There should not be more than one finger down. - DCHECK(current_touch_ids_.size() <= 1); - if (type == ui::ET_TOUCH_MOVED) { - gesture_provider_.OnTouchEvent(event); - gesture_provider_.OnTouchEventAck(false); - } - if (type == ui::ET_TOUCH_RELEASED || type == ui::ET_TOUCH_CANCELLED) { - gesture_provider_.OnTouchEvent(event); - gesture_provider_.OnTouchEventAck(false); - ignore_result(gesture_provider_.GetAndResetPendingGestures()); - if (current_touch_ids_.size() == 0) - ResetToNoFingersDown(); - return ui::EVENT_REWRITE_DISCARD; - } - - ProcessGestureEvents(); - return ui::EVENT_REWRITE_DISCARD; -} - void TouchExplorationController::OnTapTimerFired() { switch (state_) { case SINGLE_TAP_RELEASED: @@ -609,7 +521,7 @@ void TouchExplorationController::OnTapTimerFired() { CreateMouseMoveEvent(initial_press_->location(), initial_press_->flags()); DispatchEvent(mouse_move.get()); last_touch_exploration_.reset(new TouchEvent(*initial_press_)); -} + } void TouchExplorationController::DispatchEvent(ui::Event* event) { if (event_handler_for_testing_) { @@ -620,14 +532,12 @@ void TouchExplorationController::DispatchEvent(ui::Event* event) { root_window_->GetHost()->dispatcher()->OnEventFromSource(event); } -void TouchExplorationController::OnGestureEvent( - ui::GestureEvent* gesture) { +void TouchExplorationController::OnGestureEvent(ui::GestureEvent* gesture) { CHECK(gesture->IsGestureEvent()); - ui::EventType type = gesture->type(); VLOG(0) << " \n Gesture Triggered: " << gesture->name(); - if (type == ui::ET_GESTURE_SWIPE && state_ != SLIDE_GESTURE) { - VLOG(0) << "Swipe!"; - ignore_result(gesture_provider_.GetAndResetPendingGestures()); + if (gesture->type() == ui::ET_GESTURE_SWIPE) { + if (tap_timer_.IsRunning()) + tap_timer_.Stop(); OnSwipeEvent(gesture); return; } @@ -640,61 +550,11 @@ void TouchExplorationController::ProcessGestureEvents() { for (ScopedVector<GestureEvent>::iterator i = gestures->begin(); i != gestures->end(); ++i) { - if (state_ == SLIDE_GESTURE) - SideSlideControl(*i); - else - OnGestureEvent(*i); + OnGestureEvent(*i); } } } -void TouchExplorationController::SideSlideControl(ui::GestureEvent* gesture) { - ui::EventType type = gesture->type(); - if (!gesture->IsScrollGestureEvent()) - return; - - if (type == ET_GESTURE_SCROLL_BEGIN) { - delegate_->PlayVolumeAdjustSound(); - } - - if (type == ET_GESTURE_SCROLL_END) { - if (sound_timer_.IsRunning()) - sound_timer_.Stop(); - delegate_->PlayVolumeAdjustSound(); - } - - // If the user is in the corner of the right side of the screen, the volume - // will be automatically set to 100% or muted depending on which corner they - // are in. Otherwise, the user will be able to adjust the volume by sliding - // their finger along the right side of the screen. Volume is relative to - // where they are on the right side of the screen. - gfx::Point location = gesture->location(); - int edge = FindEdgesWithinBounds(location, kSlopDistanceFromEdge); - if (!(edge & RIGHT_EDGE)) - return; - - if (edge & TOP_EDGE) { - delegate_->SetOutputLevel(100); - return; - } - if (edge & BOTTOM_EDGE) { - delegate_->SetOutputLevel(0); - return; - } - - location = gesture->location(); - root_window_->GetHost()->ConvertPointFromNativeScreen(&location); - float volume_adjust_height = - root_window_->bounds().height() - 2 * kMaxDistanceFromEdge; - float ratio = (location.y() - kMaxDistanceFromEdge) / volume_adjust_height; - float volume = 100 - 100 * ratio; - VLOG(0) << "\n Volume = " << volume << "\n Location = " << location.ToString() - << "\n Bounds = " << root_window_->bounds().right(); - - delegate_->SetOutputLevel(int(volume)); -} - - void TouchExplorationController::OnSwipeEvent(ui::GestureEvent* swipe_gesture) { // A swipe gesture contains details for the direction in which the swipe // occurred. @@ -714,34 +574,6 @@ void TouchExplorationController::OnSwipeEvent(ui::GestureEvent* swipe_gesture) { } } -int TouchExplorationController::FindEdgesWithinBounds(gfx::Point point, - float bounds) { - // Since GetBoundsInScreen is in DIPs but point is not, then point needs to be - // converted. - root_window_->GetHost()->ConvertPointFromNativeScreen(&point); - gfx::Rect window = root_window_->GetBoundsInScreen(); - - float left_edge_limit = window.x() + bounds; - float right_edge_limit = window.right() - bounds; - float top_edge_limit = window.y() + bounds; - float bottom_edge_limit = window.bottom() - bounds; - - // Bitwise manipulation in order to determine where on the screen the point - // lies. If more than one bit is turned on, then it is a corner where the two - // bit/edges intersect. Otherwise, if no bits are turned on, the point must be - // in the center of the screen. - int result = NO_EDGE; - if (point.x() < left_edge_limit) - result |= LEFT_EDGE; - if (point.x() > right_edge_limit) - result |= RIGHT_EDGE; - if (point.y() < top_edge_limit) - result |= TOP_EDGE; - if (point.y() > bottom_edge_limit) - result |= BOTTOM_EDGE; - return result; -} - void TouchExplorationController::DispatchShiftSearchKeyEvent( const ui::KeyboardCode direction) { // In order to activate the shortcut shift+search+<arrow key> @@ -791,9 +623,6 @@ void TouchExplorationController::EnterTouchToMouseMode() { } void TouchExplorationController::ResetToNoFingersDown() { - ProcessGestureEvents(); - if (sound_timer_.IsRunning()) - sound_timer_.Stop(); state_ = NO_FINGERS_DOWN; VLOG_STATE(); if (tap_timer_.IsRunning()) @@ -865,8 +694,6 @@ const char* TouchExplorationController::EnumStateToString(State state) { return "PASSTHROUGH"; case WAIT_FOR_RELEASE: return "WAIT_FOR_RELEASE"; - case SLIDE_GESTURE: - return "SLIDE_GESTURE"; } return "Not a state"; } diff --git a/ui/chromeos/touch_exploration_controller.h b/ui/chromeos/touch_exploration_controller.h index 12f0bfa..17731ff 100644 --- a/ui/chromeos/touch_exploration_controller.h +++ b/ui/chromeos/touch_exploration_controller.h @@ -26,25 +26,9 @@ class GestureEvent; class GestureProviderAura; class TouchEvent; -// A delegate to handle commands in response to detected accessibility gesture -// events. -class TouchExplorationControllerDelegate { - public: - virtual ~TouchExplorationControllerDelegate() {} - - // This function should be called whenever the delegate wants to play a sound - // when the volume adjusts. - virtual void PlayVolumeAdjustSound() = 0; - - // Takes an int from 0.0 to 100.0 that indicates the percent the volume - // should be set to. - virtual void SetOutputLevel(int volume) = 0; -}; - // TouchExplorationController is used in tandem with "Spoken Feedback" to -// make the touch UI accessible. Gestures performed in the middle of the screen -// are mapped to accessiblity key shortcuts while gestures performed on the edge -// of the screen can change settings. +// make the touch UI accessible. Gestures are mapped to accessiblity key +// shortcuts. // // ** Short version ** // @@ -56,10 +40,7 @@ class TouchExplorationControllerDelegate { // right would correspond to the keyboard short cut shift+search+right. // When two or more fingers are pressed initially, from then on the events // are passed through, but with the initial finger removed - so if you swipe -// down with two fingers, the running app will see a one-finger swipe. Slide -// gestures performed on the edge of the screen can change settings -// continuously. For example, sliding a finger along the right side of the -// screen will change the volume. +// down with two fingers, the running app will see a one-finger swipe. // // ** Long version ** // @@ -110,24 +91,6 @@ class TouchExplorationControllerDelegate { // adds a third finger while in two to one finger mode, all fingers and touch // events are passed through from then on. // -// If the user places a finger on the edge of the screen and moves their finger -// past slop, a slide gesture is performed. The user can then slide one finger -// along an edge of the screen and continuously control a setting. Once the user -// enters this state, the boundaries that define an edge expand so that the user -// can now adjust the setting within a slightly bigger width along the screen. -// If the user exits this area without lifting their finger, they will not be -// able to perform any actions, however if they keep their finger down and -// return to the "hot edge," then they can still adjust the setting. In order to -// perform other touch accessibility movements, the user must lift their finger. -// If additional fingers are added while in this state, the user will transition -// to passthrough. -// -// Currently, only the right edge is mapped to control the volume. Volume -// control along the edge of the screen is directly proportional to where the -// user's finger is located on the screen. The top right corner of the screen -// automatically sets the volume to 100% and the bottome right corner of the -// screen automatically sets the volume to 0% once the user has moved past slop. -// // Once touch exploration mode has been activated, // it remains in that mode until all fingers have been released. // @@ -137,9 +100,7 @@ class UI_CHROMEOS_EXPORT TouchExplorationController : public ui::EventRewriter, public ui::GestureProviderAuraClient { public: - explicit TouchExplorationController( - aura::Window* root_window, - ui::TouchExplorationControllerDelegate* delegate); + explicit TouchExplorationController(aura::Window* root_window); virtual ~TouchExplorationController(); private: @@ -173,8 +134,6 @@ class UI_CHROMEOS_EXPORT TouchExplorationController const ui::TouchEvent& event, scoped_ptr<ui::Event>* rewritten_event); ui::EventRewriteStatus InWaitForRelease( const ui::TouchEvent& event, scoped_ptr<ui::Event>* rewritten_event); - ui::EventRewriteStatus InSlideGesture( - const ui::TouchEvent& event, scoped_ptr<ui::Event>* rewritten_event); // This timer is started every time we get the first press event, and // it fires after the double-click timeout elapses (300 ms by default). @@ -198,8 +157,6 @@ class UI_CHROMEOS_EXPORT TouchExplorationController void OnSwipeEvent(ui::GestureEvent* swipe_gesture); - void SideSlideControl(ui::GestureEvent* gesture); - // Dispatches the keyboard short cut Shift+Search+<arrow key> // outside the event rewritting flow. void DispatchShiftSearchKeyEvent(const ui::KeyboardCode direction); @@ -213,22 +170,6 @@ class UI_CHROMEOS_EXPORT TouchExplorationController // default value. void ResetToNoFingersDown(); - void PlaySoundForTimer(); - - // Some constants used in touch_exploration_controller: - - // Within this many dips of the screen edge, the release event generated will - // reset the state to NoFingersDown. - const float kLeavingScreenEdge = 6; - - // Swipe/scroll gestures within these bounds (in DIPs) will change preset - // settings. - const float kMaxDistanceFromEdge = 75; - - // After a slide gesture has been triggered, if the finger is still within - // these bounds (in DIPs), the preset settings will still change. - const float kSlopDistanceFromEdge = kMaxDistanceFromEdge + 40; - enum State { // No fingers are down and no events are pending. NO_FINGERS_DOWN, @@ -295,28 +236,8 @@ class UI_CHROMEOS_EXPORT TouchExplorationController // generally useful for developing new features, because it creates a // simple way to handle a dead end in user flow. WAIT_FOR_RELEASE, - - // If the user is within the given bounds from an edge of the screen, not - // including corners, then the resulting movements will be interpreted as - // slide gestures. - SLIDE_GESTURE, }; - enum ScreenLocation { - // Hot "edges" of the screen are each represented by a respective bit. - NO_EDGE = 0, - RIGHT_EDGE = 1 << 0, - TOP_EDGE = 1 << 1, - LEFT_EDGE = 1 << 2, - BOTTOM_EDGE = 1 << 3, - }; - - // Given a point, if it is within the given bounds of an edge, returns the - // edge. If it is within the given bounds of two edges, returns an int with - // both bits that represent the respective edges turned on. Otherwise returns - // SCREEN_CENTER. - int FindEdgesWithinBounds(gfx::Point point, float bounds); - void VlogState(const char* function_name); void VlogEvent(const ui::TouchEvent& event, const char* function_name); @@ -326,9 +247,6 @@ class UI_CHROMEOS_EXPORT TouchExplorationController aura::Window* root_window_; - // Handles volume control. Not owned. - ui::TouchExplorationControllerDelegate* delegate_; - // A set of touch ids for fingers currently touching the screen. std::vector<int> current_touch_ids_; @@ -358,9 +276,6 @@ class UI_CHROMEOS_EXPORT TouchExplorationController // A timer to fire the mouse move event after the double-tap delay. base::OneShotTimer<TouchExplorationController> tap_timer_; - // A timer to fire an indicating sound when sliding to change volume. - base::RepeatingTimer<TouchExplorationController> sound_timer_; - // For testing only, an event handler to use for generated events // outside of the normal event rewriting flow. ui::EventHandler* event_handler_for_testing_; diff --git a/ui/chromeos/touch_exploration_controller_unittest.cc b/ui/chromeos/touch_exploration_controller_unittest.cc index d190578..70bac63 100644 --- a/ui/chromeos/touch_exploration_controller_unittest.cc +++ b/ui/chromeos/touch_exploration_controller_unittest.cc @@ -72,24 +72,6 @@ int Factorial(int n) { return n * Factorial(n - 1); } -class MockTouchExplorationControllerDelegate - : public ui::TouchExplorationControllerDelegate { - public: - virtual void PlayVolumeAdjustSound() OVERRIDE { - ++num_times_adjust_sound_played_; - } - virtual void SetOutputLevel(int volume) OVERRIDE { - volume_changes_.push_back(volume); - } - - const std::vector<float> VolumeChanges() { return volume_changes_; } - const size_t NumAdjustSounds() { return num_times_adjust_sound_played_; } - - private: - std::vector<float> volume_changes_; - size_t num_times_adjust_sound_played_ = 0; -}; - } // namespace class TouchExplorationControllerTestApi { @@ -128,29 +110,12 @@ class TouchExplorationControllerTestApi { touch_exploration_controller_->GESTURE_IN_PROGRESS; } - bool IsInSlideGestureStateForTesting() const { - return touch_exploration_controller_->state_ == - touch_exploration_controller_->SLIDE_GESTURE; - } - - gfx::Rect BoundsOfRootWindowInDIPForTesting() const { - return touch_exploration_controller_->root_window_->GetBoundsInScreen(); - } - // VLOGs should be suppressed in tests that generate a lot of logs, // for example permutations of nine touch events. void SuppressVLOGsForTesting(bool suppress) { touch_exploration_controller_->VLOG_on_ = !suppress; } - float GetMaxDistanceFromEdge() const { - return touch_exploration_controller_->kMaxDistanceFromEdge; - } - - float GetSlopDistanceFromEdge() const { - return touch_exploration_controller_->kSlopDistanceFromEdge; - } - private: scoped_ptr<TouchExplorationController> touch_exploration_controller_; @@ -247,9 +212,8 @@ class TouchExplorationTest : public aura::test::AuraTestBase { if (!on && touch_exploration_controller_.get()) { touch_exploration_controller_.reset(); } else if (on && !touch_exploration_controller_.get()) { - touch_exploration_controller_.reset( - new ui::TouchExplorationControllerTestApi( - new TouchExplorationController(root_window(), &delegate_))); + touch_exploration_controller_.reset(new TouchExplorationControllerTestApi( + new ui::TouchExplorationController(root_window()))); touch_exploration_controller_->SetEventHandlerForTesting( &event_capturer_); cursor_client()->ShowCursor(); @@ -292,22 +256,6 @@ class TouchExplorationTest : public aura::test::AuraTestBase { ->IsInGestureInProgressStateForTesting(); } - bool IsInSlideGestureState() { - return touch_exploration_controller_->IsInSlideGestureStateForTesting(); - } - - gfx::Rect BoundsOfRootWindowInDIP() { - return touch_exploration_controller_->BoundsOfRootWindowInDIPForTesting(); - } - - float GetMaxDistanceFromEdge() const{ - return touch_exploration_controller_->GetMaxDistanceFromEdge(); - } - - float GetSlopDistanceFromEdge() const{ - return touch_exploration_controller_->GetSlopDistanceFromEdge(); - } - base::TimeDelta Now() { // This is the same as what EventTimeForNow() does, but here we do it // with our simulated clock. @@ -319,7 +267,6 @@ class TouchExplorationTest : public aura::test::AuraTestBase { ui::GestureDetector::Config gesture_detector_config_; // Owned by |generator_|. base::SimpleTestTickClock* simulated_clock_; - MockTouchExplorationControllerDelegate delegate_; private: EventCapturer event_capturer_; @@ -562,9 +509,6 @@ TEST_F(TouchExplorationTest, TurnOnMidTouch) { TEST_F(TouchExplorationTest, TimerFiresLateDuringTouchExploration) { SwitchTouchExplorationMode(true); - // Make sure the touch is not in a corner of the screen. - generator_->MoveTouch(gfx::Point(100, 200)); - // Send a press, then add another finger after the double-tap timeout. generator_->PressTouchId(1); simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(1000)); @@ -1413,11 +1357,10 @@ TEST_F(TouchExplorationTest, FromGestureToPassthrough) { EXPECT_FALSE(IsInGestureInProgressState()); float distance = gesture_detector_config_.touch_slop + 1; - ui::TouchEvent first_press( - ui::ET_TOUCH_PRESSED, gfx::Point(100, 200), 0, Now()); + ui::TouchEvent first_press(ui::ET_TOUCH_PRESSED, gfx::Point(0, 1), 0, Now()); generator_->Dispatch(&first_press); simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(10)); - gfx::Point second_location(100 + distance, 200); + gfx::Point second_location(distance, 1); generator_->MoveTouch(second_location); EXPECT_TRUE(IsInGestureInProgressState()); EXPECT_FALSE(IsInTouchToMouseMode()); @@ -1445,193 +1388,4 @@ TEST_F(TouchExplorationTest, FromGestureToPassthrough) { ASSERT_EQ(0U, captured_events.size()); } -TEST_F(TouchExplorationTest, EnterSlideGestureState) { - SwitchTouchExplorationMode(true); - EXPECT_FALSE(IsInTouchToMouseMode()); - EXPECT_FALSE(IsInGestureInProgressState()); - - gfx::Rect window = BoundsOfRootWindowInDIP(); - float distance = gesture_detector_config_.touch_slop + 1; - ui::TouchEvent first_press( - ui::ET_TOUCH_PRESSED, gfx::Point(window.right(), 1), 0, Now()); - gfx::Point second_location(window.right(), 1 + distance / 2); - gfx::Point third_location(window.right(), 1 + distance); - - generator_->Dispatch(&first_press); - simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(10)); - - // Since we haven't moved past slop yet, we should not be in slide gesture. - generator_->MoveTouch(second_location); - EXPECT_FALSE(IsInTouchToMouseMode()); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_FALSE(IsInSlideGestureState()); - simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(10)); - - // Once we are out of slop, we should be in slide gesture since we are along - // the edge of the screen. - generator_->MoveTouch(third_location); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_TRUE(IsInSlideGestureState()); - EXPECT_FALSE(IsInTouchToMouseMode()); - const ScopedVector<ui::Event>& captured_events = GetCapturedEvents(); - ASSERT_EQ(0U, captured_events.size()); - - // Since we are at the right edge of the screen, but the sound timer has not - // elapsed, there should have two sounds that fired and two volume - // changes (one for each movement). - size_t num_adjust_sounds = delegate_.NumAdjustSounds(); - ASSERT_EQ(2U, num_adjust_sounds); - ASSERT_EQ(2U, delegate_.VolumeChanges().size()); - - // Exit out of slide gesture once touch is lifted, but not before even if the - // grace period is over. - - AdvanceSimulatedTimePastPotentialTapDelay(); - ASSERT_EQ(0U, captured_events.size()); - EXPECT_FALSE(IsInTouchToMouseMode()); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_TRUE(IsInSlideGestureState()); - - generator_->ReleaseTouch(); - ASSERT_EQ(0U, captured_events.size()); - EXPECT_FALSE(IsInTouchToMouseMode()); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_FALSE(IsInSlideGestureState()); -} - -// If a press + move occurred outside the boundaries, but within the slop -// boundaries and then moved into the boundaries of an edge, there still should -// not be a slide gesture. -TEST_F(TouchExplorationTest, AvoidEnteringSlideGesture) { - SwitchTouchExplorationMode(true); - - gfx::Rect window = BoundsOfRootWindowInDIP(); - float distance = gesture_detector_config_.touch_slop + 1; - ui::TouchEvent first_press( - ui::ET_TOUCH_PRESSED, - gfx::Point(window.right() - GetSlopDistanceFromEdge(), 1), - 0, - Now()); - gfx::Point out_of_slop(window.right() - GetSlopDistanceFromEdge() + distance, - 1); - gfx::Point into_boundaries(window.right() - GetMaxDistanceFromEdge() / 2, 1); - - generator_->Dispatch(&first_press); - simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(10)); - - generator_->MoveTouch(out_of_slop); - EXPECT_FALSE(IsInTouchToMouseMode()); - EXPECT_TRUE(IsInGestureInProgressState()); - EXPECT_FALSE(IsInSlideGestureState()); - simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(10)); - - // Since we did not start moving while in the boundaries, we should not be in - // slide gestures. - generator_->MoveTouch(into_boundaries); - EXPECT_TRUE(IsInGestureInProgressState()); - EXPECT_FALSE(IsInSlideGestureState()); - EXPECT_FALSE(IsInTouchToMouseMode()); - const ScopedVector<ui::Event>& captured_events = GetCapturedEvents(); - ASSERT_EQ(0U, captured_events.size()); - - generator_->ReleaseTouch(); -} - -// If the slide gesture begins within the boundaries and then moves -// SlopDistanceFromEdge there should still be a sound change. If the finger -// moves into the center screen, there should no longer be a sound change but it -// should still be in slide gesture. If the finger moves back into the edges -// without lifting, it should start changing sound again. -TEST_F(TouchExplorationTest, TestingBoundaries) { - SwitchTouchExplorationMode(true); - - gfx::Rect window = BoundsOfRootWindowInDIP(); - gfx::Point initial_press(window.right() - GetMaxDistanceFromEdge() / 2, 1); - ui::TouchEvent first_press(ui::ET_TOUCH_PRESSED, initial_press, 0, Now()); - gfx::Point touch_move(initial_press.x() + gesture_detector_config_.touch_slop, - 1); - gfx::Point into_slop_boundaries( - window.right() - GetSlopDistanceFromEdge() / 2, 1); - gfx::Point center_screen(window.right() / 2, window.bottom() / 2); - - generator_->Dispatch(&first_press); - simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(10)); - - generator_->MoveTouch(touch_move); - EXPECT_FALSE(IsInTouchToMouseMode()); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_FALSE(IsInSlideGestureState()); - simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(10)); - - // Move the touch into slop boundaries. It should stil be in slide gestures - // and adjust the volume. - generator_->MoveTouch(into_slop_boundaries); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_TRUE(IsInSlideGestureState()); - EXPECT_FALSE(IsInTouchToMouseMode()); - - // The sound is rate limiting so it only activates every 150ms. - simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(200)); - - size_t num_adjust_sounds = delegate_.NumAdjustSounds(); - ASSERT_EQ(2U, num_adjust_sounds); - ASSERT_EQ(2U, delegate_.VolumeChanges().size()); - - // Move the touch into the center of the window. It should still be in slide - // gestures, but there should not be anymore volume adjustments. - generator_->MoveTouch(center_screen); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_TRUE(IsInSlideGestureState()); - EXPECT_FALSE(IsInTouchToMouseMode()); - - simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(200)); - num_adjust_sounds = delegate_.NumAdjustSounds(); - ASSERT_EQ(2U, num_adjust_sounds); - ASSERT_EQ(2U, delegate_.VolumeChanges().size()); - - // Move the touch back into slop edge distance and volume should be changing - // again. - generator_->MoveTouch(into_slop_boundaries); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_TRUE(IsInSlideGestureState()); - EXPECT_FALSE(IsInTouchToMouseMode()); - - generator_->MoveTouch( - gfx::Point(into_slop_boundaries.x() + gesture_detector_config_.touch_slop, - into_slop_boundaries.y())); - simulated_clock_->Advance(base::TimeDelta::FromMilliseconds(200)); - - num_adjust_sounds = delegate_.NumAdjustSounds(); - ASSERT_EQ(3U, num_adjust_sounds); - ASSERT_EQ(3U, delegate_.VolumeChanges().size()); - - const ScopedVector<ui::Event>& captured_events = GetCapturedEvents(); - ASSERT_EQ(0U, captured_events.size()); - - generator_->ReleaseTouch(); -} - -// Even if the gesture starts within bounds, if it has not moved past slop -// within the grace period, it should go to touch exploration. -TEST_F(TouchExplorationTest, InBoundariesTouchExploration) { - SwitchTouchExplorationMode(true); - - gfx::Rect window = BoundsOfRootWindowInDIP(); - gfx::Point initial_press(window.right() - GetMaxDistanceFromEdge() / 2, 1); - ui::TouchEvent first_press( - ui::ET_TOUCH_PRESSED, - initial_press, - 0, - Now()); - generator_->Dispatch(&first_press); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_FALSE(IsInSlideGestureState()); - EXPECT_FALSE(IsInTouchToMouseMode()); - - AdvanceSimulatedTimePastTapDelay(); - EXPECT_FALSE(IsInGestureInProgressState()); - EXPECT_FALSE(IsInSlideGestureState()); - EXPECT_TRUE(IsInTouchToMouseMode()); -} - } // namespace ui |