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/wm/power_button_controller.h" | 5 #include "ash/wm/power_button_controller.h" |
6 | 6 |
7 #include "ash/ash_switches.h" | 7 #include "ash/ash_switches.h" |
8 #include "ash/shell.h" | 8 #include "ash/shell.h" |
9 #include "ash/shell_delegate.h" | 9 #include "ash/shell_delegate.h" |
10 #include "ash/shell_window_ids.h" | 10 #include "ash/shell_window_ids.h" |
11 #include "ash/wm/cursor_manager.h" | 11 #include "ash/wm/session_state_animator.h" |
12 #include "base/command_line.h" | 12 #include "base/command_line.h" |
13 #include "base/logging.h" | |
14 #include "base/time.h" | |
15 #include "third_party/skia/include/core/SkColor.h" | |
16 #include "ui/aura/env.h" | |
17 #include "ui/aura/root_window.h" | 13 #include "ui/aura/root_window.h" |
18 #include "ui/aura/shared/compound_event_filter.h" | |
19 #include "ui/aura/window.h" | |
20 #include "ui/compositor/layer.h" | |
21 #include "ui/compositor/layer_animation_element.h" | |
22 #include "ui/compositor/layer_animation_sequence.h" | |
23 #include "ui/compositor/layer_animator.h" | |
24 #include "ui/gfx/canvas.h" | |
25 #include "ui/gfx/rect.h" | |
26 #include "ui/gfx/size.h" | |
27 #include "ui/gfx/transform.h" | |
28 | 14 |
29 namespace ash { | 15 namespace ash { |
30 | 16 |
31 namespace { | 17 namespace { |
32 | 18 |
33 // Amount of time that the power button needs to be held before we lock the | 19 // Amount of time that the power button needs to be held before we lock the |
34 // screen. | 20 // screen. |
35 const int kLockTimeoutMs = 400; | 21 const int kLockTimeoutMs = 400; |
36 | 22 |
37 // Amount of time that the power button needs to be held before we shut down. | 23 // Amount of time that the power button needs to be held before we shut down. |
(...skipping 14 matching lines...) Expand all Loading... |
52 | 38 |
53 // Amount of time taken to scale the snapshot of the screen back to its original | 39 // Amount of time taken to scale the snapshot of the screen back to its original |
54 // size when the button is released. | 40 // size when the button is released. |
55 const int kUndoSlowCloseAnimMs = 100; | 41 const int kUndoSlowCloseAnimMs = 100; |
56 | 42 |
57 // Amount of time taken to scale the snapshot down to a point in the center of | 43 // Amount of time taken to scale the snapshot down to a point in the center of |
58 // the screen once the screen has been locked or we've been notified that the | 44 // the screen once the screen has been locked or we've been notified that the |
59 // system is shutting down. | 45 // system is shutting down. |
60 const int kFastCloseAnimMs = 150; | 46 const int kFastCloseAnimMs = 150; |
61 | 47 |
62 // Amount of time taken to make the lock window fade in when the screen is | |
63 // locked. | |
64 const int kLockFadeInAnimMs = 200; | |
65 | |
66 // Additional time (beyond kFastCloseAnimMs) to wait after starting the | 48 // Additional time (beyond kFastCloseAnimMs) to wait after starting the |
67 // fast-close shutdown animation before actually requesting shutdown, to give | 49 // fast-close shutdown animation before actually requesting shutdown, to give |
68 // the animation time to finish. | 50 // the animation time to finish. |
69 const int kShutdownRequestDelayMs = 50; | 51 const int kShutdownRequestDelayMs = 50; |
70 | 52 |
71 // Slightly-smaller size that we scale the screen down to for the pre-lock and | |
72 // pre-shutdown states. | |
73 const float kSlowCloseSizeRatio = 0.95f; | |
74 | |
75 // Returns the transform that should be applied to containers for the slow-close | |
76 // animation. | |
77 ui::Transform GetSlowCloseTransform() { | |
78 gfx::Size root_size = Shell::GetPrimaryRootWindow()->bounds().size(); | |
79 ui::Transform transform; | |
80 transform.SetScale(kSlowCloseSizeRatio, kSlowCloseSizeRatio); | |
81 transform.ConcatTranslate( | |
82 floor(0.5 * (1.0 - kSlowCloseSizeRatio) * root_size.width() + 0.5), | |
83 floor(0.5 * (1.0 - kSlowCloseSizeRatio) * root_size.height() + 0.5)); | |
84 return transform; | |
85 } | |
86 | |
87 // Returns the transform that should be applied to containers for the fast-close | |
88 // animation. | |
89 ui::Transform GetFastCloseTransform() { | |
90 gfx::Size root_size = Shell::GetPrimaryRootWindow()->bounds().size(); | |
91 ui::Transform transform; | |
92 transform.SetScale(0.0, 0.0); | |
93 transform.ConcatTranslate(floor(0.5 * root_size.width() + 0.5), | |
94 floor(0.5 * root_size.height() + 0.5)); | |
95 return transform; | |
96 } | |
97 | |
98 // Slowly shrinks |window| to a slightly-smaller size. | |
99 void StartSlowCloseAnimationForWindow(aura::Window* window) { | |
100 ui::LayerAnimator* animator = window->layer()->GetAnimator(); | |
101 animator->set_preemption_strategy( | |
102 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET); | |
103 animator->StartAnimation( | |
104 new ui::LayerAnimationSequence( | |
105 ui::LayerAnimationElement::CreateTransformElement( | |
106 GetSlowCloseTransform(), | |
107 base::TimeDelta::FromMilliseconds(kSlowCloseAnimMs)))); | |
108 } | |
109 | |
110 // Quickly undoes the effects of the slow-close animation on |window|. | |
111 void StartUndoSlowCloseAnimationForWindow(aura::Window* window) { | |
112 ui::LayerAnimator* animator = window->layer()->GetAnimator(); | |
113 animator->set_preemption_strategy( | |
114 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET); | |
115 animator->StartAnimation( | |
116 new ui::LayerAnimationSequence( | |
117 ui::LayerAnimationElement::CreateTransformElement( | |
118 ui::Transform(), | |
119 base::TimeDelta::FromMilliseconds(kUndoSlowCloseAnimMs)))); | |
120 } | |
121 | |
122 // Quickly shrinks |window| down to a point in the center of the screen and | |
123 // fades it out to 0 opacity. | |
124 void StartFastCloseAnimationForWindow(aura::Window* window) { | |
125 ui::LayerAnimator* animator = window->layer()->GetAnimator(); | |
126 animator->set_preemption_strategy( | |
127 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET); | |
128 animator->StartAnimation( | |
129 new ui::LayerAnimationSequence( | |
130 ui::LayerAnimationElement::CreateTransformElement( | |
131 GetFastCloseTransform(), | |
132 base::TimeDelta::FromMilliseconds(kFastCloseAnimMs)))); | |
133 animator->StartAnimation( | |
134 new ui::LayerAnimationSequence( | |
135 ui::LayerAnimationElement::CreateOpacityElement( | |
136 0.0, base::TimeDelta::FromMilliseconds(kFastCloseAnimMs)))); | |
137 } | |
138 | |
139 // Fades |window| in to full opacity. | |
140 void FadeInWindow(aura::Window* window) { | |
141 ui::LayerAnimator* animator = window->layer()->GetAnimator(); | |
142 animator->set_preemption_strategy( | |
143 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET); | |
144 animator->StartAnimation( | |
145 new ui::LayerAnimationSequence( | |
146 ui::LayerAnimationElement::CreateOpacityElement( | |
147 1.0, base::TimeDelta::FromMilliseconds(kLockFadeInAnimMs)))); | |
148 } | |
149 | |
150 // Makes |window| fully transparent instantaneously. | |
151 void HideWindow(aura::Window* window) { | |
152 window->layer()->SetOpacity(0.0); | |
153 } | |
154 | |
155 // Restores |window| to its original position and scale and full opacity | |
156 // instantaneously. | |
157 void RestoreWindow(aura::Window* window) { | |
158 window->layer()->SetTransform(ui::Transform()); | |
159 window->layer()->SetOpacity(1.0); | |
160 } | |
161 | |
162 // Fills |containers| with the containers described by |container_mask|. | |
163 void GetContainers(int container_mask, aura::Window::Windows* containers) { | |
164 aura::RootWindow* root_window = Shell::GetPrimaryRootWindow(); | |
165 containers->clear(); | |
166 | |
167 if (container_mask & PowerButtonController::DESKTOP_BACKGROUND) { | |
168 containers->push_back(Shell::GetContainer( | |
169 root_window, | |
170 internal::kShellWindowId_DesktopBackgroundContainer)); | |
171 } | |
172 if (container_mask & PowerButtonController::NON_LOCK_SCREEN_CONTAINERS) { | |
173 containers->push_back(Shell::GetContainer( | |
174 root_window, | |
175 internal::kShellWindowId_NonLockScreenContainersContainer)); | |
176 } | |
177 if (container_mask & PowerButtonController::LOCK_SCREEN_BACKGROUND) { | |
178 containers->push_back(Shell::GetContainer( | |
179 root_window, | |
180 internal::kShellWindowId_LockScreenBackgroundContainer)); | |
181 } | |
182 if (container_mask & PowerButtonController::LOCK_SCREEN_CONTAINERS) { | |
183 containers->push_back(Shell::GetContainer( | |
184 root_window, | |
185 internal::kShellWindowId_LockScreenContainersContainer)); | |
186 } | |
187 if (container_mask & PowerButtonController::LOCK_SCREEN_RELATED_CONTAINERS) { | |
188 containers->push_back(Shell::GetContainer( | |
189 root_window, | |
190 internal::kShellWindowId_LockScreenRelatedContainersContainer)); | |
191 } | |
192 } | |
193 | |
194 // Apply animation |type| to all containers described by |container_mask|. | |
195 void StartAnimation(int container_mask, | |
196 PowerButtonController::AnimationType type) { | |
197 aura::Window::Windows containers; | |
198 GetContainers(container_mask, &containers); | |
199 | |
200 for (aura::Window::Windows::const_iterator it = containers.begin(); | |
201 it != containers.end(); ++it) { | |
202 aura::Window* window = *it; | |
203 switch (type) { | |
204 case PowerButtonController::ANIMATION_SLOW_CLOSE: | |
205 StartSlowCloseAnimationForWindow(window); | |
206 break; | |
207 case PowerButtonController::ANIMATION_UNDO_SLOW_CLOSE: | |
208 StartUndoSlowCloseAnimationForWindow(window); | |
209 break; | |
210 case PowerButtonController::ANIMATION_FAST_CLOSE: | |
211 StartFastCloseAnimationForWindow(window); | |
212 break; | |
213 case PowerButtonController::ANIMATION_FADE_IN: | |
214 FadeInWindow(window); | |
215 break; | |
216 case PowerButtonController::ANIMATION_HIDE: | |
217 HideWindow(window); | |
218 break; | |
219 case PowerButtonController::ANIMATION_RESTORE: | |
220 RestoreWindow(window); | |
221 break; | |
222 default: | |
223 NOTREACHED() << "Unhandled animation type " << type; | |
224 } | |
225 } | |
226 } | |
227 | |
228 } // namespace | 53 } // namespace |
229 | 54 |
230 bool PowerButtonController::TestApi::ContainersAreAnimated( | |
231 int container_mask, AnimationType type) const { | |
232 aura::Window::Windows containers; | |
233 GetContainers(container_mask, &containers); | |
234 for (aura::Window::Windows::const_iterator it = containers.begin(); | |
235 it != containers.end(); ++it) { | |
236 aura::Window* window = *it; | |
237 ui::Layer* layer = window->layer(); | |
238 | |
239 switch (type) { | |
240 case PowerButtonController::ANIMATION_SLOW_CLOSE: | |
241 if (layer->GetTargetTransform() != GetSlowCloseTransform()) | |
242 return false; | |
243 break; | |
244 case PowerButtonController::ANIMATION_UNDO_SLOW_CLOSE: | |
245 if (layer->GetTargetTransform() != ui::Transform()) | |
246 return false; | |
247 break; | |
248 case PowerButtonController::ANIMATION_FAST_CLOSE: | |
249 if (layer->GetTargetTransform() != GetFastCloseTransform() || | |
250 layer->GetTargetOpacity() > 0.0001) | |
251 return false; | |
252 break; | |
253 case PowerButtonController::ANIMATION_FADE_IN: | |
254 if (layer->GetTargetOpacity() < 0.9999) | |
255 return false; | |
256 break; | |
257 case PowerButtonController::ANIMATION_HIDE: | |
258 if (layer->GetTargetOpacity() > 0.0001) | |
259 return false; | |
260 break; | |
261 case PowerButtonController::ANIMATION_RESTORE: | |
262 if (layer->opacity() < 0.9999 || layer->transform() != ui::Transform()) | |
263 return false; | |
264 break; | |
265 default: | |
266 NOTREACHED() << "Unhandled animation type " << type; | |
267 return false; | |
268 } | |
269 } | |
270 return true; | |
271 } | |
272 | |
273 bool PowerButtonController::TestApi::BlackLayerIsVisible() const { | |
274 return controller_->black_layer_.get() && | |
275 controller_->black_layer_->visible(); | |
276 } | |
277 | |
278 gfx::Rect PowerButtonController::TestApi::GetBlackLayerBounds() const { | |
279 ui::Layer* layer = controller_->black_layer_.get(); | |
280 return layer ? layer->bounds() : gfx::Rect(); | |
281 } | |
282 | |
283 // static | |
284 int PowerButtonController::GetAllContainersMask() { | |
285 return PowerButtonController::DESKTOP_BACKGROUND | | |
286 PowerButtonController::NON_LOCK_SCREEN_CONTAINERS | | |
287 GetAllLockScreenContainersMask(); | |
288 } | |
289 | |
290 // static | |
291 int PowerButtonController::GetAllLockScreenContainersMask() { | |
292 return PowerButtonController::LOCK_SCREEN_BACKGROUND | | |
293 PowerButtonController::LOCK_SCREEN_CONTAINERS | | |
294 PowerButtonController::LOCK_SCREEN_RELATED_CONTAINERS; | |
295 } | |
296 | |
297 PowerButtonController::PowerButtonController() | 55 PowerButtonController::PowerButtonController() |
298 : login_status_(user::LOGGED_IN_NONE), | 56 : login_status_(user::LOGGED_IN_NONE), |
299 unlocked_login_status_(user::LOGGED_IN_NONE), | 57 unlocked_login_status_(user::LOGGED_IN_NONE), |
300 power_button_down_(false), | 58 power_button_down_(false), |
301 lock_button_down_(false), | 59 lock_button_down_(false), |
302 screen_is_off_(false), | 60 screen_is_off_(false), |
303 shutting_down_(false), | 61 shutting_down_(false), |
304 has_legacy_power_button_( | 62 has_legacy_power_button_( |
305 CommandLine::ForCurrentProcess()->HasSwitch( | 63 CommandLine::ForCurrentProcess()->HasSwitch( |
306 switches::kAuraLegacyPowerButton)) { | 64 switches::kAuraLegacyPowerButton)), |
| 65 animator_(new SessionStateAnimator()) { |
307 Shell::GetPrimaryRootWindow()->AddRootWindowObserver(this); | 66 Shell::GetPrimaryRootWindow()->AddRootWindowObserver(this); |
308 } | 67 } |
309 | 68 |
310 PowerButtonController::~PowerButtonController() { | 69 PowerButtonController::~PowerButtonController() { |
311 Shell::GetPrimaryRootWindow()->RemoveRootWindowObserver(this); | 70 Shell::GetPrimaryRootWindow()->RemoveRootWindowObserver(this); |
312 } | 71 } |
313 | 72 |
314 void PowerButtonController::OnLoginStateChanged(user::LoginStatus status) { | 73 void PowerButtonController::OnLoginStateChanged(user::LoginStatus status) { |
315 login_status_ = status; | 74 login_status_ = status; |
316 unlocked_login_status_ = user::LOGGED_IN_NONE; | 75 unlocked_login_status_ = user::LOGGED_IN_NONE; |
317 } | 76 } |
318 | 77 |
319 void PowerButtonController::OnAppTerminating() { | 78 void PowerButtonController::OnAppTerminating() { |
320 // If we hear that Chrome is exiting but didn't request it ourselves, all we | 79 // If we hear that Chrome is exiting but didn't request it ourselves, all we |
321 // can really hope for is that we'll have time to clear the screen. | 80 // can really hope for is that we'll have time to clear the screen. |
322 if (!shutting_down_) { | 81 if (!shutting_down_) { |
323 shutting_down_ = true; | 82 shutting_down_ = true; |
324 Shell* shell = ash::Shell::GetInstance(); | 83 Shell* shell = ash::Shell::GetInstance(); |
325 shell->cursor_manager()->ShowCursor(false); | 84 shell->cursor_manager()->ShowCursor(false); |
326 ShowBlackLayer(); | 85 animator_->ShowBlackLayer(); |
327 StartAnimation(GetAllContainersMask(), ANIMATION_HIDE); | 86 animator_->StartAnimation(SessionStateAnimator::GetAllContainersMask(), |
| 87 SessionStateAnimator::ANIMATION_HIDE); |
328 } | 88 } |
329 } | 89 } |
330 | 90 |
331 void PowerButtonController::OnLockStateChanged(bool locked) { | 91 void PowerButtonController::OnLockStateChanged(bool locked) { |
332 if (shutting_down_ || (login_status_ == user::LOGGED_IN_LOCKED) == locked) | 92 if (shutting_down_ || (login_status_ == user::LOGGED_IN_LOCKED) == locked) |
333 return; | 93 return; |
334 | 94 |
335 if (!locked && login_status_ == user::LOGGED_IN_LOCKED) { | 95 if (!locked && login_status_ == user::LOGGED_IN_LOCKED) { |
336 login_status_ = unlocked_login_status_; | 96 login_status_ = unlocked_login_status_; |
337 unlocked_login_status_ = user::LOGGED_IN_NONE; | 97 unlocked_login_status_ = user::LOGGED_IN_NONE; |
338 } else { | 98 } else { |
339 unlocked_login_status_ = login_status_; | 99 unlocked_login_status_ = login_status_; |
340 login_status_ = user::LOGGED_IN_LOCKED; | 100 login_status_ = user::LOGGED_IN_LOCKED; |
341 } | 101 } |
342 | 102 |
343 if (locked) { | 103 if (locked) { |
344 StartAnimation(LOCK_SCREEN_CONTAINERS, ANIMATION_FADE_IN); | 104 animator_->StartAnimation(SessionStateAnimator::LOCK_SCREEN_CONTAINERS, |
| 105 SessionStateAnimator::ANIMATION_FADE_IN); |
345 lock_timer_.Stop(); | 106 lock_timer_.Stop(); |
346 lock_fail_timer_.Stop(); | 107 lock_fail_timer_.Stop(); |
347 | 108 |
348 if (!has_legacy_power_button_ && power_button_down_) { | 109 if (!has_legacy_power_button_ && power_button_down_) { |
349 lock_to_shutdown_timer_.Stop(); | 110 lock_to_shutdown_timer_.Stop(); |
350 lock_to_shutdown_timer_.Start( | 111 lock_to_shutdown_timer_.Start( |
351 FROM_HERE, | 112 FROM_HERE, |
352 base::TimeDelta::FromMilliseconds(kLockToShutdownTimeoutMs), | 113 base::TimeDelta::FromMilliseconds(kLockToShutdownTimeoutMs), |
353 this, &PowerButtonController::OnLockToShutdownTimeout); | 114 this, &PowerButtonController::OnLockToShutdownTimeout); |
354 } | 115 } |
355 } else { | 116 } else { |
356 StartAnimation(DESKTOP_BACKGROUND | NON_LOCK_SCREEN_CONTAINERS, | 117 animator_->StartAnimation(SessionStateAnimator::DESKTOP_BACKGROUND | |
357 ANIMATION_RESTORE); | 118 SessionStateAnimator::NON_LOCK_SCREEN_CONTAINERS, |
358 HideBlackLayer(); | 119 SessionStateAnimator::ANIMATION_RESTORE); |
| 120 animator_->DropBlackLayer(); |
359 } | 121 } |
360 } | 122 } |
361 | 123 |
362 void PowerButtonController::OnScreenBrightnessChanged(double percent) { | 124 void PowerButtonController::OnScreenBrightnessChanged(double percent) { |
363 screen_is_off_ = percent <= 0.001; | 125 screen_is_off_ = percent <= 0.001; |
364 } | 126 } |
365 | 127 |
366 void PowerButtonController::OnStartingLock() { | 128 void PowerButtonController::OnStartingLock() { |
367 if (shutting_down_ || login_status_ == user::LOGGED_IN_LOCKED) | 129 if (shutting_down_ || login_status_ == user::LOGGED_IN_LOCKED) |
368 return; | 130 return; |
369 | 131 |
370 // Ensure that the black layer is visible -- if the screen was locked via | 132 // Ensure that the black layer is visible -- if the screen was locked via |
371 // the wrench menu, we won't have already shown the black background | 133 // the wrench menu, we won't have already shown the black background |
372 // as part of the slow-close animation. | 134 // as part of the slow-close animation. |
373 ShowBlackLayer(); | 135 animator_->ShowBlackLayer(); |
374 | 136 |
375 StartAnimation(NON_LOCK_SCREEN_CONTAINERS, ANIMATION_FAST_CLOSE); | 137 animator_->StartAnimation(SessionStateAnimator::NON_LOCK_SCREEN_CONTAINERS, |
| 138 SessionStateAnimator::ANIMATION_FAST_CLOSE); |
376 | 139 |
377 // Hide the screen locker containers so we can make them fade in later. | 140 // Hide the screen locker containers so we can make them fade in later. |
378 StartAnimation(LOCK_SCREEN_CONTAINERS, ANIMATION_HIDE); | 141 animator_->StartAnimation(SessionStateAnimator::LOCK_SCREEN_CONTAINERS, |
| 142 SessionStateAnimator::ANIMATION_HIDE); |
379 } | 143 } |
380 | 144 |
381 void PowerButtonController::OnPowerButtonEvent( | 145 void PowerButtonController::OnPowerButtonEvent( |
382 bool down, const base::TimeTicks& timestamp) { | 146 bool down, const base::TimeTicks& timestamp) { |
383 power_button_down_ = down; | 147 power_button_down_ = down; |
384 | 148 |
385 if (shutting_down_) | 149 if (shutting_down_) |
386 return; | 150 return; |
387 | 151 |
388 // Avoid starting the lock/shutdown sequence if the power button is pressed | 152 // Avoid starting the lock/shutdown sequence if the power button is pressed |
389 // while the screen is off (http://crbug.com/128451). | 153 // while the screen is off (http://crbug.com/128451). |
390 if (screen_is_off_) | 154 if (screen_is_off_) |
391 return; | 155 return; |
392 | 156 |
393 if (has_legacy_power_button_) { | 157 if (has_legacy_power_button_) { |
394 // If power button releases won't get reported correctly because we're not | 158 // If power button releases won't get reported correctly because we're not |
395 // running on official hardware, just lock the screen or shut down | 159 // running on official hardware, just lock the screen or shut down |
396 // immediately. | 160 // immediately. |
397 if (down) { | 161 if (down) { |
398 ShowBlackLayer(); | 162 animator_->ShowBlackLayer(); |
399 if (LoggedInAsNonGuest() && login_status_ != user::LOGGED_IN_LOCKED) { | 163 if (LoggedInAsNonGuest() && login_status_ != user::LOGGED_IN_LOCKED) { |
400 StartAnimation(NON_LOCK_SCREEN_CONTAINERS, ANIMATION_SLOW_CLOSE); | 164 animator_->StartAnimation( |
| 165 SessionStateAnimator::NON_LOCK_SCREEN_CONTAINERS, |
| 166 SessionStateAnimator::ANIMATION_SLOW_CLOSE); |
401 OnLockTimeout(); | 167 OnLockTimeout(); |
402 } else { | 168 } else { |
403 OnShutdownTimeout(); | 169 OnShutdownTimeout(); |
404 } | 170 } |
405 } | 171 } |
406 } else { // !has_legacy_power_button_ | 172 } else { // !has_legacy_power_button_ |
407 if (down) { | 173 if (down) { |
408 // If we already have a pending request to lock the screen, wait. | 174 // If we already have a pending request to lock the screen, wait. |
409 if (lock_fail_timer_.IsRunning()) | 175 if (lock_fail_timer_.IsRunning()) |
410 return; | 176 return; |
411 | 177 |
412 if (LoggedInAsNonGuest() && login_status_ != user::LOGGED_IN_LOCKED) | 178 if (LoggedInAsNonGuest() && login_status_ != user::LOGGED_IN_LOCKED) |
413 StartLockTimer(); | 179 StartLockTimer(); |
414 else | 180 else |
415 StartShutdownTimer(); | 181 StartShutdownTimer(); |
416 } else { // Button is up. | 182 } else { // Button is up. |
417 if (lock_timer_.IsRunning() || shutdown_timer_.IsRunning()) { | 183 if (lock_timer_.IsRunning() || shutdown_timer_.IsRunning()) { |
418 if (login_status_ == user::LOGGED_IN_LOCKED) { | 184 if (login_status_ == user::LOGGED_IN_LOCKED) { |
419 // If we've already started shutdown transition at lock screen | 185 // If we've already started shutdown transition at lock screen |
420 // desktop background needs to be restored immediately. | 186 // desktop background needs to be restored immediately. |
421 StartAnimation(DESKTOP_BACKGROUND, ANIMATION_RESTORE); | 187 animator_->StartAnimation(SessionStateAnimator::DESKTOP_BACKGROUND, |
| 188 SessionStateAnimator::ANIMATION_RESTORE); |
422 } | 189 } |
423 StartAnimation( | 190 animator_->StartAnimation( |
424 (login_status_ == user::LOGGED_IN_LOCKED) ? | 191 (login_status_ == user::LOGGED_IN_LOCKED) ? |
425 GetAllLockScreenContainersMask() : GetAllContainersMask(), | 192 SessionStateAnimator::GetAllLockScreenContainersMask() : |
426 ANIMATION_UNDO_SLOW_CLOSE); | 193 SessionStateAnimator::GetAllContainersMask(), |
| 194 SessionStateAnimator::ANIMATION_UNDO_SLOW_CLOSE); |
427 } | 195 } |
428 | 196 |
429 // Drop the black layer after the undo animation finishes. | 197 // Drop the black layer after the undo animation finishes. |
430 if (lock_timer_.IsRunning() || | 198 if (lock_timer_.IsRunning() || |
431 (shutdown_timer_.IsRunning() && !LoggedInAsNonGuest())) { | 199 (shutdown_timer_.IsRunning() && !LoggedInAsNonGuest())) { |
432 hide_black_layer_timer_.Stop(); | 200 animator_->ScheduleDropBlackLayer(); |
433 hide_black_layer_timer_.Start( | |
434 FROM_HERE, | |
435 base::TimeDelta::FromMilliseconds(kUndoSlowCloseAnimMs), | |
436 this, &PowerButtonController::HideBlackLayer); | |
437 } | 201 } |
438 | 202 |
439 lock_timer_.Stop(); | 203 lock_timer_.Stop(); |
440 shutdown_timer_.Stop(); | 204 shutdown_timer_.Stop(); |
441 lock_to_shutdown_timer_.Stop(); | 205 lock_to_shutdown_timer_.Stop(); |
442 } | 206 } |
443 } | 207 } |
444 } | 208 } |
445 | 209 |
446 void PowerButtonController::OnLockButtonEvent( | 210 void PowerButtonController::OnLockButtonEvent( |
447 bool down, const base::TimeTicks& timestamp) { | 211 bool down, const base::TimeTicks& timestamp) { |
448 lock_button_down_ = down; | 212 lock_button_down_ = down; |
449 | 213 |
450 if (shutting_down_ || !LoggedInAsNonGuest()) | 214 if (shutting_down_ || !LoggedInAsNonGuest()) |
451 return; | 215 return; |
452 | 216 |
453 // Bail if we're already locked or are in the process of locking. Also give | 217 // Bail if we're already locked or are in the process of locking. Also give |
454 // the power button precedence over the lock button (we don't expect both | 218 // the power button precedence over the lock button (we don't expect both |
455 // buttons to be present, so this is just making sure that we don't do | 219 // buttons to be present, so this is just making sure that we don't do |
456 // something completely stupid if that assumption changes later). | 220 // something completely stupid if that assumption changes later). |
457 if (login_status_ == user::LOGGED_IN_LOCKED || | 221 if (login_status_ == user::LOGGED_IN_LOCKED || |
458 lock_fail_timer_.IsRunning() || power_button_down_) | 222 lock_fail_timer_.IsRunning() || power_button_down_) |
459 return; | 223 return; |
460 | 224 |
461 if (down) { | 225 if (down) { |
462 StartLockTimer(); | 226 StartLockTimer(); |
463 } else { | 227 } else { |
464 if (lock_timer_.IsRunning()) { | 228 if (lock_timer_.IsRunning()) { |
465 StartAnimation(NON_LOCK_SCREEN_CONTAINERS, ANIMATION_UNDO_SLOW_CLOSE); | 229 animator_->StartAnimation( |
466 hide_black_layer_timer_.Stop(); | 230 SessionStateAnimator::NON_LOCK_SCREEN_CONTAINERS, |
467 hide_black_layer_timer_.Start( | 231 SessionStateAnimator::ANIMATION_UNDO_SLOW_CLOSE); |
468 FROM_HERE, | 232 animator_->ScheduleDropBlackLayer(); |
469 base::TimeDelta::FromMilliseconds(kUndoSlowCloseAnimMs), | |
470 this, &PowerButtonController::HideBlackLayer); | |
471 lock_timer_.Stop(); | 233 lock_timer_.Stop(); |
472 } | 234 } |
473 } | 235 } |
474 } | 236 } |
475 | 237 |
476 void PowerButtonController::RequestShutdown() { | 238 void PowerButtonController::RequestShutdown() { |
477 if (!shutting_down_) | 239 if (!shutting_down_) |
478 StartShutdownAnimationAndRequestShutdown(); | 240 StartShutdownAnimationAndRequestShutdown(); |
479 } | 241 } |
480 | 242 |
481 void PowerButtonController::OnRootWindowResized(const aura::RootWindow* root, | |
482 const gfx::Size& new_size) { | |
483 if (black_layer_.get()) | |
484 black_layer_->SetBounds(gfx::Rect(root->bounds().size())); | |
485 } | |
486 | |
487 void PowerButtonController::OnRootWindowHostCloseRequested( | 243 void PowerButtonController::OnRootWindowHostCloseRequested( |
488 const aura::RootWindow*) { | 244 const aura::RootWindow*) { |
489 if(Shell::GetInstance() && Shell::GetInstance()->delegate()) | 245 if(Shell::GetInstance() && Shell::GetInstance()->delegate()) |
490 Shell::GetInstance()->delegate()->Exit(); | 246 Shell::GetInstance()->delegate()->Exit(); |
491 } | 247 } |
492 | 248 |
493 bool PowerButtonController::LoggedInAsNonGuest() const { | 249 bool PowerButtonController::LoggedInAsNonGuest() const { |
494 if (login_status_ == user::LOGGED_IN_NONE) | 250 if (login_status_ == user::LOGGED_IN_NONE) |
495 return false; | 251 return false; |
496 if (login_status_ == user::LOGGED_IN_GUEST) | 252 if (login_status_ == user::LOGGED_IN_GUEST) |
497 return false; | 253 return false; |
498 // TODO(mukai): think about kiosk mode. | 254 // TODO(mukai): think about kiosk mode. |
499 return true; | 255 return true; |
500 } | 256 } |
501 | 257 |
502 void PowerButtonController::OnLockTimeout() { | 258 void PowerButtonController::OnLockTimeout() { |
503 delegate_->RequestLockScreen(); | 259 delegate_->RequestLockScreen(); |
504 lock_fail_timer_.Start( | 260 lock_fail_timer_.Start( |
505 FROM_HERE, | 261 FROM_HERE, |
506 base::TimeDelta::FromMilliseconds(kLockFailTimeoutMs), | 262 base::TimeDelta::FromMilliseconds(kLockFailTimeoutMs), |
507 this, &PowerButtonController::OnLockFailTimeout); | 263 this, &PowerButtonController::OnLockFailTimeout); |
508 } | 264 } |
509 | 265 |
510 void PowerButtonController::OnLockFailTimeout() { | 266 void PowerButtonController::OnLockFailTimeout() { |
511 DCHECK_NE(login_status_, user::LOGGED_IN_LOCKED); | 267 DCHECK_NE(login_status_, user::LOGGED_IN_LOCKED); |
512 LOG(ERROR) << "Screen lock request timed out"; | 268 LOG(ERROR) << "Screen lock request timed out"; |
513 StartAnimation(NON_LOCK_SCREEN_CONTAINERS, ANIMATION_RESTORE); | 269 animator_->StartAnimation(SessionStateAnimator::NON_LOCK_SCREEN_CONTAINERS, |
514 HideBlackLayer(); | 270 SessionStateAnimator::ANIMATION_RESTORE); |
| 271 animator_->DropBlackLayer(); |
515 } | 272 } |
516 | 273 |
517 void PowerButtonController::OnLockToShutdownTimeout() { | 274 void PowerButtonController::OnLockToShutdownTimeout() { |
518 DCHECK_EQ(login_status_, user::LOGGED_IN_LOCKED); | 275 DCHECK_EQ(login_status_, user::LOGGED_IN_LOCKED); |
519 StartShutdownTimer(); | 276 StartShutdownTimer(); |
520 } | 277 } |
521 | 278 |
522 void PowerButtonController::OnShutdownTimeout() { | 279 void PowerButtonController::OnShutdownTimeout() { |
523 if (!shutting_down_) | 280 if (!shutting_down_) |
524 StartShutdownAnimationAndRequestShutdown(); | 281 StartShutdownAnimationAndRequestShutdown(); |
525 } | 282 } |
526 | 283 |
527 void PowerButtonController::OnRealShutdownTimeout() { | 284 void PowerButtonController::OnRealShutdownTimeout() { |
528 DCHECK(shutting_down_); | 285 DCHECK(shutting_down_); |
529 delegate_->RequestShutdown(); | 286 delegate_->RequestShutdown(); |
530 } | 287 } |
531 | 288 |
532 void PowerButtonController::StartLockTimer() { | 289 void PowerButtonController::StartLockTimer() { |
533 ShowBlackLayer(); | 290 animator_->ShowBlackLayer(); |
534 StartAnimation(NON_LOCK_SCREEN_CONTAINERS, ANIMATION_SLOW_CLOSE); | 291 animator_->StartAnimation(SessionStateAnimator::NON_LOCK_SCREEN_CONTAINERS, |
| 292 SessionStateAnimator::ANIMATION_SLOW_CLOSE); |
535 lock_timer_.Stop(); | 293 lock_timer_.Stop(); |
536 lock_timer_.Start(FROM_HERE, | 294 lock_timer_.Start(FROM_HERE, |
537 base::TimeDelta::FromMilliseconds(kSlowCloseAnimMs), | 295 base::TimeDelta::FromMilliseconds(kSlowCloseAnimMs), |
538 this, &PowerButtonController::OnLockTimeout); | 296 this, &PowerButtonController::OnLockTimeout); |
539 } | 297 } |
540 | 298 |
541 void PowerButtonController::StartShutdownTimer() { | 299 void PowerButtonController::StartShutdownTimer() { |
542 ShowBlackLayer(); | 300 animator_->ShowBlackLayer(); |
543 StartAnimation(GetAllContainersMask(), ANIMATION_SLOW_CLOSE); | 301 animator_->StartAnimation(SessionStateAnimator::GetAllContainersMask(), |
| 302 SessionStateAnimator::ANIMATION_SLOW_CLOSE); |
544 shutdown_timer_.Stop(); | 303 shutdown_timer_.Stop(); |
545 shutdown_timer_.Start( | 304 shutdown_timer_.Start( |
546 FROM_HERE, | 305 FROM_HERE, |
547 base::TimeDelta::FromMilliseconds(kShutdownTimeoutMs), | 306 base::TimeDelta::FromMilliseconds(kShutdownTimeoutMs), |
548 this, &PowerButtonController::OnShutdownTimeout); | 307 this, &PowerButtonController::OnShutdownTimeout); |
549 } | 308 } |
550 | 309 |
551 void PowerButtonController::StartShutdownAnimationAndRequestShutdown() { | 310 void PowerButtonController::StartShutdownAnimationAndRequestShutdown() { |
552 DCHECK(!shutting_down_); | 311 DCHECK(!shutting_down_); |
553 shutting_down_ = true; | 312 shutting_down_ = true; |
554 | 313 |
555 Shell* shell = ash::Shell::GetInstance(); | 314 Shell* shell = ash::Shell::GetInstance(); |
556 shell->cursor_manager()->ShowCursor(false); | 315 shell->cursor_manager()->ShowCursor(false); |
557 | 316 |
558 ShowBlackLayer(); | 317 animator_->ShowBlackLayer(); |
559 if (login_status_ != user::LOGGED_IN_NONE) { | 318 if (login_status_ != user::LOGGED_IN_NONE) { |
560 // Hide the other containers before starting the animation. | 319 // Hide the other containers before starting the animation. |
561 // ANIMATION_FAST_CLOSE will make the screen locker windows partially | 320 // ANIMATION_FAST_CLOSE will make the screen locker windows partially |
562 // transparent, and we don't want the other windows to show through. | 321 // transparent, and we don't want the other windows to show through. |
563 StartAnimation(NON_LOCK_SCREEN_CONTAINERS, ANIMATION_HIDE); | 322 animator_->StartAnimation(SessionStateAnimator::NON_LOCK_SCREEN_CONTAINERS, |
564 StartAnimation(GetAllLockScreenContainersMask(), ANIMATION_FAST_CLOSE); | 323 SessionStateAnimator::ANIMATION_HIDE); |
| 324 animator_->StartAnimation( |
| 325 SessionStateAnimator::GetAllLockScreenContainersMask(), |
| 326 SessionStateAnimator::ANIMATION_FAST_CLOSE); |
565 } else { | 327 } else { |
566 StartAnimation(GetAllContainersMask(), ANIMATION_FAST_CLOSE); | 328 animator_->StartAnimation(SessionStateAnimator::GetAllContainersMask(), |
| 329 SessionStateAnimator::ANIMATION_FAST_CLOSE); |
567 } | 330 } |
568 | 331 |
569 real_shutdown_timer_.Start( | 332 real_shutdown_timer_.Start( |
570 FROM_HERE, | 333 FROM_HERE, |
571 base::TimeDelta::FromMilliseconds( | 334 base::TimeDelta::FromMilliseconds( |
572 kFastCloseAnimMs + kShutdownRequestDelayMs), | 335 kFastCloseAnimMs + kShutdownRequestDelayMs), |
573 this, &PowerButtonController::OnRealShutdownTimeout); | 336 this, &PowerButtonController::OnRealShutdownTimeout); |
574 } | 337 } |
575 | 338 |
576 void PowerButtonController::ShowBlackLayer() { | |
577 if (hide_black_layer_timer_.IsRunning()) | |
578 hide_black_layer_timer_.Stop(); | |
579 | |
580 if (!black_layer_.get()) { | |
581 black_layer_.reset(new ui::Layer(ui::LAYER_SOLID_COLOR)); | |
582 black_layer_->SetColor(SK_ColorBLACK); | |
583 | |
584 ui::Layer* root_layer = Shell::GetPrimaryRootWindow()->layer(); | |
585 black_layer_->SetBounds(root_layer->bounds()); | |
586 root_layer->Add(black_layer_.get()); | |
587 root_layer->StackAtBottom(black_layer_.get()); | |
588 } | |
589 black_layer_->SetVisible(true); | |
590 } | |
591 | |
592 void PowerButtonController::HideBlackLayer() { | |
593 black_layer_.reset(); | |
594 } | |
595 | |
596 } // namespace ash | 339 } // namespace ash |
OLD | NEW |