| 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 "ash/magnifier/magnification_controller.h" | 5 #include "ash/magnifier/magnification_controller.h" |
| 6 | 6 |
| 7 #include "ash/accelerators/accelerator_controller.h" | 7 #include "ash/accelerators/accelerator_controller.h" |
| 8 #include "ash/accessibility_delegate.h" | 8 #include "ash/accessibility_delegate.h" |
| 9 #include "ash/ash_switches.h" | 9 #include "ash/ash_switches.h" |
| 10 #include "ash/display/root_window_transformers.h" | 10 #include "ash/display/root_window_transformers.h" |
| 11 #include "ash/host/ash_window_tree_host.h" | 11 #include "ash/host/ash_window_tree_host.h" |
| 12 #include "ash/host/root_window_transformer.h" | 12 #include "ash/host/root_window_transformer.h" |
| 13 #include "ash/root_window_controller.h" | 13 #include "ash/root_window_controller.h" |
| 14 #include "ash/screen_util.h" | 14 #include "ash/screen_util.h" |
| 15 #include "ash/shell.h" | 15 #include "ash/shell.h" |
| 16 #include "ash/system/tray/system_tray_delegate.h" | 16 #include "ash/system/tray/system_tray_delegate.h" |
| 17 #include "base/command_line.h" | 17 #include "base/command_line.h" |
| 18 #include "base/synchronization/waitable_event.h" | 18 #include "base/synchronization/waitable_event.h" |
| 19 #include "base/timer/timer.h" |
| 19 #include "ui/aura/client/aura_constants.h" | 20 #include "ui/aura/client/aura_constants.h" |
| 20 #include "ui/aura/client/cursor_client.h" | 21 #include "ui/aura/client/cursor_client.h" |
| 21 #include "ui/aura/window.h" | 22 #include "ui/aura/window.h" |
| 22 #include "ui/aura/window_tree_host.h" | 23 #include "ui/aura/window_tree_host.h" |
| 23 #include "ui/base/ime/input_method.h" | 24 #include "ui/base/ime/input_method.h" |
| 24 #include "ui/base/ime/input_method_observer.h" | 25 #include "ui/base/ime/input_method_observer.h" |
| 25 #include "ui/base/ime/text_input_client.h" | 26 #include "ui/base/ime/text_input_client.h" |
| 26 #include "ui/compositor/dip_util.h" | 27 #include "ui/compositor/dip_util.h" |
| 27 #include "ui/compositor/layer.h" | 28 #include "ui/compositor/layer.h" |
| 28 #include "ui/compositor/layer_animation_observer.h" | 29 #include "ui/compositor/layer_animation_observer.h" |
| (...skipping 11 matching lines...) Expand all Loading... |
| 40 namespace { | 41 namespace { |
| 41 | 42 |
| 42 const float kMaxMagnifiedScale = 4.0f; | 43 const float kMaxMagnifiedScale = 4.0f; |
| 43 const float kMaxMagnifiedScaleThreshold = 4.0f; | 44 const float kMaxMagnifiedScaleThreshold = 4.0f; |
| 44 const float kMinMagnifiedScaleThreshold = 1.1f; | 45 const float kMinMagnifiedScaleThreshold = 1.1f; |
| 45 const float kNonMagnifiedScale = 1.0f; | 46 const float kNonMagnifiedScale = 1.0f; |
| 46 | 47 |
| 47 const float kInitialMagnifiedScale = 2.0f; | 48 const float kInitialMagnifiedScale = 2.0f; |
| 48 const float kScrollScaleChangeFactor = 0.05f; | 49 const float kScrollScaleChangeFactor = 0.05f; |
| 49 | 50 |
| 51 // Default animation parameters for redrawing the magnification window. |
| 52 const gfx::Tween::Type kDefaultAnimationTweenType = gfx::Tween::EASE_OUT; |
| 53 const int kDefaultAnimationDurationInMs = 100; |
| 54 |
| 55 // Use linear transformation to make the magnifier window move smoothly |
| 56 // to center the focus when user types in a text input field. |
| 57 const gfx::Tween::Type kCenterCaretAnimationTweenType = gfx::Tween::LINEAR; |
| 58 |
| 59 // The delay of the timer for moving magnifier window for centering the text |
| 60 // input focus. |
| 61 const int kMoveMagnifierDelayInMs = 10; |
| 62 |
| 50 // Threadshold of panning. If the cursor moves to within pixels (in DIP) of | 63 // Threadshold of panning. If the cursor moves to within pixels (in DIP) of |
| 51 // |kPanningMergin| from the edge, the view-port moves. | 64 // |kCursorPanningMargin| from the edge, the view-port moves. |
| 52 const int kPanningMergin = 100; | 65 const int kCursorPanningMargin = 100; |
| 53 | 66 |
| 54 // Gives a little panning margin for following caret, so that we will move the | 67 // Threadshold of panning. If the caret moves to within pixels (in DIP) of |
| 55 // view-port before the caret is completely out of sight. | 68 // |kCaretPanningMargin| from the edge, the view-port moves. |
| 56 const int kCaretPanningMargin = 10; | 69 const int kCaretPanningMargin = 50; |
| 57 | 70 |
| 58 void MoveCursorTo(aura::WindowTreeHost* host, const gfx::Point& root_location) { | 71 void MoveCursorTo(aura::WindowTreeHost* host, const gfx::Point& root_location) { |
| 59 gfx::Point3F host_location_3f(root_location); | 72 gfx::Point3F host_location_3f(root_location); |
| 60 host->GetRootTransform().TransformPoint(&host_location_3f); | 73 host->GetRootTransform().TransformPoint(&host_location_3f); |
| 61 host->MoveCursorToHostLocation( | 74 host->MoveCursorToHostLocation( |
| 62 gfx::ToCeiledPoint(host_location_3f.AsPointF())); | 75 gfx::ToCeiledPoint(host_location_3f.AsPointF())); |
| 63 } | 76 } |
| 64 | 77 |
| 65 } // namespace | 78 } // namespace |
| 66 | 79 |
| 67 namespace ash { | 80 namespace ash { |
| 68 | 81 |
| 69 //////////////////////////////////////////////////////////////////////////////// | 82 //////////////////////////////////////////////////////////////////////////////// |
| 70 // MagnificationControllerImpl: | 83 // MagnificationControllerImpl: |
| 71 | 84 |
| 72 class MagnificationControllerImpl : virtual public MagnificationController, | 85 class MagnificationControllerImpl : virtual public MagnificationController, |
| 73 public ui::EventHandler, | 86 public ui::EventHandler, |
| 74 public ui::ImplicitAnimationObserver, | 87 public ui::ImplicitAnimationObserver, |
| 75 public aura::WindowObserver, | 88 public aura::WindowObserver, |
| 76 public ui::InputMethodObserver { | 89 public ui::InputMethodObserver { |
| 77 public: | 90 public: |
| 78 MagnificationControllerImpl(); | 91 MagnificationControllerImpl(); |
| 79 ~MagnificationControllerImpl() override; | 92 ~MagnificationControllerImpl() override; |
| 80 | 93 |
| 81 // MagnificationController overrides: | 94 // MagnificationController overrides: |
| 82 void SetEnabled(bool enabled) override; | 95 void SetEnabled(bool enabled) override; |
| 83 bool IsEnabled() const override; | 96 bool IsEnabled() const override; |
| 97 void SetKeepFocusCentered(bool keep_focus_centered) override; |
| 98 bool KeepFocusCentered() const override; |
| 84 void SetScale(float scale, bool animate) override; | 99 void SetScale(float scale, bool animate) override; |
| 85 float GetScale() const override { return scale_; } | 100 float GetScale() const override { return scale_; } |
| 86 void MoveWindow(int x, int y, bool animate) override; | 101 void MoveWindow(int x, int y, bool animate) override; |
| 87 void MoveWindow(const gfx::Point& point, bool animate) override; | 102 void MoveWindow(const gfx::Point& point, bool animate) override; |
| 88 gfx::Point GetWindowPosition() const override { | 103 gfx::Point GetWindowPosition() const override { |
| 89 return gfx::ToFlooredPoint(origin_); | 104 return gfx::ToFlooredPoint(origin_); |
| 90 } | 105 } |
| 91 void SetScrollDirection(ScrollDirection direction) override; | 106 void SetScrollDirection(ScrollDirection direction) override; |
| 92 gfx::Rect GetViewportRect() const override; | 107 gfx::Rect GetViewportRect() const override; |
| 93 void HandleFocusedNodeChanged( | 108 void HandleFocusedNodeChanged( |
| 94 bool is_editable_node, | 109 bool is_editable_node, |
| 95 const gfx::Rect& node_bounds_in_screen) override; | 110 const gfx::Rect& node_bounds_in_screen) override; |
| 96 void SwitchTargetRootWindow(aura::Window* new_root_window, | 111 void SwitchTargetRootWindow(aura::Window* new_root_window, |
| 97 bool redraw_original_root_window) override; | 112 bool redraw_original_root_window) override; |
| 98 | 113 |
| 99 // For test | 114 // For test |
| 100 gfx::Point GetPointOfInterestForTesting() override { | 115 gfx::Point GetPointOfInterestForTesting() override { |
| 101 return point_of_interest_; | 116 return point_of_interest_; |
| 102 } | 117 } |
| 103 | 118 |
| 104 bool IsOnAnimationForTesting() const override { return is_on_animation_; } | 119 bool IsOnAnimationForTesting() const override { return is_on_animation_; } |
| 105 | 120 |
| 121 void DisableMoveMagnifierDelayForTesting() override { |
| 122 disable_move_magnifier_delay_ = true; |
| 123 } |
| 124 |
| 106 private: | 125 private: |
| 107 // ui::ImplicitAnimationObserver overrides: | 126 // ui::ImplicitAnimationObserver overrides: |
| 108 void OnImplicitAnimationsCompleted() override; | 127 void OnImplicitAnimationsCompleted() override; |
| 109 | 128 |
| 110 // aura::WindowObserver overrides: | 129 // aura::WindowObserver overrides: |
| 111 void OnWindowDestroying(aura::Window* root_window) override; | 130 void OnWindowDestroying(aura::Window* root_window) override; |
| 112 void OnWindowBoundsChanged(aura::Window* window, | 131 void OnWindowBoundsChanged(aura::Window* window, |
| 113 const gfx::Rect& old_bounds, | 132 const gfx::Rect& old_bounds, |
| 114 const gfx::Rect& new_bounds) override; | 133 const gfx::Rect& new_bounds) override; |
| 115 | 134 |
| 116 // Redraws the magnification window with the given origin position and the | 135 // Redraws the magnification window with the given origin position and the |
| 117 // given scale. Returns true if the window is changed; otherwise, false. | 136 // given scale. Returns true if the window is changed; otherwise, false. |
| 118 // These methods should be called internally just after the scale and/or | 137 // These methods should be called internally just after the scale and/or |
| 119 // the position are changed to redraw the window. | 138 // the position are changed to redraw the window. |
| 120 bool Redraw(const gfx::PointF& position, float scale, bool animate); | 139 bool Redraw(const gfx::PointF& position, float scale, bool animate); |
| 121 bool RedrawDIP(const gfx::PointF& position, float scale, bool animate); | 140 |
| 141 // Redraws the magnification window with the given origin position in dip and |
| 142 // the given scale. Returns true if the window is changed; otherwise, false. |
| 143 // The last two parameters specify the animation duration and tween type. |
| 144 // If |animation_in_ms| is zero, there will be no animation, and |tween_type| |
| 145 // will be ignored. |
| 146 bool RedrawDIP(const gfx::PointF& position_in_dip, |
| 147 float scale, |
| 148 int animation_in_ms, |
| 149 gfx::Tween::Type tween_type); |
| 122 | 150 |
| 123 // 1) If the screen is scrolling (i.e. animating) and should scroll further, | 151 // 1) If the screen is scrolling (i.e. animating) and should scroll further, |
| 124 // it does nothing. | 152 // it does nothing. |
| 125 // 2) If the screen is scrolling (i.e. animating) and the direction is NONE, | 153 // 2) If the screen is scrolling (i.e. animating) and the direction is NONE, |
| 126 // it stops the scrolling animation. | 154 // it stops the scrolling animation. |
| 127 // 3) If the direction is set to value other than NONE, it starts the | 155 // 3) If the direction is set to value other than NONE, it starts the |
| 128 // scrolling/ animation towards that direction. | 156 // scrolling/ animation towards that direction. |
| 129 void StartOrStopScrollIfNecessary(); | 157 void StartOrStopScrollIfNecessary(); |
| 130 | 158 |
| 131 // Redraw with the given zoom scale keeping the mouse cursor location. In | 159 // Redraw with the given zoom scale keeping the mouse cursor location. In |
| (...skipping 27 matching lines...) Expand all Loading... |
| 159 // |x_panning_margin| and |y_pannin_margin| to the edge of the visible | 187 // |x_panning_margin| and |y_pannin_margin| to the edge of the visible |
| 160 // window region. The view port will be moved so that the |point| will be | 188 // window region. The view port will be moved so that the |point| will be |
| 161 // moved to the point where it has |x_target_margin| and |y_target_margin| | 189 // moved to the point where it has |x_target_margin| and |y_target_margin| |
| 162 // to the edge of the visible region. | 190 // to the edge of the visible region. |
| 163 void MoveMagnifierWindowFollowPoint(const gfx::Point& point, | 191 void MoveMagnifierWindowFollowPoint(const gfx::Point& point, |
| 164 int x_panning_margin, | 192 int x_panning_margin, |
| 165 int y_panning_margin, | 193 int y_panning_margin, |
| 166 int x_target_margin, | 194 int x_target_margin, |
| 167 int y_target_margin); | 195 int y_target_margin); |
| 168 | 196 |
| 197 // Moves the view port to center |point| in magnifier screen. |
| 198 void MoveMagnifierWindowCenterPoint(const gfx::Point& point); |
| 199 |
| 169 // Moves the viewport so that |rect| is fully visible. If |rect| is larger | 200 // Moves the viewport so that |rect| is fully visible. If |rect| is larger |
| 170 // than the viewport horizontally or vertically, the viewport will be moved | 201 // than the viewport horizontally or vertically, the viewport will be moved |
| 171 // to center the |rect| in that dimension. | 202 // to center the |rect| in that dimension. |
| 172 void MoveMagnifierWindowFollowRect(const gfx::Rect& rect); | 203 void MoveMagnifierWindowFollowRect(const gfx::Rect& rect); |
| 173 | 204 |
| 205 // Invoked when |move_magnifier_timer_| fires to move the magnifier window to |
| 206 // follow the caret. |
| 207 void OnMoveMagnifierTimer(); |
| 208 |
| 174 // ui::InputMethodObserver: | 209 // ui::InputMethodObserver: |
| 175 void OnTextInputTypeChanged(const ui::TextInputClient* client) override {} | 210 void OnTextInputTypeChanged(const ui::TextInputClient* client) override {} |
| 176 void OnFocus() override {} | 211 void OnFocus() override {} |
| 177 void OnBlur() override {} | 212 void OnBlur() override {} |
| 178 void OnTextInputStateChanged(const ui::TextInputClient* client) override {} | 213 void OnTextInputStateChanged(const ui::TextInputClient* client) override {} |
| 179 void OnInputMethodDestroyed(const ui::InputMethod* input_method) override {} | 214 void OnInputMethodDestroyed(const ui::InputMethod* input_method) override {} |
| 180 void OnShowImeIfNeeded() override {} | 215 void OnShowImeIfNeeded() override {} |
| 181 void OnCaretBoundsChanged(const ui::TextInputClient* client) override; | 216 void OnCaretBoundsChanged(const ui::TextInputClient* client) override; |
| 182 | 217 |
| 183 // Target root window. This must not be NULL. | 218 // Target root window. This must not be NULL. |
| 184 aura::Window* root_window_; | 219 aura::Window* root_window_; |
| 185 | 220 |
| 186 // True if the magnified window is currently animating a change. Otherwise, | 221 // True if the magnified window is currently animating a change. Otherwise, |
| 187 // false. | 222 // false. |
| 188 bool is_on_animation_; | 223 bool is_on_animation_; |
| 189 | 224 |
| 190 bool is_enabled_; | 225 bool is_enabled_; |
| 191 | 226 |
| 227 bool keep_focus_centered_; |
| 228 |
| 192 // True if the cursor needs to move the given position after the animation | 229 // True if the cursor needs to move the given position after the animation |
| 193 // will be finished. When using this, set |position_after_animation_| as well. | 230 // will be finished. When using this, set |position_after_animation_| as well. |
| 194 bool move_cursor_after_animation_; | 231 bool move_cursor_after_animation_; |
| 195 // Stores the position of cursor to be moved after animation. | 232 // Stores the position of cursor to be moved after animation. |
| 196 gfx::Point position_after_animation_; | 233 gfx::Point position_after_animation_; |
| 197 | 234 |
| 198 // Stores the last mouse cursor (or last touched) location. This value is | 235 // Stores the last mouse cursor (or last touched) location. This value is |
| 199 // used on zooming to keep this location visible. | 236 // used on zooming to keep this location visible. |
| 200 gfx::Point point_of_interest_; | 237 gfx::Point point_of_interest_; |
| 201 | 238 |
| 202 // Current scale, origin (left-top) position of the magnification window. | 239 // Current scale, origin (left-top) position of the magnification window. |
| 203 float scale_; | 240 float scale_; |
| 204 gfx::PointF origin_; | 241 gfx::PointF origin_; |
| 205 | 242 |
| 206 ScrollDirection scroll_direction_; | 243 ScrollDirection scroll_direction_; |
| 207 | 244 |
| 208 ui::InputMethod* input_method_; // Not owned. | 245 ui::InputMethod* input_method_; // Not owned. |
| 209 | 246 |
| 247 // Timer for moving magnifier window when it fires. |
| 248 base::OneShotTimer<MagnificationControllerImpl> move_magnifier_timer_; |
| 249 |
| 250 // Most recent caret position in |root_window_| coordinates. |
| 251 gfx::Point caret_point_; |
| 252 |
| 253 // Flag for disabling moving magnifier delay. It can only be true in testing |
| 254 // mode. |
| 255 bool disable_move_magnifier_delay_; |
| 256 |
| 210 DISALLOW_COPY_AND_ASSIGN(MagnificationControllerImpl); | 257 DISALLOW_COPY_AND_ASSIGN(MagnificationControllerImpl); |
| 211 }; | 258 }; |
| 212 | 259 |
| 213 //////////////////////////////////////////////////////////////////////////////// | 260 //////////////////////////////////////////////////////////////////////////////// |
| 214 // MagnificationControllerImpl: | 261 // MagnificationControllerImpl: |
| 215 | 262 |
| 216 MagnificationControllerImpl::MagnificationControllerImpl() | 263 MagnificationControllerImpl::MagnificationControllerImpl() |
| 217 : root_window_(Shell::GetPrimaryRootWindow()), | 264 : root_window_(Shell::GetPrimaryRootWindow()), |
| 218 is_on_animation_(false), | 265 is_on_animation_(false), |
| 219 is_enabled_(false), | 266 is_enabled_(false), |
| 267 keep_focus_centered_(false), |
| 220 move_cursor_after_animation_(false), | 268 move_cursor_after_animation_(false), |
| 221 scale_(kNonMagnifiedScale), | 269 scale_(kNonMagnifiedScale), |
| 222 scroll_direction_(SCROLL_NONE), | 270 scroll_direction_(SCROLL_NONE), |
| 223 input_method_(NULL) { | 271 input_method_(NULL), |
| 272 disable_move_magnifier_delay_(false) { |
| 224 Shell::GetInstance()->AddPreTargetHandler(this); | 273 Shell::GetInstance()->AddPreTargetHandler(this); |
| 225 root_window_->AddObserver(this); | 274 root_window_->AddObserver(this); |
| 226 point_of_interest_ = root_window_->bounds().CenterPoint(); | 275 point_of_interest_ = root_window_->bounds().CenterPoint(); |
| 227 } | 276 } |
| 228 | 277 |
| 229 MagnificationControllerImpl::~MagnificationControllerImpl() { | 278 MagnificationControllerImpl::~MagnificationControllerImpl() { |
| 230 if (input_method_) | 279 if (input_method_) |
| 231 input_method_->RemoveObserver(this); | 280 input_method_->RemoveObserver(this); |
| 232 | 281 |
| 233 root_window_->RemoveObserver(this); | 282 root_window_->RemoveObserver(this); |
| 234 | 283 |
| 235 Shell::GetInstance()->RemovePreTargetHandler(this); | 284 Shell::GetInstance()->RemovePreTargetHandler(this); |
| 236 } | 285 } |
| 237 | 286 |
| 238 void MagnificationControllerImpl::RedrawKeepingMousePosition( | 287 void MagnificationControllerImpl::RedrawKeepingMousePosition( |
| 239 float scale, bool animate) { | 288 float scale, bool animate) { |
| 240 gfx::Point mouse_in_root = point_of_interest_; | 289 gfx::Point mouse_in_root = point_of_interest_; |
| 241 | 290 |
| 242 // mouse_in_root is invalid value when the cursor is hidden. | 291 // mouse_in_root is invalid value when the cursor is hidden. |
| 243 if (!root_window_->bounds().Contains(mouse_in_root)) | 292 if (!root_window_->bounds().Contains(mouse_in_root)) |
| 244 mouse_in_root = root_window_->bounds().CenterPoint(); | 293 mouse_in_root = root_window_->bounds().CenterPoint(); |
| 245 | 294 |
| 246 const gfx::PointF origin = | 295 const gfx::PointF origin = |
| 247 gfx::PointF(mouse_in_root.x() - | 296 gfx::PointF(mouse_in_root.x() - |
| 248 (scale_ / scale) * (mouse_in_root.x() - origin_.x()), | 297 (scale_ / scale) * (mouse_in_root.x() - origin_.x()), |
| 249 mouse_in_root.y() - | 298 mouse_in_root.y() - |
| 250 (scale_ / scale) * (mouse_in_root.y() - origin_.y())); | 299 (scale_ / scale) * (mouse_in_root.y() - origin_.y())); |
| 251 bool changed = RedrawDIP(origin, scale, animate); | 300 bool changed = RedrawDIP(origin, scale, |
| 301 animate ? kDefaultAnimationDurationInMs : 0, |
| 302 kDefaultAnimationTweenType); |
| 252 if (changed) | 303 if (changed) |
| 253 AfterAnimationMoveCursorTo(mouse_in_root); | 304 AfterAnimationMoveCursorTo(mouse_in_root); |
| 254 } | 305 } |
| 255 | 306 |
| 256 bool MagnificationControllerImpl::Redraw(const gfx::PointF& position, | 307 bool MagnificationControllerImpl::Redraw(const gfx::PointF& position, |
| 257 float scale, | 308 float scale, |
| 258 bool animate) { | 309 bool animate) { |
| 259 const gfx::PointF position_in_dip = | 310 const gfx::PointF position_in_dip = |
| 260 ui::ConvertPointToDIP(root_window_->layer(), position); | 311 ui::ConvertPointToDIP(root_window_->layer(), position); |
| 261 return RedrawDIP(position_in_dip, scale, animate); | 312 return RedrawDIP(position_in_dip, scale, |
| 313 animate ? kDefaultAnimationDurationInMs : 0, |
| 314 kDefaultAnimationTweenType); |
| 262 } | 315 } |
| 263 | 316 |
| 264 bool MagnificationControllerImpl::RedrawDIP(const gfx::PointF& position_in_dip, | 317 bool MagnificationControllerImpl::RedrawDIP(const gfx::PointF& position_in_dip, |
| 265 float scale, | 318 float scale, |
| 266 bool animate) { | 319 int duration_in_ms, |
| 320 gfx::Tween::Type tween_type) { |
| 267 DCHECK(root_window_); | 321 DCHECK(root_window_); |
| 268 | 322 |
| 269 float x = position_in_dip.x(); | 323 float x = position_in_dip.x(); |
| 270 float y = position_in_dip.y(); | 324 float y = position_in_dip.y(); |
| 271 | 325 |
| 272 ValidateScale(&scale); | 326 ValidateScale(&scale); |
| 273 | 327 |
| 274 if (x < 0) | 328 if (x < 0) |
| 275 x = 0; | 329 x = 0; |
| 276 if (y < 0) | 330 if (y < 0) |
| (...skipping 24 matching lines...) Expand all Loading... |
| 301 // Flips the signs intentionally to convert them from the position of the | 355 // Flips the signs intentionally to convert them from the position of the |
| 302 // magnification window. | 356 // magnification window. |
| 303 transform.Scale(scale_, scale_); | 357 transform.Scale(scale_, scale_); |
| 304 transform.Translate(-origin_.x(), -origin_.y()); | 358 transform.Translate(-origin_.x(), -origin_.y()); |
| 305 | 359 |
| 306 ui::ScopedLayerAnimationSettings settings( | 360 ui::ScopedLayerAnimationSettings settings( |
| 307 root_window_->layer()->GetAnimator()); | 361 root_window_->layer()->GetAnimator()); |
| 308 settings.AddObserver(this); | 362 settings.AddObserver(this); |
| 309 settings.SetPreemptionStrategy( | 363 settings.SetPreemptionStrategy( |
| 310 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET); | 364 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET); |
| 311 settings.SetTweenType(gfx::Tween::EASE_OUT); | 365 settings.SetTweenType(tween_type); |
| 312 settings.SetTransitionDuration( | 366 settings.SetTransitionDuration( |
| 313 base::TimeDelta::FromMilliseconds(animate ? 100 : 0)); | 367 base::TimeDelta::FromMilliseconds(duration_in_ms)); |
| 314 | 368 |
| 315 gfx::Display display = | 369 gfx::Display display = |
| 316 Shell::GetScreen()->GetDisplayNearestWindow(root_window_); | 370 Shell::GetScreen()->GetDisplayNearestWindow(root_window_); |
| 317 scoped_ptr<RootWindowTransformer> transformer( | 371 scoped_ptr<RootWindowTransformer> transformer( |
| 318 CreateRootWindowTransformerForDisplay(root_window_, display)); | 372 CreateRootWindowTransformerForDisplay(root_window_, display)); |
| 319 GetRootWindowController(root_window_)->ash_host()->SetRootWindowTransformer( | 373 GetRootWindowController(root_window_)->ash_host()->SetRootWindowTransformer( |
| 320 transformer.Pass()); | 374 transformer.Pass()); |
| 321 | 375 |
| 322 if (animate) | 376 if (duration_in_ms > 0) |
| 323 is_on_animation_ = true; | 377 is_on_animation_ = true; |
| 324 | 378 |
| 325 return true; | 379 return true; |
| 326 } | 380 } |
| 327 | 381 |
| 328 void MagnificationControllerImpl::StartOrStopScrollIfNecessary() { | 382 void MagnificationControllerImpl::StartOrStopScrollIfNecessary() { |
| 329 // This value controls the scrolling speed. | 383 // This value controls the scrolling speed. |
| 330 const int kMoveOffset = 40; | 384 const int kMoveOffset = 40; |
| 331 if (is_on_animation_) { | 385 if (is_on_animation_) { |
| 332 if (scroll_direction_ == SCROLL_NONE) | 386 if (scroll_direction_ == SCROLL_NONE) |
| (...skipping 12 matching lines...) Expand all Loading... |
| 345 case SCROLL_RIGHT: | 399 case SCROLL_RIGHT: |
| 346 new_origin.Offset(kMoveOffset, 0); | 400 new_origin.Offset(kMoveOffset, 0); |
| 347 break; | 401 break; |
| 348 case SCROLL_UP: | 402 case SCROLL_UP: |
| 349 new_origin.Offset(0, -kMoveOffset); | 403 new_origin.Offset(0, -kMoveOffset); |
| 350 break; | 404 break; |
| 351 case SCROLL_DOWN: | 405 case SCROLL_DOWN: |
| 352 new_origin.Offset(0, kMoveOffset); | 406 new_origin.Offset(0, kMoveOffset); |
| 353 break; | 407 break; |
| 354 } | 408 } |
| 355 RedrawDIP(new_origin, scale_, true); | 409 RedrawDIP(new_origin, scale_, kDefaultAnimationDurationInMs, |
| 410 kDefaultAnimationTweenType); |
| 356 } | 411 } |
| 357 | 412 |
| 358 void MagnificationControllerImpl::OnMouseMove(const gfx::Point& location) { | 413 void MagnificationControllerImpl::OnMouseMove(const gfx::Point& location) { |
| 359 DCHECK(root_window_); | 414 DCHECK(root_window_); |
| 360 | 415 |
| 361 gfx::Point mouse(location); | 416 gfx::Point mouse(location); |
| 362 int margin = kPanningMergin / scale_; // No need to consider DPI. | 417 int margin = kCursorPanningMargin / scale_; // No need to consider DPI. |
| 363 MoveMagnifierWindowFollowPoint(mouse, margin, margin, margin, margin); | 418 MoveMagnifierWindowFollowPoint(mouse, margin, margin, margin, margin); |
| 364 } | 419 } |
| 365 | 420 |
| 366 gfx::Rect MagnificationControllerImpl::GetViewportRect() const { | 421 gfx::Rect MagnificationControllerImpl::GetViewportRect() const { |
| 367 return gfx::ToEnclosingRect(GetWindowRectDIP(scale_)); | 422 return gfx::ToEnclosingRect(GetWindowRectDIP(scale_)); |
| 368 } | 423 } |
| 369 | 424 |
| 370 void MagnificationControllerImpl::HandleFocusedNodeChanged( | 425 void MagnificationControllerImpl::HandleFocusedNodeChanged( |
| 371 bool is_editable_node, | 426 bool is_editable_node, |
| 372 const gfx::Rect& node_bounds_in_screen) { | 427 const gfx::Rect& node_bounds_in_screen) { |
| (...skipping 190 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 563 | 618 |
| 564 RedrawKeepingMousePosition(kNonMagnifiedScale, true); | 619 RedrawKeepingMousePosition(kNonMagnifiedScale, true); |
| 565 is_enabled_ = enabled; | 620 is_enabled_ = enabled; |
| 566 } | 621 } |
| 567 } | 622 } |
| 568 | 623 |
| 569 bool MagnificationControllerImpl::IsEnabled() const { | 624 bool MagnificationControllerImpl::IsEnabled() const { |
| 570 return is_enabled_; | 625 return is_enabled_; |
| 571 } | 626 } |
| 572 | 627 |
| 628 void MagnificationControllerImpl::SetKeepFocusCentered( |
| 629 bool keep_focus_centered) { |
| 630 keep_focus_centered_ = keep_focus_centered; |
| 631 } |
| 632 |
| 633 bool MagnificationControllerImpl::KeepFocusCentered() const { |
| 634 return keep_focus_centered_; |
| 635 } |
| 636 |
| 573 //////////////////////////////////////////////////////////////////////////////// | 637 //////////////////////////////////////////////////////////////////////////////// |
| 574 // MagnificationControllerImpl: aura::EventFilter implementation | 638 // MagnificationControllerImpl: aura::EventFilter implementation |
| 575 | 639 |
| 576 void MagnificationControllerImpl::OnMouseEvent(ui::MouseEvent* event) { | 640 void MagnificationControllerImpl::OnMouseEvent(ui::MouseEvent* event) { |
| 577 aura::Window* target = static_cast<aura::Window*>(event->target()); | 641 aura::Window* target = static_cast<aura::Window*>(event->target()); |
| 578 aura::Window* current_root = target->GetRootWindow(); | 642 aura::Window* current_root = target->GetRootWindow(); |
| 579 gfx::Rect root_bounds = current_root->bounds(); | 643 gfx::Rect root_bounds = current_root->bounds(); |
| 580 | 644 |
| 581 if (root_bounds.Contains(event->root_location())) { | 645 if (root_bounds.Contains(event->root_location())) { |
| 582 // This must be before |SwitchTargetRootWindow()|. | 646 // This must be before |SwitchTargetRootWindow()|. |
| (...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 655 // Panning up. | 719 // Panning up. |
| 656 y_diff = point.y() - (top + y_target_margin); | 720 y_diff = point.y() - (top + y_target_margin); |
| 657 start_zoom = true; | 721 start_zoom = true; |
| 658 } else if (bottom - y_panning_margin < point.y()) { | 722 } else if (bottom - y_panning_margin < point.y()) { |
| 659 // Panning down. | 723 // Panning down. |
| 660 y_diff = point.y() - (bottom - y_target_margin); | 724 y_diff = point.y() - (bottom - y_target_margin); |
| 661 start_zoom = true; | 725 start_zoom = true; |
| 662 } | 726 } |
| 663 int y = top + y_diff; | 727 int y = top + y_diff; |
| 664 if (start_zoom && !is_on_animation_) { | 728 if (start_zoom && !is_on_animation_) { |
| 665 // No animation on panning. | 729 bool ret = RedrawDIP(gfx::Point(x, y), scale_, |
| 666 bool animate = false; | 730 0, // No animation on panning. |
| 667 bool ret = RedrawDIP(gfx::Point(x, y), scale_, animate); | 731 kDefaultAnimationTweenType); |
| 668 | 732 |
| 669 if (ret) { | 733 if (ret) { |
| 670 // If the magnified region is moved, hides the mouse cursor and moves it. | 734 // If the magnified region is moved, hides the mouse cursor and moves it. |
| 671 if (x_diff != 0 || y_diff != 0) | 735 if (x_diff != 0 || y_diff != 0) |
| 672 MoveCursorTo(root_window_->GetHost(), point); | 736 MoveCursorTo(root_window_->GetHost(), point); |
| 673 } | 737 } |
| 674 } | 738 } |
| 675 } | 739 } |
| 676 | 740 |
| 741 void MagnificationControllerImpl::MoveMagnifierWindowCenterPoint( |
| 742 const gfx::Point& point) { |
| 743 DCHECK(root_window_); |
| 744 |
| 745 const gfx::Rect window_rect = GetViewportRect(); |
| 746 if (point == window_rect.CenterPoint()) |
| 747 return; |
| 748 |
| 749 if (!is_on_animation_) { |
| 750 // With animation on panning. |
| 751 RedrawDIP(window_rect.origin() + (point - window_rect.CenterPoint()), |
| 752 scale_, kDefaultAnimationDurationInMs, |
| 753 kCenterCaretAnimationTweenType); |
| 754 } |
| 755 } |
| 756 |
| 677 void MagnificationControllerImpl::MoveMagnifierWindowFollowRect( | 757 void MagnificationControllerImpl::MoveMagnifierWindowFollowRect( |
| 678 const gfx::Rect& rect) { | 758 const gfx::Rect& rect) { |
| 679 DCHECK(root_window_); | 759 DCHECK(root_window_); |
| 680 bool should_pan = false; | 760 bool should_pan = false; |
| 681 | 761 |
| 682 const gfx::Rect viewport_rect = GetViewportRect(); | 762 const gfx::Rect viewport_rect = GetViewportRect(); |
| 683 const int left = viewport_rect.x(); | 763 const int left = viewport_rect.x(); |
| 684 const int right = viewport_rect.right(); | 764 const int right = viewport_rect.right(); |
| 685 const gfx::Point rect_center = rect.CenterPoint(); | 765 const gfx::Point rect_center = rect.CenterPoint(); |
| 686 const gfx::Point window_center = viewport_rect.CenterPoint(); | 766 const gfx::Point window_center = viewport_rect.CenterPoint(); |
| (...skipping 13 matching lines...) Expand all Loading... |
| 700 // Panning vertically. | 780 // Panning vertically. |
| 701 y = rect_center.y() - viewport_rect.height() / 2; | 781 y = rect_center.y() - viewport_rect.height() / 2; |
| 702 should_pan = true; | 782 should_pan = true; |
| 703 } | 783 } |
| 704 | 784 |
| 705 if (should_pan) { | 785 if (should_pan) { |
| 706 if (is_on_animation_) { | 786 if (is_on_animation_) { |
| 707 root_window_->layer()->GetAnimator()->StopAnimating(); | 787 root_window_->layer()->GetAnimator()->StopAnimating(); |
| 708 is_on_animation_ = false; | 788 is_on_animation_ = false; |
| 709 } | 789 } |
| 710 RedrawDIP(gfx::Point(x, y), scale_, false); // No animation on panning. | 790 RedrawDIP(gfx::Point(x, y), scale_, |
| 791 0, // No animation on panning. |
| 792 kDefaultAnimationTweenType); |
| 711 } | 793 } |
| 712 } | 794 } |
| 713 | 795 |
| 796 void MagnificationControllerImpl::OnMoveMagnifierTimer() { |
| 797 MoveMagnifierWindowCenterPoint(caret_point_); |
| 798 } |
| 799 |
| 714 void MagnificationControllerImpl::OnCaretBoundsChanged( | 800 void MagnificationControllerImpl::OnCaretBoundsChanged( |
| 715 const ui::TextInputClient* client) { | 801 const ui::TextInputClient* client) { |
| 716 // caret bounds in screen coordinates. | 802 // caret bounds in screen coordinates. |
| 717 const gfx::Rect caret_bounds = client->GetCaretBounds(); | 803 const gfx::Rect caret_bounds = client->GetCaretBounds(); |
| 718 // Note: OnCaretBoundsChanged could be fired OnTextInputTypeChanged during | 804 // Note: OnCaretBoundsChanged could be fired OnTextInputTypeChanged during |
| 719 // which the caret position is not set a meaning position, and we do not | 805 // which the caret position is not set a meaning position, and we do not |
| 720 // need to adjust the view port position based on the bogus caret position. | 806 // need to adjust the view port position based on the bogus caret position. |
| 721 // This is only a transition period, the caret position will be fixed upon | 807 // This is only a transition period, the caret position will be fixed upon |
| 722 // focusing right after. | 808 // focusing right after. |
| 723 if (caret_bounds.width() == 0 && caret_bounds.height() == 0) | 809 if (caret_bounds.width() == 0 && caret_bounds.height() == 0) |
| 724 return; | 810 return; |
| 725 | 811 |
| 726 gfx::Point caret_origin = caret_bounds.origin(); | 812 caret_point_ = caret_bounds.CenterPoint(); |
| 727 // caret_origin in |root_window_| coordinates. | 813 // |caret_point_| in |root_window_| coordinates. |
| 728 wm::ConvertPointFromScreen(root_window_, &caret_origin); | 814 wm::ConvertPointFromScreen(root_window_, &caret_point_); |
| 729 | 815 |
| 730 // Visible window_rect in |root_window_| coordinates. | 816 // If the feature for centering the text input focus is disabled, the |
| 731 const gfx::Rect visible_window_rect = GetViewportRect(); | 817 // magnifier window will be moved to follow the focus with a panning margin. |
| 818 if (!KeepFocusCentered()) { |
| 819 // Visible window_rect in |root_window_| coordinates. |
| 820 const gfx::Rect visible_window_rect = GetViewportRect(); |
| 821 const int panning_margin = kCaretPanningMargin / scale_; |
| 822 MoveMagnifierWindowFollowPoint(caret_point_, |
| 823 panning_margin, |
| 824 panning_margin, |
| 825 visible_window_rect.width() / 2, |
| 826 visible_window_rect.height() / 2); |
| 827 return; |
| 828 } |
| 732 | 829 |
| 733 const int panning_margin = kCaretPanningMargin / scale_; | 830 // Move the magnifier window to center the focus with a little delay. |
| 734 MoveMagnifierWindowFollowPoint(caret_origin, panning_margin, panning_margin, | 831 // In Gmail compose window, when user types a blank space, it will insert |
| 735 visible_window_rect.width() / 2, | 832 // a non-breaking space(NBSP). NBSP will be replaced with a blank space |
| 736 visible_window_rect.height() / 2); | 833 // character when user types a non-blank space character later, which causes |
| 834 // OnCaretBoundsChanged be called twice. The first call moves the caret back |
| 835 // to the character position just before NBSP, replaces the NBSP with blank |
| 836 // space plus the new character, then the second call will move caret to the |
| 837 // position after the new character. In order to avoid the magnifier window |
| 838 // being moved back and forth with these two OnCaretBoundsChanged events, we |
| 839 // defer moving magnifier window until the |move_magnifier_timer_| fires, |
| 840 // when the caret settles eventually. |
| 841 move_magnifier_timer_.Stop(); |
| 842 move_magnifier_timer_.Start( |
| 843 FROM_HERE, |
| 844 base::TimeDelta::FromMilliseconds( |
| 845 disable_move_magnifier_delay_ ? 0 : kMoveMagnifierDelayInMs), |
| 846 this, &MagnificationControllerImpl::OnMoveMagnifierTimer); |
| 737 } | 847 } |
| 738 | 848 |
| 739 //////////////////////////////////////////////////////////////////////////////// | 849 //////////////////////////////////////////////////////////////////////////////// |
| 740 // MagnificationController: | 850 // MagnificationController: |
| 741 | 851 |
| 742 // static | 852 // static |
| 743 MagnificationController* MagnificationController::CreateInstance() { | 853 MagnificationController* MagnificationController::CreateInstance() { |
| 744 return new MagnificationControllerImpl(); | 854 return new MagnificationControllerImpl(); |
| 745 } | 855 } |
| 746 | 856 |
| 747 } // namespace ash | 857 } // namespace ash |
| OLD | NEW |